力扣-491-递增子序列

起因是我做笔试,要写出所有子序列并做条件判断,我以为是回溯改一改,但事实上完全不是这样的

直达链接

主要是1,利用二进制序列枚举快速生成所有的可能子序列,然后利用哈希算法对数组去重(这个哈希算法可以直接背)

	vector<int> temp;
	vector<vector<int>> res;
	unordered_set<int> set;
	int n;

	void findSubsequences(int mask, vector<int>& nums) {
		temp.clear();
		for (int i = 0; i < n; i++) {
			// 就是二进制位为1的才插入临时数组
			// 从左右哪边开始无所谓,但是位运算是从右边开始的
			if (mask & 1) temp.push_back(nums[i]);
			mask >>= 1;
		}
	}

	int getHash(int base, int mod) {
		int hashValue = 0;
		for (int i : temp) {
			hashValue = 1LL * hashValue * base % mod + (i + 101);
			hashValue %= mod;
		}
	}

	bool check() {
                // 我不理解为什么这里越界报空指针,按理来说应该更不容易空才对
		// for (int i = 0; i < temp.size() - 1; i++) if (temp[i] > temp[i + 1]) return false;
		for (int i = 1; i < temp.size(); i++) if (temp[i] < temp[i - 1]) return false;
		// 本来是return true,但是依题意一个元素的也不算
		return temp.size() >= 2;
	}

	vector<vector<int>> findSubsequences(vector<int>& nums) {
		n = nums.size();
		// 这个位运算构造二进制序列真的妙
		for (int i = 0; i < (1 << n); ++i) {
			findSubsequences(i, nums);
			// 检查temp数组是否有重复的
			// 通过为每个数组生成一个hash码
			int hashValue = getHash(263, int(1E9) + 7);
			// 这里,set没有count()方法,原来查找是这么用的
			if (check() && set.find(hashValue) == set.end()) {
				res.push_back(temp);
				set.emplace(hashValue);
			}
		}
		return res;
	}
};

但是好像还是不是我想要的,我想要的是全排列+所有子排列,不是子序列啊

posted @ 2022-09-29 16:44  YaosGHC  阅读(30)  评论(0)    收藏  举报