LeetCode第 78 场双周赛
LeetCode第 78 场双周赛
5299. 找到一个数字的 K 美丽值
一道简单的模拟题,当时忘了转int的库函数,只能用sstream流来实现了,真香。
class Solution {
public:
int convert(string s){
int res;
stringstream ss(s);
ss >> res;
return res;
}
int divisorSubstrings(int num, int k) {
int res = 0;
string str = to_string(num);
for (int i = 0; i <= str.size() - k; i ++ ) {
int t = convert(str.substr(i, k));
if (t && num % t == 0) res ++ ;
}
return res;
}
};
6067. 分割数组的方案数
简单的前缀和,已经连续两次踩坑,前缀和数组可能会爆int
class Solution {
public:
int waysToSplitArray(vector<int>& nums) {
long long int res = 0;
vector<long long int> s(nums.size() + 10);
long long int len = nums.size();
for (long long int i = 1; i <= len; i ++ ) {
s[i] = s[i - 1] + nums[i - 1];
}
for (long long int i = 0; i < len - 1; i ++ ) {
if (s[i + 1] >= s[len] - s[i + 1]) res ++ ;
}
return res;
}
};
6068. 毯子覆盖的最多白色砖块数
二分的边界问题非常值得注意,一定要考虑无解的情况下(要么一直不成立,要么一直成立),最终值是什么,需不需要特判。手写二分的好处有很多,可以参考之前发的模板,建议手写更灵活处理。
class Solution {
public:
int maximumWhiteTiles(vector<vector<int>>& t, int len) {
ios::sync_with_stdio(0),cin.tie(0), cout.tie(0);
int res = -1;
// 对区间数组t排序
sort(t.begin(), t.end());
// 左区间端点的前缀和数组s
vector<int> s(t.size() + 1);
for (int i = 0; i < t.size(); i ++ ) {
s[i + 1] = s[i] + t[i][1] - t[i][0] + 1;
}
// 枚举从每个端点开始盖
for (int i = 0; i < t.size(); i ++ ) {
int R = t[i][0] + len - 1; // 左区间最大的值-1
// 找到区间内>R的第一个值
int l = i, r = t.size();
while (l < r) {
int mid = l + r >> 1;
if (t[mid][1] - t[i][0] >= len) {
r = mid;
} else l = mid + 1;
}
// 没找到后,最终结果一定是右端点+1,不影响前缀和
int sum = s[l] - s[i];
// 如果找到了,并且有剩余
if (l < t.size() && t[l][0] <= R)
{
sum += (R - t[l][0] + 1);
}
res = max(res, sum);
}
return res;
}
};

浙公网安备 33010602011771号