2025 ICPC Gran Premio de Mexico 3ra Fecha
A题
签到
cpp
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N = 1e6+5;
ll n;
ll a[N];
int main() {
ios_base::sync_with_stdio(false),cin.tie(0),cout.tie(0);
cin>>n;
ll sum = 0;
for(int i=0;i<n;i++) {
cin>>a[i];
sum+=a[i];
}
ll t = n;
while (t >= 1) {
if (sum % t == 0) {
cout<<n - t <<'\n';
return 0;
}
t--;
}
return 0;
}
二、K题
分类讨论
cpp
#include<bits/stdc++.h>
#define int long long
using namespace std;
void solve() {
int a,b,c,d;
cin>>a>>b>>c>>d;
if (d <= a) {
cout<<"0\n";
return;
}
if (d > a && d <= b) {
int ans = d - max(a,c);
cout<<ans<<"\n";
return;
}
if (d > b) {
if (c <= a) {cout<<b - a <<'\n'; return;}
if (c > a && c <= b){cout << b - c <<'\n'; return;}
if (c > b){cout << "0\n";return;}
}
}
signed main() {
ios_base::sync_with_stdio(false),cin.tie(0),cout.tie(0);
int T;
cin>>T;
while(T--) {
solve();
}
return 0;
}
三、B题
贡献法
结论就是i * (n - i + 1) * a[i]是每个值的贡献。
cpp
#include<bits/stdc++.h>
const int N = 1e5;
#define int long long
using namespace std;
int a[N];
void solve() {
int n;
cin>>n;
for(int i=1;i<=n;i++) {
cin>>a[i];
}
int ans = 0;
for(int i=1;i<=n;i++) {
ans += i * (n - i + 1) * a[i];
}
cout<<ans<<'\n';
}
signed main() {
ios_base::sync_with_stdio(false),cin.tie(0),cout.tie(0);
int T = 1;
// cin>>T;
while(T--) {
solve();
}
return 0;
}
四、J题
线段树 + 尼姆博弈
cpp
#include <bits/stdc++.h>
using namespace std;
const int MAX_N = 1e6 + 5;
long long a[MAX_N];
long long sum_xor[MAX_N << 2];
//建树
void build(int l, int r, int rt) {
if (l == r) {
sum_xor[rt] = a[l];
return;
}
int mid = (l + r) >> 1;
build(l, mid, rt << 1);
build(mid + 1, r, rt << 1 | 1);
sum_xor[rt] = sum_xor[rt << 1] ^ sum_xor[rt << 1 | 1];//up函数
}
void update(int k, long long x, int l, int r, int rt) {
if (l == r) {//注意:这里是叶子节点异或值等于本身,加上后仍然是其异或值
sum_xor[rt] += x;
return;
}
int mid = (l + r) >> 1;
if (k <= mid) {
update(k, x, l, mid, rt << 1);
} else {
update(k, x, mid + 1, r, rt << 1 | 1);
}
sum_xor[rt] = sum_xor[rt << 1] ^ sum_xor[rt << 1 | 1];//up函数
}
//范围查询
long long query(int L, int R, int l, int r, int rt) {
if (L <= l && r <= R) {
return sum_xor[rt];
}
int mid = (l + r) >> 1;
long long res = 0;
if (L <= mid) {
res ^= query(L, R, l, mid, rt << 1);
}
if (R > mid) {
res ^= query(L, R, mid + 1, r, rt << 1 | 1);
}
return res;
}
int main() {
ios::sync_with_stdio(false);
cin.tie(0);
cout.tie(0);
int n, q;
scanf("%d%d", &n, &q);
for (int i = 1; i <= n; ++i) {
scanf("%lld", &a[i]);
}
build(1, n, 1);
char op[2];
while (q--) {
scanf("%s", op);
if (op[0] == 'P') {
int l, r;
scanf("%d%d", &l, &r);
long long xor_sum = query(l, r, 1, n, 1);
if (xor_sum == 0) {
printf("JUAN\n");
} else {
printf("FRANK\n");
}
} else if (op[0] == 'R') {
int k;
long long x;
scanf("%d%lld", &k, &x);
update(k, x, 1, n, 1);
}
}
return 0;
}
五、G题
经典精度问题,一定要想到要将除法转换为乘法,转换后因为数值较大,可以转为log,乘变加。
cpp
#include<bits/stdc++.h>
#define int long long
using namespace std;
typedef long double ld;
void solve() {
int h1, h2, b;
cin >> h1 >> h2 >> b;
ld t = logl(ld (h1) / h2);
ld r = logl(ld (b)) - logl(ld (b-1));
ld ans = t / r;
int res = int32_t(ceil(ans));
cout << res << '\n';
}
signed main() {
ios_base::sync_with_stdio(false), cin.tie(NULL), cout.tie(NULL);
int T;
cin >> T;
while (T--) {
solve();
}
return 0;
}