classSolution { public: intfindUnsortedSubarray(vector<int>& nums){ /* 单调栈(vector模拟)*/ int n = nums.size(); int l = n - 1, r = 0; vector<int> stk; //从左往右递增栈,找到不符合自己位置的最小元素的坐标 for (int i = 0; i < n; i++) { while (stk.size() && nums[stk.back()] > nums[i]) { l = min(l, stk.back()); stk.pop_back(); } stk.push_back(i); } stk.clear(); //从右往左递减栈,找到不符合自己位置的最大元素的坐标 for (int i = n - 1; i >= 0; i--) { while (stk.size() && nums[stk.back()] < nums[i]) { r = max(r, stk.back()); stk.pop_back(); } stk.push_back(i); } //r - l > 0时所需排序长度为r - l + 1, r - l <= 0时整体已经有序 return r - l > 0 ? r - l + 1 : 0; } };
classSolution { public: inttrap(vector<int>& height){ int ans = 0; stack<int> stk; int n = height.size(); for (int i = 0; i < n; ++i) { while (!stk.empty() && height[i] > height[stk.top()]) { int top = stk.top(); stk.pop(); if (stk.empty()) { break; } int left = stk.top(); int currWidth = i - left - 1; int currHeight = min(height[left], height[i]) - height[top]; ans += currWidth * currHeight; } stk.push(i); } return ans; } };
动态规划
classSolution { public: int res = 0; // 找到每一列左边最高的墙和右边最高的墙 inttrap(vector<int>& height){ int n = height.size(); vector<vector<int>> dp(n, vector<int>(2, 0)); // dp[0][0] = 0; 左边最高的墙 // dp[n - 1][1] = 0; 右边最高的墙 for(int i = n - 2; i >= 0; i --){ dp[i][1] = max(dp[i + 1][1], height[i + 1]); } for(int i = 1; i < n; i ++){ dp[n - i - 1][1] = max(dp[n - i][1], height[n - i]); dp[i][0] = max(dp[i - 1][0], height[i - 1]); res += min(dp[i][0], dp[i][1]) > height[i] ? min(dp[i][0], dp[i][1]) - height[i] : 0; } return res; } };
for(int i = 0; i < heights.size(); i ++){ while(!s.empty() && heights[i] < heights[s.top()]){ // 2进栈 6,5被弹出 //6: cur = 4; left = 4; right = 4; (right - left + 1) = 1 //5: cur = 3; left = 3; right = 4; (right - left + 1) = 2 int cur = s.top(); s.pop(); int left = s.top() + 1; int right = i - 1; res = max(res, (right - left + 1) * heights[cur]); } s.push(i); } return res; } };