leetcode 2024.03.02 第 125 场双周赛 题解
- 超过阈值的最少操作数 I
简单题
class Solution {
public:
int minOperations(vector<int>& nums, int k) {
int ans = 0;
for(int i: nums) {
if(i<k){
++ans;
}
}
return ans;
}
};
- 超过阈值的最少操作数 II
简单题 会用优先队列就行 注意数据范围
class Solution {
public:
int minOperations(vector<int>& nums, int k) {
priority_queue <long long,vector<long long>,greater<long long> > q;
for(int i: nums){
q.push(i);
}
int ans = 0;
while(q.top()<k){
long long x = q.top();
q.pop();
long long y = q.top();
q.pop();
q.push(x*2+y);
++ans;
}
return ans;
}
};
- 在带权树网络中统计可连接服务器对数目
困难题 周赛过程中思路想到了但是没打出来
分两部分
a.枚举根 DFS ,计算符合点的个数
b.乘法原理 假设枚举到点C 那么C左边符合条件的点的数量 * C右边符合条件的点的数量 = 可连接的对数目
一开始左边是0,枚举一次后,右边合并到左边,再遍历更右边。(这句话有点抽象,但大概就是这么个意思)
类似题 2867. 统计树中的合法路径数目
class Solution {
public:
vector<int> countPairsOfConnectableServers(vector<vector<int>>& edges, int signalSpeed) {
int n = edges.size() + 1;
vector<vector<pair<int,int>>> g(n);
for(auto edge:edges){
int u = edge[0], v =edge[1], w=edge[2];
g[u].push_back({v,w});
g[v].push_back({u,w});
}
function<int(int,int,int)> dfs = [&](int cur,int fa,int dis) -> int {
int ans = dis % signalSpeed == 0 ? 1 : 0;
for(pair<int,int> i:g[cur]){
if(i.first == fa) continue;
ans += dfs(i.first,cur,dis+i.second);
}
return ans;
};
vector<int>count(n);
for(int i=0;i<n;++i){
int sum = 0;
for(pair<int,int> j:g[i]){
int temp = dfs(j.first,i,j.second);
count[i] += sum*temp;
sum+=temp;
}
}
return count;
}
};
- 最大节点价值之和
中等题
两个关键点:
a.重复异或等于自己
b.因为是树且无限操作,所以相当于可以任意找两个点异或(贪心找增加最大的两个),其余点的值不变
class Solution {
public:
long long maximumValueSum(vector<int>& nums, int k, vector<vector<int>>& edges) {
int n = nums.size();
vector<int>v;
long long sum = accumulate(nums.begin(),nums.end(),0ll);
for(int i:nums){
v.push_back((i^k)-i);
}
sort(v.begin(),v.end(), [](const int x,const int y) {
return x>y;
});
for(int i=0;i<n-1; i+=2){
int temp = v[i] + v[i+1];
if (temp<=0){
break;
}
sum+=temp;
}
return sum;
}
};