【问题标题】:False Mirrors. can you help me to solve?假镜。你能帮我解决吗?
【发布时间】:2011-05-18 16:34:50
【问题描述】:

这里是problem

BFG-9000 一次射击可摧毁三个相邻的阳台。 (第N个阳台紧邻 第一个)。射击后生存怪物对 Leonid 造成伤害 (小说的主要英雄)——每个怪物一个单位。进一步跟随新的拍摄等等 直到所有怪物 会灭亡。需要定义最小损坏量, 可以带狮子座。

例如:

N = 8
A[] = 4 5 6 5 4 5 6 5

answer : 33
4 * * * 4 5 6 5 - 24
4 * * * * * * 5 - 9
* * * * * * * * - 0

你能帮我解决这个问题吗?复杂性是什么?

【问题讨论】:

  • 天哪,我只花了 10 分钟写了一个解决方案,然后才意识到我的方法并不总是有效:-(

标签: algorithm dynamic-programming


【解决方案1】:

问题可以通过 DP 解决。

第一次拍摄后问题将不再是循环的。攻击后留下的怪物的伤害可以用DP计算。让NB 是阳台的数量。

D[n,m]定义为n<=mm+4<=n作为留在阳台上的怪物的伤害bn<=b<=mm<=b<=n

If n <= m < n+3 than D[n,m] = sum A[i] for n<=i<=m.
If m >= n+3 than D[n,m] =
   min{ 2*D[n,i-1] + D[i,i+2] + 2*D[i+3,m] } for i in {n,...,m}.
If m < n than D[n,m] =
   min{ 2*D[n,i-1] + D[i,i+2] + 2*D[i+3,m] } for i in {n,...,NB} U {1,...,m}.

结果是min{ D[i+3,NB+i-1] for i in {1,...,NB-2} }

在第三种情况下,结果索引以 NB 为模。

这种方法很复杂O(n^3)

【讨论】:

    【解决方案2】:

    看起来问题的限制是你可以暴力破解它。基本上

    def go(hit):
        res = 999 
        #base case, check if all items in hit are true.
        for i in range(len(hit)):
            if not hit[i]:
                 newhit = [x for x in hit]
                 newhit[i] = newhit[i-1] = newhit[(i+1)%len(hit)] = True; 
                 damage = 0;
                 for j in range(len(hit)):
                      if not newhit[j]:
                         damage+=hit[j]
                 res = min(res, go(newhit)+damage)
    

    您也可以将hit实现为位图,然后将其记忆以加快功能。

    【讨论】:

    • 我不懂python。你能告诉我这段代码的意思吗newhit = [x for x in hit]
    • @Elmi - 只是复制数组。最好将其实现为二进制值标记“命中”阳台的位集或整数
    • @spinnig_place 我不明白你的代码你能用 C++ 或 C 写吗?
    • 这更多地意味着伪代码。我不会为你写它,但这个想法只是创建一个递归函数,它接受一组代表哪些阳台已经消失的位。然后该函数考虑任何现有的阳台并将其与 2 个相邻的阳台一起拆除,然后递归。如果您有具体问题,我很乐意回答
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-08-29
    • 1970-01-01
    • 1970-01-01
    • 2022-12-15
    • 2011-01-24
    • 2020-09-03
    • 2021-08-14
    相关资源
    最近更新 更多