无法理解dp解决方案

时间:2013-10-30 16:34:00

标签: algorithm dynamic-programming

问题如下:

  

Lazer Tag包含一个小组游戏,在整个游戏过程中,您将被分配固定数量的子弹(通常称为激光镜头)。每个右手射击你的目标敌人,给你一点。

     

考虑一系列的命中和未命中,可以用“x”和“o”的形式表示,其中“o”表示命中,“x”表示未命中。假设该系列的形式为“xxxoooxxxxooxxo”,那么你的最终得分将等于3^2 + 2^2 +1^2,即在整个游戏过程中将每个最大连续命中数的平方加起来。

     

正确击中第j次击球的概率(1≤j≤n)是P(j)。简单来说,在第j个转弯处获得系列中“o”的概率是P(j)。您需要在回合结束时计算预期得分。

我可以使用memoization理解这个O(n ^ 2)解决方案,但问题需要一个O(n)解决方案。我见过O(n)解决方案,但我无法理解。 O(n)解决方案如下:

for(i = 1; i <= n; i++)
    dp[i] = (dp[i-1] + p[i-1]) * p[i];   
for(i = 1; i <= n; i++)
    ans+=2 * dp[i] + p[i];

其中p [i]是击中第i个目标的概率。任何人都可以解释O(n)解决方案的工作原理吗?

1 个答案:

答案 0 :(得分:3)

您可以通过以下方式考虑得分:

  1. 每次点击1分
  2. 每次运行长度> 1的点击(多次重叠计分)
  3. 例如,一系列xxooox会得分:

      每个o的
    1. +1
    2. +2 for ooo
    3. +2 for first oo
    4. +2 for second oo
    5. 得分= 1 * 3 + 2 * 3 = 3 + 6 = 9分。 (这与原来的得分方式相符,因为9 = 3 * 3)

      dp [i]计算在位置i结束的长度> 1的预期运行次数。

      因此,要计算总预期分数,我们需要总和2 * dp [i](因为我们每次运行得到2分),再加上p [i]之和,加上每个得分1分的预期分数击中。

      递归关系是因为在位置i结束的长度> 1的预期运行次数将是:

      1. +1,如果我们通过在i和i-1点击(位置i [概率p [i] * p [i-1])
      2. 从位置i开始新的运行
      3. + dp [i-1]如果我们通过获得另一个命中(概率p [i])继续在位置i-1结束的运行