You will given each bomb's value and the 'effect range',and you need calculate the max value you can get.
eg. n=3 index 0's bomb' v is 2,range is 0(will not effect others).and v[1]=1,r[1]=1,v[2]=3,r[2]=1;
this case's max value is 5.(detonate the 0's and than the 2's).
HELP ME.
ps: It's a interval DP.
-------------------------------------------------------------------------------------------------------------------------------
Let dp[i][j] be the max value from ith and jth bomb on the circle, forcing i no greater than j.
Actually by denoting any kth (i <= k and k <= j) bomb, we got a precisely sub problem with smaller size, such that:
dp[i][j] = Max{ dp[i][bkd] + v[i] + dp[fwd][j] } , where bkd and fwd is by denoting kth bomb, the backward and foward range that not get effected.
Note this is a circle, sequence does matter, so dp[i][j] assumes from i to j, there are bombs, but from j to i, no bombs.
public class BombGame {
/**
* @param args
*/
public static void main(String[] args) {
BombGame bg = new BombGame();
System.out.println(bg.maxValue(new int[] {1, 3, 2}, new int[] {1, 1, 0}));
}
private int[] v;
private int[] r;
private int length;
private int[][] dp;
public int maxValue(int[] v, int[] r) {
this.v = v;
this.r = r;
this.length = v.length;
this.dp = new int[length][length];
for(int i = 0; i < length; i++) {
dp[i][i] = v[i];
}
return maxValueInternal(0, length - 1);
}
private int maxValueInternal(int start, int end) {
if(start > end) return 0;
if (start == end || dp[start][end] != 0)
return dp[start][end];
for (int i = start; i <= end; i++) {
// denote i
int fwd = i + r[i] + 1;
int bkd = i - r[i] - 1;
//this is a little tricky, as we have to consider
//when the range is very big, it destroy the end
//bomb, thus changing the end range
int end_ = (bkd + length) % length;
end_ = end_ < end ? end_ : end;
dp[start][end] = Math.max(dp[start][end],
maxValueInternal(start, bkd) + v[i] + maxValueInternal(fwd, end_));
}
return dp[start][end];
}
}