总结
再接再厉,争取早日上2000分
5234. 移除字母异位词后的结果数组
第一题判断一下上一个位置是否一样的,如果一样的就跳过,否则加入答案,可以排序比较是否相同。
// shiran
#include <bits/stdc++.h>
using namespace std;
#define rep(i, a, n) for (int i = a; i < n; i++)
#define per(i, n, a) for (int i = n - 1; i >= a; i--)
#define sz(x) (int)size(x)
#define fi first
#define se second
#define all(x) x.begin(), x.end()
#define pb push_back
#define mk make_mair
typedef long long ll;
typedef pair<int, int> PII;
const int mod = 1e9+7;
const int N = 200010, M = 300010;
int dx[4] = {-1, 0, 1, 0}, dy[4] = {0, 1, 0, -1};
class Solution {
public:
vector<string> removeAnagrams(vector<string>& words) {
set<string> S;
vector<string> ans;
string p;
for (int i = 0; i < sz(words); i ++ )
{
if (i)
{
string t = words[i];
sort(all(t));
if (t != p) ans.pb(words[i]);
p = t;
}
else
{
ans.pb(words[i]);
p = words[i];
sort(all(p));
}
}
return ans;
}
};
6064. 不含特殊楼层的最大连续楼层数
这道题比较坑的一点是端点可以算进去。因此比较特殊楼层差最大值后,再比较一下端点即可
// shiran
#include <bits/stdc++.h>
using namespace std;
#define rep(i, a, n) for (int i = a; i < n; i++)
#define per(i, n, a) for (int i = n - 1; i >= a; i--)
#define sz(x) (int)size(x)
#define fi first
#define se second
#define all(x) x.begin(), x.end()
#define pb push_back
#define mk make_mair
typedef long long ll;
typedef pair<int, int> PII;
const int mod = 1e9+7;
const int N = 200010, M = 300010;
int dx[4] = {-1, 0, 1, 0}, dy[4] = {0, 1, 0, -1};
class Solution {
public:
int maxConsecutive(int l, int r, vector<int>& v) {
// v.pb(l), v.pb(r);
sort(all(v));
int ans = 0;
rep(i, 0, sz(v) - 1)
{
ans = max(ans, v[i + 1] - v[i] - 1);
}
ans = max(ans, max(v[0] - l, r - v[sz(v) - 1]));
return ans;
}
};
6065. 按位与结果大于零的最长组合
这道题是一道思维题,按位与的本质是比较二进制中1的个数,那么这道题就转化为每一个数第i
位出现了多少个1,返回出现最多的那一位1的个数就是答案。
// shiran
#include <bits/stdc++.h>
using namespace std;
#define rep(i, a, n) for (int i = a; i < n; i++)
#define per(i, n, a) for (int i = n - 1; i >= a; i--)
#define sz(x) (int)size(x)
#define fi first
#define se second
#define all(x) x.begin(), x.end()
#define pb push_back
#define mk make_mair
typedef long long ll;
typedef pair<int, int> PII;
const int mod = 1e9+7;
const int N = 35, M = 300010;
int dx[4] = {-1, 0, 1, 0}, dy[4] = {0, 1, 0, -1};
int a[N];
class Solution {
public:
int largestCombination(vector<int>& v) {
memset(a, 0, sizeof a);
for (auto t: v)
{
int k = 0;
while (t) {
a[k ++ ] += t & 1;
t >>= 1;
}
}
int ans = 0;
rep(i, 0, 32)
ans = max(ans, a[i]);
return ans;
}
};
6066. 统计区间中的整数数目
最后一题也有点思维的味道在里面,其实是区间合并的扩展。用一个集合维护不相交区间的端点,用set排序,每一次插入,其实就是比较跟前后区间交集,每次合并前后的区间即可
时间复杂度: O ( n l o g n ) O(nlogn) O(nlogn)
// shiran
#include <bits/stdc++.h>
using namespace std;
#define rep(i, a, n) for (int i = a; i < n; i++)
#define per(i, n, a) for (int i = n - 1; i >= a; i--)
#define sz(x) (int)size(x)
#define fi first
#define se second
#define all(x) x.begin(), x.end()
#define pb push_back
#define mk make_pair
typedef long long ll;
typedef pair<int, int> PII;
const int mod = 1e9+7;
const int N = 100010, M = 300010;
int dx[4] = {-1, 0, 1, 0}, dy[4] = {0, 1, 0, -1};
class CountIntervals {
set<PII> S;
int k = 0;
public:
CountIntervals() {
S.clear();
k = 0;
}
void add(int l, int r) {
auto p = mk(l, r);
while (true)
{
auto it = S.lower_bound(p);
if (it != S.end() && it->fi <= r) {
k -= (it->se - it->fi + 1);
p.fi = min(p.fi, it->fi);
p.se = max(it->se, p.se);
S.erase(it);
}
else break;
}
auto it = S.lower_bound(p);
if (it != S.begin())
{
it -- ;
if (l <= it->se)
{
k -= (it->se - it->fi + 1);
p.fi = min(p.fi, it->fi);
p.se = max(it->se, p.se);
S.erase(it);
}
}
k += p.se - p.fi + 1;
S.insert(p);
}
int count() {
//for (auto& t : S)
// printf("%d %d\n", t.fi, t.se);
return k;
}
};
/**
* Your CountIntervals object will be instantiated and called as such:
* CountIntervals* obj = new CountIntervals();
* obj->add(left,right);
* int param_2 = obj->count();
*/