思路:html
這題應該不止一種解法,其中的一種能夠看做是leetcode85http://www.javashuo.com/article/p-qwyuleqr-hs.html的增強版:c++
首先對於每一行,分別使用滑動窗口法將這一行劃分紅符合題目定義的若干合法子段s1, s2, s3, ...。對於每一段si,從起點到終點分別將每一個元素分別編號爲1, 2, 3, ..., |si|。spa
例如:code
2 2 4 4 20 8 3 3 3 12 6 6 3 3 3 1 6 8 6 4
能夠轉化成htm
1 2 1 2 1 1 1 2 3 1 1 2 1 2 3 1 1 1 1 1
接下來就能夠將此矩陣轉置,使用leetcode85的思路進行計算了:blog
1 2 1 2 1 1 1 2 3 1 1 2 1 2 3 1 1 1 1 1
實現:ci
1 #include <bits/stdc++.h> 2 using namespace std; 3 const int N = 305; 4 int a[N][N], b[N][N]; 5 int main() 6 { 7 int T, r, c, k; 8 cin >> T; 9 for (int t = 1; t <= T; t++) 10 { 11 memset(b, 0x3f, sizeof b); 12 cin >> r >> c >> k; 13 for (int i = 0; i < r; i++) 14 for (int j = 0; j < c; j++) 15 cin >> a[i][j]; 16 for (int i = 0; i < r; i++) 17 { 18 map<int, int> mp; 19 int f = 0, s = 0; 20 while (f < c) 21 { 22 while (f < c) 23 { 24 if (!mp.count(a[i][f])) mp[a[i][f]] = 0; 25 mp[a[i][f]]++; 26 if (mp.rbegin()->first - mp.begin()->first > k) break; 27 b[i][f] = f - s + 1; 28 f++; 29 } 30 while (s < f && mp.rbegin()->first - mp.begin()->first > k) 31 { 32 if (mp[a[i][s]] == 1) mp.erase(a[i][s]); 33 else mp[a[i][s]]--; 34 s++; 35 } 36 b[i][f] = f - s + 1; 37 f++; 38 } 39 } 40 int ans = 0; 41 for (int j = 0; j < c; j++) 42 { 43 stack<pair<int, int>> sta; 44 vector<int> pre; 45 for (int i = 0; i < r; i++) 46 { 47 while (sta.size() && sta.top().first >= b[i][j]) sta.pop(); 48 if (!sta.empty()) pre.push_back(sta.top().second + 1); 49 else pre.push_back(0); 50 sta.push(make_pair(b[i][j], i)); 51 } 52 while (sta.size()) sta.pop(); 53 for (int i = r - 1; i >= 0; i--) 54 { 55 while (sta.size() && sta.top().first >= b[i][j]) sta.pop(); 56 if (!sta.empty()) ans = max(ans, (sta.top().second - pre[i]) * b[i][j]); 57 else ans = max(ans, b[i][j] * (r - pre[i])); 58 sta.push(make_pair(b[i][j], i)); 59 } 60 } 61 cout << "Case #" << t << ": " << ans << endl; 62 } 63 return 0; 64 }