GPLT-全国赛2026
总体来说还是非常简单的,最终的情况是 L1,L2 满分,L3-1 30 分, L3-2 12 分, L3-3 10 分。
L1
全都是水题。
L1-1
python
print('Building the Future, One Line of Code at a Time.')L1-2
python
n = int(input())
print(n * 15)L1-3
python
a, b = map(int, input().split())
print(b - a)
if (b - a > 250):
print('jiu ting tu ran de...')
elif b - a <= 0:
print('hai sheng ma?')
else:
print('nin tai cong ming le!')L1-4
cpp
#include <iostream>
using namespace std;
int main() {
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
int n;
cin >> n;
int res = 0;
for (int i = 1; i <= n; ++i) {
int t;
cin >> t;
if (t < 1700) res++;
}
cout << res << endl;
return 0;
}L1-5
cpp
#include <iostream>
#include <map>
using namespace std;
map<int, int> mp;
int main() {
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
int n;
cin >> n;
for (int i = 1; i <= n; ++i) {
int a, b;
cin >> a >> b;
if (mp.find(a) != mp.end()) {
mp[a] |= b;
}
else mp[a] = b;
}
bool f = true;
for (auto [a, b] : mp) {
if (b == 0) {
if (f) cout << a;
else cout << ' ' << a;
f = false;
}
}
if (f) cout << "NONE" << endl;
return 0;
}L1-6
cpp
for _ in range(11):
print(len(input()), end='')L1-7
python
n = int(input())
a = list(map(int, input().split()))
mx, mn, avg = max(a), min(a), sum(a) // n
print(mx, mn, avg)
l = [(i + 1) for i in range(n) if a[i] > avg * 2]
if l:
print(' '.join(str(i) for i in l))
else:
print('Normal')L1-8
当时出了一小会儿事故,需要注意边界,防止 RE。
cpp
#include <iostream>
#include <algorithm>
using namespace std;
int main() {
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
int t;
cin >> t;
string s;
cin >> s;
while (t--) {
int op;
cin >> op;
if (op == 1) {
string tt;
cin >> tt;
int cnt = 0;
bool f = true;
if (s.length() < tt.length()) {
cout << -1 << endl;
continue;
}
for (int i = 0; i < s.length() - tt.length() + 1; ++i) {
if (s.substr(i, tt.length()) == tt) {
if (f) cout << i, f = false;
else cout << ' ' << i;
cnt++;
}
if (cnt == 3) break;
}
if (f) cout << -1 << endl;
else cout << endl;
}
else if (op == 2) {
int p;
string tt;
cin >> p >> tt;
s.insert(p, tt);
cout << s << endl;
}
else {
int l, r;
cin >> l >> r;
reverse(s.begin() + l, s.begin() + r + 1);
cout << s << endl;
}
}
return 0;
}L2
L2-1
直接开两个数组模拟即可,非常的简单。
cpp
#include <iostream>
#include <algorithm>
#include <vector>
using namespace std;
vector<pair<int, int>> a, b;
bool f = true;
void print(int a) {
if (f) cout << a + 1, f = false;
else cout << ' ' << a + 1;
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
int n, t;
cin >> n >> t;
a.resize(n);
for (int i = 0; i < n; ++i) {
cin >> a[i].first;
a[i].second = i;
}
int curt = 0;
while (!a.empty()) {
for (auto &[aa, bb] : a) {
if (aa <= t) print(bb);
else b.emplace_back(aa, bb), curt += aa;
}
if (b.empty()) break;
t = curt / b.size();
curt = 0;
a = b;
b.clear();
reverse(a.begin(), a.end());
}
cout << endl;
return 0;
}L2-2
二分查找,直接用 upper_bound 就解决了。
cpp
#include <iostream>
#include <algorithm>
#include <vector>
using namespace std;
int main() {
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
int n;
cin >> n;
vector<pair<int, int>> a(n);
int mx = 0;
for (int i = 0; i < n; ++i) {
cin >> a[i].first;
a[i].second = i + 1;
mx = max(a[i].first, mx);
}
sort(a.begin(), a.end());
bool f = true;
for (auto [aa, bb] : a) {
if (aa == mx) {
if (f) cout << bb, f = false;
else cout << ' ' << bb;
}
}
cout << endl;
int t;
cin >> t;
while (t--) {
int q;
cin >> q;
auto p = upper_bound(a.begin(), a.end(), make_pair(q, 0));
if (p == a.end()) cout << 0 << endl;
else cout << p->second << endl;
}
return 0;
}L2-3
树形 DP,就是找根到每个叶子路径上的最小值,然后把最大的几个输出。
cpp
#include <iostream>
#include <algorithm>
#include <vector>
#include <cstring>
using namespace std;
const int N = 100010;
vector<pair<int, int>> ed[N];
int dis[N], deg[N];
void dfs(int x) {
for (auto [y, val] : ed[x]) {
dis[y] = min(val, dis[x]);
dfs(y);
}
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
int n;
cin >> n;
for (int i = 1; i < n; ++i) {
int fa, val;
cin >> fa >> val;
ed[fa].emplace_back(i, val);
deg[fa]++;
}
dis[0] = 0x3f3f3f3f;
dfs(0);
int mx = 0;
for (int i = 0; i < n; ++i) {
if (deg[i] == 0) mx = max(mx, dis[i]);
}
cout << mx << endl;
bool f = true;
for (int i = 0; i < n; ++i) {
if (dis[i] == mx && deg[i] == 0) {
if (f) cout << i, f = false;
else cout << ' ' << i;
}
}
cout << endl;
return 0;
}L2-4
直接按要求搜即可,非常简单。
cpp
#include <iostream>
#include <algorithm>
#include <vector>
#include <cstring>
using namespace std;
const int N = 10010;
vector<pair<int, int>> ed[N];
int dis[N], deg[N];
vector<int> seq;
bool vis[N];
void print_seq() {
bool f = true;
for (auto x : seq) {
if (f) cout << x, f = false;
else cout << "->" << x;
}
cout << endl;
seq.clear();
}
void dfs(int x) {
if (vis[x]) return;
seq.emplace_back(x);
vis[x] = true;
if (ed[x].empty()) return;
for (auto [_, y] : ed[x]) {
if (!vis[y]) {
dfs(y);
return;
}
}
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
int n, m;
cin >> n >> m;
for (int i = 1; i <= m; ++i) {
int x, y, z;
cin >> x >> y >> z;
ed[x].emplace_back(-z, y);
}
for (int i = 1; i <= n; ++i) sort(ed[i].begin(), ed[i].end());
int q;
cin >> q;
while (q--) {
int x;
cin >> x;
memset(vis, 0, sizeof(vis));
dfs(x);
print_seq();
}
return 0;
}L3
依然是第一个送分,后两个不会。
L3-1
开两个优先队列,一个放老人,一个放其他人,然后按要求模拟。
cpp
#include <iostream>
#include <algorithm>
#include <queue>
#include <cstring>
using namespace std;
const int N = 10010;
struct Node {
int t1, t2, age;
string id;
bool operator <(const Node &a) const {
return t2 > a.t2;
}
} a[N];
bool vis[N];
int b[N];
priority_queue<Node> q1, q2;
int main() {
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
int n;
cin >> n;
for (int i = 1; i <= n; ++i) {
cin >> a[i].t1 >> a[i].t2 >> a[i].id >> a[i].age;
b[a[i].t2] = i;
}
for (int i = 1, j = 1, tt = 0; tt < n; ++i) {
if (i <= n && a[b[i]].t1 <= i && !vis[a[b[i]].t2]) {
vis[a[b[i]].t2] = true;
// cout << a[b[i]].t2 << endl;
cout << i << ' ' << a[b[i]].id << endl;
tt++;
}
else {
while (j <= n && a[j].t1 <= i) {
if (a[j].age >= 80) q2.emplace(a[j]);
else q1.emplace(a[j]);
j++;
}
while (!q1.empty() && vis[q1.top().t2]) q1.pop();
while (!q2.empty() && vis[q2.top().t2]) q2.pop();
// cout << vis[q2.top().t2] << endl;
// exit(0);
if (!q2.empty()) {
cout << i << ' ' << q2.top().id << endl;
vis[q2.top().t2] = true;
q2.pop();
tt++;
}
else if (!q1.empty()) {
cout << i << ' ' << q1.top().id << endl;
vis[q1.top().t2] = true;
q1.pop();
tt++;
}
}
}
return 0;
}L3-2
大概率是网络流,什么点覆盖独立集之类的,大概率会补。
先贴个暴力的代码了。
WARNING
这是个 12 分的暴力的代码!
cpp
#include <iostream>
#include <cstring>
using namespace std;
const int N = 100010;
int a[N][2];
int b[N * 2];
int res, n;
void dfs(int x, int t) {
if (t > res) return;
if (x == n) {
res = t;
return;
}
if (b[a[x][0]] || b[a[x][1] + n]) dfs(x + 1, t);
else {
b[a[x][0]] = 1;
dfs(x + 1, t + 1);
b[a[x][0]] = 0;
b[a[x][1] + n] = 1;
dfs(x + 1, t + 1);
b[a[x][1] + n] = 0;
}
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
int T;
cin >> T;
while (T--) {
cin >> n;
res = n;
for (int i = 0; i < n; ++i) cin >> a[i][0] >> a[i][1];
dfs(0, 0);
cout << res + n << endl;
}
return 0;
}L3-3
我直接打暴力了高达 10 分。
WARNING
这是个 10 分的暴力的代码。
cpp
#include <iostream>
#include <algorithm>
#include <queue>
#include <cstring>
using namespace std;
int res;
vector<int> a, b;
void dfs(int x) {
if (x == b.size()) {
bool f = true;
for (int i = 0; i < b.size(); ++i) {
if (a[b[i]] != b[a[i]]) {
f = false;
break;
}
}
if (f) res++;
return;
}
for (int i = 0; i < b.size(); ++i) {
b[x] = i;
dfs(x + 1);
}
}
int main() {
ios::sync_with_stdio(0);
cin.tie(0), cout.tie(0);
int T;
cin >> T;
while (T--) {
int n;
cin >> n;
a = vector<int>(n), b = vector<int>(n);
for (auto &i : a) cin >> i, i--;
for (int i = 0; i < n; ++i) b[i] = i;
int t = 1;
for (int i = 1; i <= n; ++i) t *= i;
res = 0;
dfs(0);
cout << res << endl;
}
return 0;
}