JZ42 连续子数组的最大和
/* 贪心 */
public class JZ42_1
{
public static int FindGreatestSumOfSubArray(int[] array)
{
int sum = 0, res = Integer.MIN_VALUE;
for (int i = 0; i < array.length; i++)
{
sum += array[i];
res = Math.max(res, sum);
if (sum < 0)
sum = 0;
}
return res;
}
}
/*
* dp
* dp[i]:以 array[i] 结尾的连续子数组最大和。
* 状态转移方程: dp[i] = Math.max(dp[i-1] + array[i], array[i]);
* */
public class JZ42_2
{
public static int FindGreatestSumOfSubArray(int[] array)
{
int[] dp = new int[array.length];
int res = array[0];
dp[0] = array[0];
for (int i = 1; i < array.length; i++)
{
dp[i] = Math.max(array[i], dp[i - 1] + array[i]);
res = Math.max(res, dp[i]);
}
return res;
}
}
JZ85 连续子数组的最大和(二)
/* 贪心(与JZ42类似) */
public class JZ85_1
{
public static int[] FindGreatestSumOfSubArray(int[] array)
{
int sum = 0, mmax = Integer.MIN_VALUE, len = -1, start = 0, idx = 0;
for (int i = 0; i < array.length; i++)
{
sum += array[i];
if (mmax == sum)
{
if (i - idx + 1 > len)
{
len = i - idx + 1;
start = idx;
}
}
if (mmax < sum)
{
mmax = sum;
len = i - idx + 1;
start = idx;
}
if (sum < 0)
{
idx = i + 1;
sum = 0;
}
}
int[] res = new int[len];
System.arraycopy(array, start, res, 0, len);
return res;
}
}
/*
* dp
* dp[i]:以 array[i] 结尾的连续子数组最大和。
* 状态转移方程: dp[i] = Math.max(dp[i-1] + array[i], array[i]);
* (与JZ42类似)
* */
public class JZ85_2
{
public static int[] FindGreatestSumOfSubArray(int[] array)
{
int[] dp = new int[array.length];
int mmax = array[0], idx = 0, start = 0, len = 1;
dp[0] = array[0];
for (int i = 1; i < array.length; i++)
{
dp[i] = dp[i - 1] + array[i];
if (dp[i] < array[i])
{
dp[i] = array[i];
idx = i;
}
if (mmax == dp[i])
{
if (i - idx + 1 > len)
{
len = i - idx + 1;
start = idx;
}
}
if (mmax < dp[i])
{
len = i - idx + 1;
start = idx;
mmax = dp[i];
}
}
int[] res = new int[len];
System.arraycopy(array, start, res, 0, len);
return res;
}
}
JZ69 跳台阶
/*
* dp
* dp[n]: 跳 n 级台阶,有 dp[n] 种跳法
* 状态转移方程: dp[n]=dp[n-1]+dp[n-2]
* */
public class JZ69_1
{
public static int jumpFloor(int number)
{
if (number <= 2) return number;
int[] dp = new int[number + 1];
dp[1] = 1;
dp[2] = 2;
for (int i = 3; i <= number; i++)
dp[i] = dp[i - 1] + dp[i - 2];
return dp[number];
}
}
/* 递归 */
public class JZ69_2
{
public static int jumpFloor(int number)
{
if (number <= 2) return number;
return jumpFloor(number - 1) + jumpFloor(number - 2);
}
}
JZ10 斐波那契数列
/* 递推 */
public class JZ10_1
{
public static int Fibonacci(int n)
{
if (n < 3) return 1;
int x1 = 1, x2 = 1;
for (int i = 3; i <= n; i++)
{
x2 = x1 + x2;
x1 = x2 - x1;
}
return x2;
}
}
/* 递归+备忘录 */
public class JZ10_2
{
public static int[] memo = new int[50];
public static int Fibonacci(int n)
{
if (memo[n] != 0) return memo[n];
if (n <= 2) return 1;
else
{
memo[n] = Fibonacci(n - 1) + Fibonacci(n - 2);
return memo[n];
}
}
}
JZ19 正则表达式匹配⭐
/* 递归 */
public class JZ19_1
{
public static boolean match(String str, String pattern)
{
return match(str, 0, pattern, 0);
}
private static boolean match(String str, int sIdx, String pattern, int pIdx)
{
if (str.length() == sIdx && pattern.length() == pIdx) return true;
if (pattern.length() == pIdx) return false;
boolean res = false;
if (pIdx + 1 < pattern.length() && pattern.charAt(pIdx + 1) == '*')
if (sIdx < str.length() && (str.charAt(sIdx) == pattern.charAt(pIdx) || pattern.charAt(pIdx) == '.'))
return match(str, sIdx, pattern, pIdx + 2) || match(str, sIdx+1, pattern , pIdx + 2) || match(str, sIdx+1, pattern, pIdx);
else
return match(str, sIdx, pattern, pIdx + 2);
else
{
if (sIdx < str.length() && (str.charAt(sIdx) == pattern.charAt(pIdx) || pattern.charAt(pIdx) == '.'))
return match(str, sIdx + 1, pattern, pIdx + 1);
else return false;
}
}
}
/* dp */
public class JZ19_2
{
public boolean match(String str, String pattern)
{
int n = str.length();
int m = pattern.length();
boolean[][] f = new boolean[n + 1][m + 1];
for (int i = 0; i <= n; i++)
{
for (int j = 0; j <= m; j++)
{
if (j == 0)
f[i][j] = i == 0;
else
{
if (pattern.charAt(j - 1) != '*')
{
if (i > 0 && (str.charAt(i - 1) == pattern.charAt(j - 1) || pattern.charAt(j - 1) == '.'))
f[i][j] = f[i - 1][j - 1];
}
else
{
if (j >= 2)
f[i][j] |= f[i][j - 2];
if (i >= 1 && j >= 2 && (str.charAt(i - 1) == pattern.charAt(j - 2) || pattern.charAt(j - 2) == '.'))
f[i][j] |= f[i - 1][j];
}
}
}
}
return f[n][m];
}
}
JZ71 跳台阶扩展问题
/* 找规律 */
public class JZ71_1
{
public static int jumpFloorII(int number)
{
return (int) Math.pow(2,number-1);
}
}
/* dp */
public class JZ71_2
{
public static int jumpFloorII(int number)
{
if (number <= 2) return number;
int[] dp = new int[number + 1];
dp[0] = 1;
dp[1] = 1;
dp[2] = 2;
for (int i = 3; i <= number; i++)
for (int j = 0; j < i; j++)
dp[i] += dp[j];
return dp[number];
}
}
JZ70 矩形覆盖
/* 找规律 */
public class JZ70_1
{
public static int rectCover(int target)
{
if (target == 0) return 0;
if (target <= 2) return target;
return rectCover(target - 1) + rectCover(target - 2);
}
}
JZ63 买卖股票的最好时机(一)⭐
/*
* dp
* dp[i][0]: 第i天不持股; dp[i][1]: 第i天持股;
* 状态转移方程:
* dp[i][0] = Math.max(dp[i-1][0], dp[i-1][1] + prices[i]);
* dp[i][1] = Math.max(dp[i-1][1], -prices[i]);
* */
public class JZ63_1
{
public static int maxProfit(int[] prices)
{
int[][] dp = new int[prices.length + 1][2];
dp[0][1] = -prices[0];
dp[0][0] = 0;
for (int i = 1; i < prices.length; i++)
{
dp[i][0] = Math.max(dp[i - 1][0], dp[i - 1][1] + prices[i]);
dp[i][1] = Math.max(dp[i - 1][1], -prices[i]);
}
return dp[prices.length - 1][0];
}
}
JZ47 礼物的最大价值
/* dp */
public class JZ47_1
{
public static int maxValue(int[][] grid)
{
int m = grid.length, n = grid[0].length;
int[][] dp = new int[m][n];
dp[0][0] = grid[0][0];
for (int i = 1; i < n; i++)
dp[0][i] = dp[0][i - 1] + grid[0][i];
for (int i = 1; i < m; i++)
dp[i][0] = dp[i - 1][0] + grid[i][0];
for (int i = 1; i < m; i++)
for (int j = 1; j < n; j++)
dp[i][j] = Math.max(dp[i - 1][j], dp[i][j - 1]) + grid[i][j];
return dp[m - 1][n - 1];
}
}
/* dfs+memo */
public class JZ47_2
{
public static int[][] memo;
public static int maxValue(int[][] grid)
{
int m = grid.length, n = grid[0].length;
memo = new int[m][n];
return dfs(grid, m - 1, n - 1);
}
public static int dfs(int[][] grid, int x, int y)
{
if (memo[x][y] != 0) return memo[x][y];
if (x == 0 && y == 0) return memo[x][y] = grid[0][0];
if (x == 0) return memo[x][y] = grid[x][y] + dfs(grid, x, y - 1);
if (y == 0) return memo[x][y] = grid[x][y] + dfs(grid, x - 1, y);
return memo[x][y] = grid[x][y] + Math.max(dfs(grid, x, y - 1), dfs(grid, x - 1, y));
}
}
JZ48 最长不含重复字符的子字符串
/* 滑动窗口 */
public class JZ48_1
{
public static int lengthOfLongestSubstring(String s)
{
int res = Integer.MIN_VALUE, left = 0, right = 0;
while (right < s.length())
{
while (left < right && s.substring(left, right).contains("" + s.charAt(right)))
left++;
right++;
res = Math.max(res, right - left);
}
return res;
}
}
public class JZ48_2
{
public static int lengthOfLongestSubstring(String s)
{
int[] dp = new int[s.length()];
int[] start = new int[s.length()];
int res = 1;
dp[0] = 1;
start[0] = 0;
for (int i = 1; i < s.length(); i++)
{
if (s.substring(start[i - 1], i).contains("" + s.charAt(i)))
{
int temp = s.substring(start[i - 1], i).indexOf("" + s.charAt(i)) + start[i - 1];
dp[i] = i - temp;
start[i] = temp + 1;
}
else
{
dp[i] = dp[i - 1] + 1;
start[i] = start[i - 1];
}
res = Math.max(res, dp[i]);
}
return res;
}
}
JZ46 把数字翻译成字符串⭐
/* dp */
public class JZ46_1
{
public static int solve(String nums)
{
if (nums.length() == 0) return 0;
if (nums.charAt(0) == '0') return 0;
if (nums.length() == 1) return 1;
int[] dp = new int[nums.length()];
dp[0] = 1;
dp[1] = 1;
if (new Integer(nums.substring(0, 2)) <= 26 && nums.charAt(1) != '0')
dp[1]++;
for (int i = 2; i < nums.length(); i++)
{
if (nums.charAt(i) == '0')
{
if (nums.charAt(i - 1) == '1' || nums.charAt(i - 1) == '2')
dp[i] = dp[i - 2];
else
break;
}
else
{
dp[i] = dp[i - 1];
if (nums.charAt(i - 1) != '0' && new Integer(nums.substring(i - 1, i + 1)) <= 26)
dp[i] += dp[i - 2];
}
}
return dp[nums.length() - 1];
}
}
/* 递归 */
public class JZ46_2
{
public int solve(String nums)
{
return back(nums.toCharArray(), 0);
}
public int back(char[] nums, int start)
{
if (start == nums.length) return 1;
if (nums[start] == '0') return 0;
int res1 = back(nums, start + 1);
int res2 = 0;
if ((start < nums.length - 1) && (nums[start] == '1' || (nums[start] == '2' && nums[start + 1] <= '6')))
res2 = back(nums, start + 2);
return res1 + res2;
}
}