枚举矩阵两个端点,时间O(N*N*M*M),差点超时:
class Solution {
public:
int numSubmatrixSumTarget(vector<vector<int>>& matrix, int target) {
int N = matrix.size();
int M = matrix[0].size();
int dp[N+1][M+1];
memset(dp,0,sizeof(dp));
for(int i=1;i<=N;i++){
for(int j=1;j<=M;j++){
dp[i][j] = dp[i-1][j] + matrix[i-1][j-1];
}
}
int ans = 0;
// 枚举左上角
for(int i=1;i<=N;i++){
for(int j=1;j<=M;j++){
// 枚举右下角
for(int x=i;x<=N;x++){
int sum = 0;
for(int y=j;y<=M;y++){
sum += dp[x][y] - dp[i-1][y];
if(sum == target) ans++;
}
}
}
}
return ans;
}
};
哈希降时间复杂度,时间O(N*N*M),貌似也没快多少,快了1/3:
class Solution {
public:
int numSubmatrixSumTarget(vector<vector<int>>& matrix, int target) {
int N = matrix.size();
int M = matrix[0].size();
int dp[N+1][M+1];
memset(dp,0,sizeof(dp));
for(int i=1;i<=N;i++){
for(int j=1;j<=M;j++){
dp[i][j] = matrix[i-1][j-1] +
dp[i-1][j] + dp[i][j-1] - dp[i-1][j-1];
}
}
int ans = 0;
// 枚举起始行
for(int i=1;i<=N;i++){
// 枚举结束行
for(int j=i;j<=N;j++){
unordered_map<int,int> mp;
// 横扫列
for(int k=1;k<=M;k++){
int T = dp[j][k] - dp[i-1][k];
ans += (T == target?1:0);
ans += mp[T-target];
mp[T]++;
}
}
}
return ans;
}
};