及时卖腐烂的苹果

时间:2015-04-24 16:42:08

标签: algorithm sorting

我对以下问题感到困惑。你有好主意吗?当然,强制所有排列可以解决问题。但是,还有另一种方法吗?

假设你卖苹果,并且每个苹果都有相关的“腐烂时间”,直到它不再出售为止。

假设所有苹果都有一个独立的价格取决于它们的美学。价格是恒定的,直到苹果烂了,然后变成零。

卖苹果需要一些时间,因此你不能把它们全部卖掉,只能卖掉第一批苹果。

为了最大化您的结果,您应该以哪种顺序出售缓慢腐烂的苹果?

您是否有任何类型的文献可以提供帮助的提示?像运营研究或排队理论一样?

3 个答案:

答案 0 :(得分:4)

我认为一个简单的动态编程将起作用:

T(i, j) = 0 #if i>|apples|
T(i, j) = T(i+1, j) #if j/k >= rot(i)
T(i, j) = max(value(i) + T(i+1, j+1), T(i+1, j)) #if j/k < rot(i)

T(i, j)意味着在销售j苹果后,最高利润销售到第i个苹果。

在每个DP步骤中,您必须在销售或不销售当前苹果之间选择最佳。如果到目前为止销售的苹果数量(j)除以您可以按时间单位(k)销售的苹果数量达到了苹果&#34;时间腐烂&#34; 34; (rot(i)),它不能出售。

这里的一个诀窍就是你必须按时间分类,然后腐烂#34;第一

正确性

我会在这里粘贴Ilmari Karonen的评论,因为它解释了算法的正确性,不应仅仅是评论。

  

请注意,此解决方案的正确性主要取决于以下观察:如果苹果的某个子集可以出售,则可以按到期时间的升序出售。因此,如果您按到期时间按升序考虑所有苹果,那么您需要为每个苹果做出的唯一决定是现在是出售还是不出售它

实施

这是Python中一个简单的递归实现(可以很容易地记住多项式时间):

该计划还解释了必须选择哪些苹果以最大化结果:

A = [(2, 3), (1, 1), (3, 4), (1, 2)]

def solve(A, k, i, j):
    if i>=len(A): return (0, [])
    ttr, value = A[i]
    if j/k >= ttr:
        return solve(A, k, i+1, j)
    else:
        answer, explanation = solve(A, k, i+1, j+1)
        return max((value+answer, [A[i]]+explanation), solve(A, k, i+1, j))

print solve(sorted(A), 1, 0, 0)

输出:

(9, [(1, 2), (2, 3), (3, 4)])

答案 1 :(得分:2)

首先按时间对你的苹果进行分类。

如果最慢的腐烂苹果需要X个时间单位来腐烂,那么从X开始并朝着0个时间单位工作。 (Ben Voight观察到您实际上只需要min(time-to-sell-all-apples,time-until-last-apple-rots)

对于每个时间单位,选择之前未选择的最昂贵但尚未腐烂的苹果,并将其标记为在此时间单位内出售。如果没有未选择的未选择的苹果,立即跳到下一个最慢腐烂的苹果的时间单位。

您现在有一个从0到X的时间单位列表,以及与每个单位相关联的苹果。按此顺序出售苹果。

认为这是最优的,但我不确定。这有点违反直觉,因为您选择以相反的顺序在哪个时间出售哪个苹果

<小时/> 如果这些是你的苹果:

Index  1   2   3
Price  1  20  30
Time   1   3   3

然后我们为每个时段选择一个苹果,从三到零。

  • 首先是时间-3。这里未被选中的苹果是#2(价值20)和#3(价值30)我们选择#3(因为它值得更多)在时间-3出售。
  • 下一个时段是时间2。只有一个未被选中的未经选择的苹果 - #2(价值20),所以我们选择它在时间-2出售。
  • 下一个时段是时间-1。只有一个未被选中的未经选择的苹果 - #1(价值10),所以我们选择在时间-1出售的苹果。
  • 最后一个时间段是时间-0。没有苹果,所以我们在0时没有卖东西。

我假设我的示例中有一个零时隙,并且该时间过后,苹果腐烂,但算法都不需要这些>工作,他们只是改变了实施。

答案 2 :(得分:0)

假设时间是离散的,并且每个时间单位只能卖一个苹果,我认为以下算法可以解决问题。

按值递减的顺序对苹果进行排序。现在,标记苹果import pygame, RCcarFunctions, time pygame.init() try: while True: #get_pressed() returns a list of bools ? keypressed = pygame.key.get_pressed() if keypressed[pygame.K_w]: RCcarFunctions.forward() elif keypressed[pygame.K_a]: RCcarFunctions.spinleft() elif keypressed[pygame.K_s]: RCcarFunctions.reverse() elif keypressed[pygame.K_d]: RCcarFunctions.spinright() elif keypressed[pygame.K_ESCAPE]: RCcarFunctions.stop() pygame.event.pump() except KeyboardInterrupt: RCcarFunctions.cleanup()

让苹果及时腐烂[1,N]

让苹果具有值R1, R2, R3, ...

构造一个数组V1, V2, V3, ...。这是您出售每个苹果的顺序。

拿最贵的苹果。在S1, S2, S3, ...时间出售这个苹果。如果你以后卖掉苹果,它将毫无价值。如果你在任何早些时候出售苹果,你可能会在卖掉一个不同的苹果的时候出售它,而卖两个苹果比只出售一个苹果更有价值。

考虑具有第二高价值的苹果。如果R1不是R2,则在R1时间卖掉苹果。如果R2等于R2,则在时间R1出售此苹果。这样,我们仍然会尽可能晚地销售苹果以保持我们的选项开放,但仍然按值{R2-1优先于V2优先考虑苹果,{{1超过V3)。

对所有苹果执行上述操作。如果没有时间来卖苹果,那意味着在这段时间内只卖出更有价值的苹果,这是更好的选择。

在伪代码中:

V1