- Maximum Subarray
https://leetcode.com/problems/maximum-subarray/description/
Given an integer array nums, find the contiguous subarray (containing at least one number) which has the largest sum and return its sum.
Follow up: If you have figured out the O(n) solution, try coding another solution using the divide and conquer approach, which is more subtle.
contiguous adj. 连续的;邻近的;接触的
subarray :n. 子阵列;子数组
divide 分治,v. (使)分开,分成;分配,分担;分隔;(道路)分叉;使产生分歧;(数)除,除以
subtle :adj. 微妙的;精细的;敏感的;狡猾的;稀薄的
’
’
题目的意思就是,给一个整型数组,找到相邻的一段数据(至少一个元素)是最大和的子数组,并返回这个最大和.
后续:如果您已经找到了O(n)解决方案,那么尝试使用分治法编写另一个解决方案,后者更加微妙。
题解:
这就是最基础的dp,最开始做的dp就长这个样子,我们要算数组中的最大值 ,相当于算0-n的这段的最大值,相当于算0-n-1这段的最大值,然后在加上(或者不加最后一个),相当于算0-n-2中的最大值,然后再觉得加还是不加a[n-1],所以dp就出来了 f[i],设f[i],为前i个数的最大值,则,动态方程就出来了:
f[i] = max(f[i-1]+a[i] , a[i]) 当然还有细节要处理.这里先不管来推一次: 其实我觉得我这里的推到过程不是很详细,我们可以这样看 :
f(0) =max(0,a[0]);
f(1) = max(f[0]+a[1] , a[1]);
f(2) = max(f[1]+a[2], a[2]);
这样我们就把包括a[n]的所有的最大子序和算出来了,然后找到最大值返回就行了
代码:
class Solution {
public:
int maxSubArray(vector<int>& a) {
int size = a.size();
if(size == 0) return 0;
int f[20003] , maxn = a[0];
f[0] = max(0,a[0]);
for(int i=1;i<size ; i++ )
{
f[i] = max(f[i-1]+a[i] , a[i]);//算出每个包括ai的最大的自诩和
if(maxn<f[i]) maxn = f[i];
}
return maxn;
}
};
- Minimum Path Sum
https://leetcode-cn.com/problems/minimum-path-sum/
Given a m x n grid filled with non-negative numbers, find a path from top left to bottom right which minimizes the sum of all numbers along its path.
Note: You can only move either down or right at any point in time.
Example:
Input:
[
[1,3,1],
[1,5,1],
[4,2,1]
]
Output: 7
Explanation: Because the path 1→3→1→1→1 minimizes the sum.
翻译:
grid :n. 网格;格子,栅格;输电网
top left to bottom righ :左上角到右下角
all numbers along its path.:路径上的和
’
’
最短路径,
给你一个m*n的网格,填满了非负整数,找到一个从左上角到右下角的路径,使得路径上的的数字和最小.
说明:你只能向下或者想右移动
题解::
虽然不知道怎么回事但是,但是由于最近在练习dp,所以要用dp思路: 由于我们要找左上到右下的 ,那我们把到每个地方的路径和求出来就行,因为只能像右和下走,所以,我们到左和下的全都标记为1(因为只能有一种方法到达),
找到每种方法用掉路径值最小的方法.
动态方程:
f[0][0]=a[0][0];
f[ 1][0] = f[0][0]+a[1][0];
f[ 2][0] = f[1][0]+a[2][0];
f[ 3][0] = f[2][0]+a[3][0];
…
f[0][1] = f[0][0]+a[0][1];
f[0][2] = f[0][1]+a[0][2];
f[0][3] = f[0][2]+a[0][3];
f[0][4] = f[0][3]+a[0][4];
f[0][5] = f[0][4]+a[0][5];
f[0][6] = f[0][5]+a[0][6];
//初始化成功:
看
f[i[j] =min(f[i-1][j] ,f[i][j-1])+a[i][j];//他们两个中间的最小值
class Solution {
public:
int minPathSum(vector<vector<int>>& grid) {
int size_row = grid.size(); //获取行数
int size_col = grid[0].size(); //获取列数
int f[1000][1000];
f[0][0] =grid[0][0];
for(int i = 1;i<size_row ;i++)
{
f[i][0] = grid[i][0]+f[i-1][0];
// cout<<f[i][0]<<endl;
}
//cout<<endl;
for(int i = 1;i<size_col ;i++)
{
f[0][i] = grid[0][i]+f[0][i-1];
// cout<<f[0][i]<<endl;
}
//cout<<endl;
for(int i = 1;i<size_row ;i++)
{
for(int j = 1;j<size_col ;j++)
{
f[i][j] = min(f[i-1][j] +grid[i][j] , f[i][j-1]+grid[i][j]);
// cout<<f[i][j]<<endl;
}
}
return f[size_row-1][size_col-1];
}
};
- Unique Paths
https://leetcode-cn.com/problems/unique-paths/
A robot is located at the top-left corner of a m x n grid (marked ‘Start’ in the diagram below).
The robot can only move either down or right at any point in time. The robot is trying to reach the bottom-right corner of the grid (marked ‘Finish’ in the diagram below).
How many possible unique paths are there?
一个机器人在左上角,在下图中标记为开始,然后这个机器人智能向下或者像右走一个点,这个机器人想要到达右下角的格子,下图中标记finish的格子,有多少可能的路径在这里?
其实这个题也很简单,简单的dp就可,因为我们要算到右下角的位置,所以要先到右下角的前一个位置,因为只能是像右和下移动,所以我们只能是从上或者左方的格子来到当前位置的.所以到达右下角的路径个数就是从左方和上方的和.
大致的过程就如图:
因为只能向右和下走,所以右方和下方全为1,只有一种到达的可能,其他的地方可能是他的上方或者左方到达的
所以,到达此地方的路径数就是f[i-1][j]+f[i]j-1]
所以动态方程就出来了:
f[i][j] = f[i-1][j]+f[i]j-1];
代码:
class Solution {
public:
int uniquePaths(int m, int n) {
if(m=