class Solution {
public:
	vector<int> maxSlidingWindow(vector<int>& nums, int k) {
		vector<int> ve;
		
		priority_queue<Num> q;
		for (int i = 0; i <= k-2; i++) {
			q.push(Num(i, nums[i]));
		}
		
		int left = 0, right = k - 1;
		for (; right < nums.size(); right++, left++) {
			q.push(Num(right, nums[right]));
			while (q.top().index < left || q.top().index > right) {
				q.pop();
			}
			ve.push_back(q.top().value);
		}
		return ve;
	}
};

# 76. 最小覆盖子串

因为 t 中可以有重复字符,因此不能用数组相等的形式。

map<char, int> mpt;
	if (mpt['a']) {
		cout << "hello " << endl;
	}
	if (mpt['b']) {
		cout << "hello " << endl;
	}
	// 像上面这种判断其实已经将 mpt 的大小增加为 2 了
	if (mpt.find('a') != mpt.end()) {
		cout << "hello " << endl;
	}
    // 上面使用 find 没有改变 size

另外这里是覆盖,从 s 截取出来的子串中可以含有重复字符的,所以使用 map 或者数组相等的方式也不行。

class Solution {
public:
	map<char, int> mpt;
	map<char, int> mps;
	string minWindow(string s, string t) {
		
		for (int i = 0; i < t.length(); i++) {
			mpt[t[i]]++;
		}
		bool isInit = false;
		string res = "";
		if (s.length() < t.length())
			return "";
		int r = 0, l = 0;
		for (; r < s.length(); r++) {
			
			if (mpt.find(s[r]) != mpt.end()) {
				mps[s[r]]++;
				if (check()) {
					while (l <= r) {
						while (mpt.find(s[l]) == mpt.end()) {
							l++;
						}
						if (isInit == false) {
							res = s.substr(l, r - l + 1);
							isInit = true;
						}
						else if(s.substr(l, r - l + 1).length() < res.length())
							res = s.substr(l, r - l + 1);
						mps[s[l++]]--;
						if (check())
							continue;
						else
							break;
					}
					// 假如在满足字符的时候仍然前进,就有可能不能再满足要求了
					// 但是貌似 l 只需要一直自增,直到当前不再满足要求
				}
			}
		}
		return res;
	}
	bool check() {
		for (auto& p : mpt) {
			if (mps[p.first] < p.second) {
				return false;
			}
		}
		return true;
	}
};

上面这个解法会出现下面这个问题:

1710378422210

1710378431306

这里的问题主要解决点是窗口左坐标的缩小,在缩小的时候主要是不在 t 中的字符串的去除,和在 t 中的字符的去除。

class Solution {
public:
	map<char, int> mpt;
	map<char, int> mps;
	string minWindow(string s, string t) {
		
		for (int i = 0; i < t.length(); i++) {
			mpt[t[i]]++;
		}
		bool isInit = false;
		string res = "";
		if (s.length() < t.length())
			return "";
		int r = 0, l = 0;
		for (; r < s.length(); r++) {
			
			if (mpt.find(s[r]) != mpt.end()) {
				mps[s[r]]++;
				if (check()) {
					while (l <= r) {
						while (mpt.find(s[l]) == mpt.end()) {
							l++;
						}
						// 此时 s [l] 必定出现在 mpt 中
						while (l < r && s[l] == s[l + 1] && mps[s[l]] - 1 >= mpt[s[l]]) {
							l++;
							mps[s[l]]--;
						}
						if (isInit == false) {
							res = s.substr(l, r - l + 1);
							isInit = true;
						}
						else if(r-l+1 < res.length())
							res = s.substr(l, r - l + 1);
						mps[s[l++]]--;  // 这里每次只舍弃了一个,能不能增多一点呢?
						if (check())
							continue;
						else
							break;
					}
					// 假如在满足字符的时候仍然前进,就有可能不能再满足要求了
					// 但是貌似 l 只需要一直自增,直到当前不再满足要求
				}
			}
		}
		return res;
	}
	bool check() {
		for (auto& p : mpt) {
			if (mps[p.first] < p.second) {
				return false;
			}
		}
		return true;
	}
};