【问题标题】:Find maximum point out of n tasks从 n 个任务中找出最大点
【发布时间】:2015-09-08 18:09:15
【问题描述】:

确切的问题陈述:

给定N 任务,找出完成它们可以达到的最大点数

问题约束

完成N 任务需要T 分钟

可以随时提交解决方案,包括开始后的确切时间T 分钟

i-th 任务提交t 分钟后启动,会得到 maxPoints[i] - t * pointsPerMinute[i]积分

i-th 任务需要requiredTime[i] 分钟才能解决

输入格式

Line 1:T,可完成的总分钟数

Line 2maxPoints 的逗号分隔列表

Line 3pointsPerMinute 的逗号分隔列表

Line 4requiredTime 的逗号分隔列表

示例输入

75

250 500 1000

2 4 8

25 25 25

样本输出

1200

解释

首先,在比赛开始后几分钟解决第三个任务25。获取1000 - 8 * 25 = 800积分

第二,在比赛开始后的几分钟内解决第二个任务50。获取500 - 4 * 50 = 300积分

第三,在比赛开始后几分钟解决第一个任务75。获取250 - 2 * 75 = 100积分

总共获得800 + 300 + 100 = 1200

我能够通过排列和计算每个排列的点来获得解决方案。我无法为此找到优化的解决方案。

【问题讨论】:

  • 在一般的 NP-hard 问题中,检查maximum flow algorithm
  • 穷举算法(检查所有排列)可以通过注意某些排列/排列从一开始(或至少很早)就不是最佳的来优化

标签: algorithm task


【解决方案1】:

我使用贪心算法来解决这个问题。

我用 m 表示 maxPoint,p 表示 pointsPerMinute,r 表示 requiredTime。

考虑在完成B任务之前完成A任务,可以得到: 点(A, B) = m[A] - p[A] * r[A] + m[B] - p[B] * (r[A] + r[B])

在A任务之前完成B任务,可以获得: 点(B, A) = m[B] - p[B] * r[B] + m[A] - p[A] * (r[A] + r[B])

如果你应该在B任务之前完成A任务,Point(A, B)需要大于Point(B, A),所以Point(A, B) - Point(B, A) >= 0。

对于一些计算,我们可以得到:

r[A] / p[A]

也就是说,如果我们需要在 B 任务之前完成 A 任务,则 r[A] / p[A] 应该小于 r[B] / p[B]。我们可以以此对所有任务进行排序并计算答案。

【讨论】:

  • 谢谢,解释得很好。
  • 为了您的解释,我尝试将比率乘以因子: (maxPoint[A]/requredTime[A]) * (r[A]/p[A]) 并对该比率进行排序但是对于某些测试用例,它失败了。任何想法是否可以使用贪婪的方法来完成。
  • 嗨,我猜这是一个精度问题,所以你可以防止除法运算符,而是使用乘法。例如 bool cmp(Task p, Task q) { return p.requireTime * q.pointPerMinute
猜你喜欢
  • 2020-08-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-05-24
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-07-01
相关资源
最近更新 更多