363. Max Sum of Rectangle No Larger Than K

来源:互联网 发布:历史停车数据分析 编辑:程序博客网 时间:2024/06/06 02:50

Given a non-empty 2D matrix matrix and an integer k, find the max sum of a rectangle in thematrix such that its sum is no larger than k.

Example:

Given matrix = [  [1,  0, 1],  [0, -2, 3]]k = 2

The answer is 2. Because the sum of rectangle [[0, 1], [-2, 3]] is 2 and 2 is the max number no larger than k (k = 2).

Note:

  1. The rectangle inside the matrix must have an area > 0.
  2. What if the number of rows is much larger than the number of columns?

Credits:
Special thanks to @fujiaozhu for adding this problem and creating all test cases.

Subscribe to see which companies asked this question.



看solution提示做的。。求矩阵中各个矩形的和的最大值(不超过k的,超过k的不算)。看solution的提示说类似这道题的解法,求数组中各子序列的和(也是不超过k的)的最大值,方法是求所有[0,i]的和(记为sum[0,i]),然后[i,j]子序列的和就是sum[0,j]-sum[0,i],为了更有效率累加到j时,用二分法搜索前面所有sum[0,i],找出最接近(sum[0,j]-k)的值,准确点说是比(sum[0,j]-k)大的最小值,因为要满足sum[0,j]-sum[0,i]<=k,即sum[0,j]-k<=sum[0,i]。实现这一点,直接用lower_bound做。

这道题是矩阵形式的变形。为了遍历所有的矩形,对于每个矩形,需要平行和竖直的两条线。如下图所示:

首先定下竖直的两条,也就是对列进行遍历,两层的循环。为什么是列先。。因为题目说行比列多的多。为了转化成数列形式的问题,可以看成当前列与列之间的每一行是一个元素,计算每一行的和(这里说的是夹在两列中间的部分),这样就化成了上面说的数组形式的问题。


代码:

class Solution{public:int maxSumSubmatrix(vector<vector<int> >& matrix, int k){int m = matrix.size(); if(m == 0) return 0;int n = matrix[0].size(); if(n == 0) return 0;int res = INT_MIN;for(int col = 0; col < n; ++col){vector<int> row_sums(m, 0);for(int i = col; i < n; ++i){for(int row = 0; row < m; ++row){row_sums[row] += matrix[row][i];}int tmp_res = INT_MIN, accum = 0;set<int> accums; accums.insert(0);for(auto num:row_sums){accum += num;auto iter = accums.lower_bound(accum - k);if(iter != accums.end()) tmp_res = max(tmp_res, accum - *iter);accums.insert(accum);}res = max(res, tmp_res);}}return res;}};



0 0
原创粉丝点击