At each index, you can jump to any index to the right. The score for a jump from i to j is (j - i) * nums[i]. We want to maximize the total score to reach the last index. This is a classic DP problem: for each position, the best way to reach it is from some previous position, and we want to maximize the sum.
Let dp[i] be the maximum score to reach index i. For each i, we can jump to any j > i, so for each j, dp[j] = max(dp[j], dp[i] + (j - i) * nums[i]). However, this is O(n^2) and too slow.
But, since (j - i) * nums[i] is linear in j, and we want to maximize dp[j], we can use a monotonic queue or convex hull trick to optimize. However, for this problem, a greedy approach works: the best jump is either directly to the end or to the next highest value. For each index, try all possible jumps (in practice, the optimal is to jump directly to the end or to the next local maximum).
But since the constraints are large, we can process from the end backwards: for each i, dp[i] = max over all j > i of (j - i) * nums[i] + dp[j]. Since we can jump to any j > i, the optimal is to jump directly to the end: dp[i] = (n-1 - i) * nums[i]. But sometimes, an intermediate jump gives a better result. So, we process from the end, and for each i, dp[i] = max((j - i) * nums[i] + dp[j]) for all j > i. This is a classic convex hull trick/monotonic queue optimization, but for simplicity, we provide a clear O(n^2) DP here.
#include<vector>#include<algorithm>usingnamespace std;
classSolution {
public:int maxScore(const vector<int>& nums) {
int n = nums.size();
vector<longlong> dp(n, 0);
dp[n-1] =0;
for (int i = n-2; i >=0; --i) {
longlong best =0;
for (int j = i+1; j < n; ++j) {
best = max(best, (longlong)(j - i) * nums[i] + dp[j]);
}
dp[i] = best;
}
returnstatic_cast<int>(dp[0]);
}
};
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
packagesolutionfuncmaxScore(nums []int) int {
n:= len(nums)
dp:= make([]int, n)
fori:=n-2; i>=0; i-- {
best:=0forj:=i+1; j < n; j++ {
score:= (j-i) *nums[i] +dp[j]
ifscore > best {
best = score }
}
dp[i] = best }
returndp[0]
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
classSolution {
publicintmaxScore(int[] nums) {
int n = nums.length;
long[] dp =newlong[n];
dp[n-1]= 0;
for (int i = n-2; i >= 0; --i) {
long best = 0;
for (int j = i+1; j < n; ++j) {
best = Math.max(best, (long)(j-i) * nums[i]+ dp[j]);
}
dp[i]= best;
}
return (int)dp[0];
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
classSolution {
funmaxScore(nums: IntArray): Int {
val n = nums.size
val dp = LongArray(n)
for (i in n - 2 downTo 0) {
var best = 0Lfor (j in i + 1 until n) {
best = maxOf(best, (j - i).toLong() * nums[i] + dp[j])
}
dp[i] = best
}
return dp[0].toInt()
}
}
1
2
3
4
5
6
7
8
9
10
classSolution:
defmaxScore(self, nums: list[int]) -> int:
n = len(nums)
dp = [0] * n
for i in range(n -2, -1, -1):
best =0for j in range(i +1, n):
best = max(best, (j - i) * nums[i] + dp[j])
dp[i] = best
return dp[0]
1
2
3
4
5
6
7
8
9
10
11
12
13
14
impl Solution {
pubfnmaxScore(nums: Vec<i32>) -> i32 {
let n = nums.len();
letmut dp =vec![0i64; n];
for i in (0..n-1).rev() {
letmut best =0i64;
for j in (i+1)..n {
best = best.max((j asi64- i asi64) * nums[i] asi64+ dp[j]);
}
dp[i] = best;
}
dp[0] asi32 }
}