题目描述:
你的面前有一堵方形的、由多行砖块组成的砖墙。 这些砖块高度相同但是宽度不同。你现在要画一条自顶向下的、穿过最少砖块的垂线。
砖墙由行的列表表示。 每一行都是一个代表从左至右每块砖的宽度的整数列表。
如果你画的线只是从砖块的边缘经过,就不算穿过这块砖。你需要找出怎样画才能使这条线穿过的砖块数量最少,并且返回穿过的砖块数量。
你不能沿着墙的两个垂直边缘之一画线,这样显然是没有穿过一块砖的。
示例:
输入: [[1,2,2,1], [3,1,2], [1,3,2], [2,4], [3,1,2], [1,3,1,1]] 输出: 2 解释:
提示:
- 每一行砖块的宽度之和应该相等,并且不能超过 INT_MAX。
- 每一行砖块的数量在 [1,10,000] 范围内, 墙的高度在 [1,10,000] 范围内, 总的砖块数量不超过 20,000。
解题思路:
1.依次求出每一个数组的前n项元素和(n依次等于1,2,...,数组长度-1)
例,由数组 [1,2,2,1] 我们可以得到值: 1 3(2+1=3) 5(1+2+2)
由数组 [3,1,2] 我们可以得到值: 3 4(3+1)
2.对于每一次求得的累加值存入一个map中,key表示求得的累加值(1 3 5),value值表示累加值出现的次数
把上面例子中求出的累加值存入map中则可以得到 (1,1) (3,2) (4,1) (5,1)
示例最终得到的map为(1,3) (2,1) (3,3) (4,4) (5,2)
3.穿过的最少砖块数=数组总行数-max(value)
遍历map中的value值,可以得到max(value)为 4,所以最终求得的穿过的最少砖块数为 2 (6-4=2)
参考代码:
class Solution
{
public:
int leastBricks(vector<vector<int>>& wall)
{
map<int,int> m;
for (int i = 0; i < wall.size(); i++)
{
int sum=0;
for(int j = 0; j < (wall[i].size())-1; j++)
{
sum+=wall[i][j];
if(m.count(sum)>0)
m[sum]+=1;
else
m[sum]=1;
}
}
int max=0;
map<int, int>::iterator iter;
for(iter = m.begin(); iter !=m.end(); iter++)
{
if(iter->second>max)
max=iter->second;
}
return wall.size()-max;
}
};