// 朴素思想 TLE classSolution { public: staticconstint N = 25; staticconstint M = 1e5 + 10; int s[M][N] = {0};
boolcheck(int l, int r) { for(int i = 1; i <= 21; i ++) { int t = s[r][i] - s[l - 1][i]; if(t % 2) returnfalse; } returntrue; } longlongbeautifulSubarrays(vector<int>& nums){ int n = nums.size();
for(int i = 0; i < n;i ++) { int num = nums[i]; for(int j = 0; j <= 20; j ++) { int k = num >> j & 1; if(k) s[i + 1][j + 1] += 1; } }
for(int i = 1; i <= n; i ++) for(int j = 1; j <= 21; j ++) s[i][j] += s[i - 1][j];
longlong res = 0; for(int i = 0;i < n ;i ++) for(int j = i; j < n; j ++ ) if(check(i + 1, j + 1)) res ++; return res; } };
//利用哈希表来寻找左侧出现过的值 * 降低时间复杂度 classSolution { public: longlongbeautifulSubarrays(vector<int>& nums){ int n = nums.size(); vector<int> s(n + 1); //异或和 通过异或来简化统计二进制下不同位1个数的奇偶性 for(int i = 1; i <= n ; i ++) { s[i] = s[i - 1] ^ nums[i - 1]; } unordered_map<int, int> h;
longlong res = 0; for(auto c: s) { cout << c <<endl; // 此处表示异或和下的间隔,先+=再++ res += h[c]++; } return res; } };
classSolution { public: intminSubarray(vector<int>& nums, int p){ int n = nums.size(); int k = 0; for(auto c : nums) { k = (k + c) % p; // cout << k <<endl; } if(!k) return0; int ans = n; unordered_map<int, int> h; int y = 0; //坐标保持一致 h[0] = -1; for(int i = 0; i < n;i ++) { h[y] = i; y = (y + nums[i]) % p; if(h.count((y - k + p) % p)) { //注意idx坐标位置、举例说明 int idx = h[(y - k + p) % p] - 1; if(ans == -1 || ans > i - idx) ans = i - idx; } } //表示如果全部删除才能满足结果 返回-1 return ans == n ? -1 : ans;
} };
3.连续的子数组和 523
原题:
给你一个整数数组 nums 和一个整数 k ,编写一个函数来判断该数组是否含有同时满足下述条件的连续子数组:
子数组大小 至少为 2 ,且
子数组元素总和为 k 的倍数。
如果存在,返回 true ;否则,返回 false 。
如果存在一个整数 n ,令整数 x 符合 x = n * k ,则称 x 是 k 的一个倍数。0 始终视为 k 的一个倍数。 注意n可以为0