方法一:暴力方法
使用两个变量 i 和 j ,它们分别表示买进这支股票和卖出这支股票,枚举它们在价格数组上可能出现的所有位置。编码很简单,相信大家都会,写一个二重循环即可。
public class Solution {
public int maxProfit(int[] prices) {
int len = prices.length;
if (len < 2) {
return 0;
}
// 有可能不做交易,因此结果的初始值设置为 0
int res = 0;
for (int i = 0; i < len - 1; i++) {
for (int j = i + 1; j < len; j++) {
res = Math.max(res, prices[j] - prices[i]);
}
}
return res;
}
}
方法二:针对暴力方法的优化
public class Solution {
public int maxProfit(int[] prices) {
int len = prices.length;
if (len < 2) {
return 0;
}
// 0:不进行任何操作
// 1:用户执行了一次买入操作
// 2:用户执行了一次卖出操作
// 状态转移方程:
// dp[i][0] 永远等于 0
// dp[i][1] = max(dp[i - 1][1], dp[i - 1][0] - prices[i])
// dp[i][2] = max(dp[i - 1][2], dp[i - 1][1] + prices[i])
// 注意:如果是 `[7, 6, 5, 4, 3]` 这种波动,应该不交易,
// 因此输出是:max(dp[len - 1][0], dp[len - 1][2])
int[][] dp = new int[len][3];
dp[0][0] = 0;
dp[0][1] = -prices[0];
// 这里状态 2 不应该有值,设置为 0 不影响正确性
dp[0][2] = 0;
for (int i = 1; i < len; i++) {
// 可以不显式赋值,因为 int 的初值就是 0
dp[i][0] = 0;
dp[i][1] = Math.max(dp[i - 1][1], dp[i - 1][0] - prices[i]);
dp[i][2] = Math.max(dp[i - 1][2], dp[i - 1][1] + prices[i]);
}
return Math.max(dp[len - 1][0], dp[len - 1][2]);
}
}