吉首大学第十届“新星杯”大学生程序设计大赛摸鱼记(有代码了!)

前几天在u裙看到这个比赛,发现有u盘,就报名了(
upd: 代码来了

正赛

看题
不记得做的顺序了,按题目顺序讲吧(

A

好像是个式子题,过会再搞
最后直接打了个表,oeis一波过
交了一发罚时,用了傻逼的pow T了一发(
好像吊打std了?

#include <bits/stdc++.h>
#define ll long long
using namespace std;
int f(ll n) {
    return 63 - __builtin_clzll(n);
}
int main() {
    int t;
    scanf("%d", &t);
    while (t--) {
        ll n, ans, k;
        scanf("%lld", &n);
        ans = n * (n - 1) / 2;
        n--;
        k = floor(f(n + 2));
        ans += (n + 2) * (1ll << k) - (2 * (1ll << k) * (1ll << k) + 1) / 3;
        printf("%lld\n", ans);
    }
    return 0;
}

B

交了两发shit
发现看错题了
重新思考一波发现子集枚举就好(
发现复杂度小于\(O(2^{20}t)\)
一发A了

#include <bits/stdc++.h>
using namespace std;
int n, a[11], val[2000];
bool fl[1000];
int main() {
    int t;
    cin >> t;
    while (t--) {
        int mx = 0, cnt = 0;
        cin >> n;
        for (int i = 0; i < n; i++)
            cin >> a[i];
        if (n <= 1) {
            cout << "0 0" << endl;
            continue;
        }
        memset(fl, 0, sizeof(fl));
        memset(val, 0, sizeof(val));
        int S = (1 << n) - 1;
        for (int s = 0; s <= S; s++)
            for (int i = 0; i < n; i++) 
                if (s >> i & 1)
                    val[s] += a[i];
        for (int s1 = 0; s1 <= S; s1++)
            int s2 = S ^ s1;
            for (int ss2 = s2; ss2; ss2 = (ss2 - 1) & s2)
                if (val[s1] == val[ss2]) {
                    int x = val[s1];
                    if (!fl[x]) {
                        fl[x] = 1;
                        mx = max(mx, x);
                        cnt++;
                    }
                }
        cout << cnt << ' ' << mx << endl;
    }
    return 0;
} 

C

简单题,满足a+b=n即可

#include <bits/stdc++.h> 
using namespace std;
int main() {
    int n;
    cin >> n;
    cout << 1 << ' ' << n - 1 << endl;
    return 0;
}

D

搞个栈记录一下当前桌面上的牌,然后搞个数组记一下每个值有没有出现过
来一张新牌的话如果存在就一直pop,然后给val加一下
如果不存在就压栈
考虑一张牌最多进栈一次,出栈一次,复杂度是线性的

#include <bits/stdc++.h>
using namespace std;
int to_int(char c) {
    if (isdigit(c)) return c - '0';
    else if (c == 'A') return 1;
    else if (c == 'J') return 10;
    else if (c == 'Q') return 11;
    return 12;
}
int val1, val2;
bool appear[13];
stack<int> s;
int main() {
    ios::sync_with_stdio(false);
    cin.tie(0);
    char c;
    int rnd = 0;
    while (cin >> c) {
        rnd++;
        int x = to_int(c);
        if (!appear[x]) {
            appear[x] = 1;
            s.push(x);
        }
        else {
            int y = 0, val = x;
            while (y != x) {
                y = s.top();
                appear[y] = 0;
                val += y;
                s.pop();
            }
            if (rnd & 1)
                val1 += val;
            else
                val2 += val;
        }
    }
    if (val1 == val2)
        cout << "-1" << endl;
    else
        cout << (val1 > val2 ? "zqc" : "lbg") << ' ' << max(val1, val2) << endl;
    return 0;
}

E

模拟题

#include <bits/stdc++.h>
using namespace std;
int main() {
    int n;
    string id;
    cin >> n >> id;
    cout << id << ' ';
    for (int i = 1; i <= n; i++) {
        int t;
        cin >> t;
        if (!t) {
            cout << 0 << ' ';
            continue;
        }
        int x = 0, y = 0, z = 0;
        x = t / 3600;
        t -= x * 3600;
        y = t / 60;
        t -= y * 60;
        z = t;
        printf("%02d:%02d:%02d ", x, y, z);
    }
    return 0;
}

F

首先发现选出的数列一定是2~n的质数
然后考虑质数个数
如果是奇数则一定平局
否则先手必胜

这题场上没A,我把个数是2n+1时,我又分了n为奇偶讨论,然后WA了

#include <bits/stdc++.h>
#define maxn 1000005
using namespace std;
bool bpr[maxn];
int main() {
    ios::sync_with_stdio(false);
    cin.tie(0);
    cout.tie(0);
    for (int i = 2; i < maxn; i++)
        bpr[i] = 1;
    for (int i = 2; i < maxn; i++)
        if (bpr[i])
            for (int j = 2 * i; j < maxn; j += i)
                bpr[j] = 0;
    int t;
    cin >> t;
    while (t--) {
        int n;
        cin >> n;
        int cnt = 0;
        for (int i = 2; i <= n; i++)
            if (bpr[i])
                cnt++;
        int win = 114514;
        if (cnt & 1)
            win = 0;
        else 
            win = 1;
        if (!win)
            cout << -1 << endl;
        else
            cout << (win > 0 ? "cxy" : "yls") << endl;
    }
    return 0;
}

GH

不会
补题是不可能的,这辈子也不可能的

I

模拟题
坑有点多

#include <bits/stdc++.h>
using namespace std;
struct people {
    string name;
    int score[20], a, b, c, s;
    void read() {
        cin >> name;
        s = 0;
        for (int i = 1; i <= 15; i++)
            cin >> score[i],
            s += score[i];
        a = b = c = 0;
        for (int i = 1; i <= 8; i++)
            a += score[i];
        for (int i = 9; i <= 12; i++)
            b += score[i];
        for (int i = 13; i <= 15; i++)
            c += score[i];
    }
};
vector<people> all;
struct team {
    string name;
    people p[15];
    int a, b, c, s, id, rank;
    void read() {
        cin >> name;
        a = b = c = 0;
        for (int i = 1; i <= 10; i++) {
            p[i].read();
            all.push_back(p[i]);
            a += p[i].a;
            b += p[i].b;
            c += p[i].c;
        }
        s = a;
        if (a >= 800)
            s += b;
        if (a >= 800 && b >= 400)
            s += c;
    }
}a[105];
bool cmp1(team a, team b) { return a.s == b.s ? a.name < b.name : a.s > b.s; }
bool cmp2(people a, people b) { return a.name < b.name; }
int main() {
    ios::sync_with_stdio(false);
    cin.tie(0);
    cout.tie(0);
    int n;
    cin >> n;
    for (int i = 1; i <= n; i++)
        a[i].read(),
        a[i].id = i;
    sort(a + 1, a + n + 1, cmp1);
    for (int i = 1; i <= n; i++) {
        a[i].rank = i;
        if (a[i].s == a[i - 1].s)
            a[i].rank = a[i - 1].rank;
    }
    for (int i = 1; i <= n; i++)
        cout << a[i].name << ' ' << a[i].a << ' ' << a[i].b << ' ' << a[i].c << ' ' << a[i].s << ' ' << a[i].rank << endl;
    int mx = 0;
    sort(all.begin(), all.end(), cmp2);
    for (int i = 0; i < all.size(); i++)
        mx = max(mx, all[i].s);
    cout << mx << ' ';
    for (int i = 0; i < all.size(); i++)
        if (all[i].s == mx)
            cout << all[i].name << ' ';
    cout << endl;
    return 0;
}

J

就23一个数
手算的,不想打代码

#include <bits/stdc++.h>
using namespace std;
int main() {
    cout << 1 << endl << 23 << endl;
    return 0;
}

K

模拟题
每抽一次奖for一遍找最大值
复杂度O(nm)

#include <bits/stdc++.h>
#define maxn 1005
using namespace std;
int n, a[maxn], m, b[maxn], sum;
int main() {
    ios::sync_with_stdio(0);
    cin.tie(0);
    cout.tie(0);
    cin >> n;
    for (int i = 1; i <= n; i++)
        cin >> a[i],
        sum += a[i];
    cin >> m;
    bool fl = 1;
    while (m--) {
        int x;
        cin >> x;
        int mx = 0;
        for (int i = 1; i <= n; i++)
            mx = max(mx, a[i]);
        /*
        (mx - x) / sum <= 1/5
        5(mx - x) <= sum
        */
        if (5 * (mx - a[x]) > sum) {
            fl = 0;
            break;
        }
        else {
            a[x]--;
            sum--;
        }
    }
    cout << (fl ? "PASS" : "BUG") << '\n';
    return 0;
}

L

sort一下,然后for一遍找最小值

#include <bits/stdc++.h>
using namespace std;
int a[25];
int main() {
    int t;
    cin >> t;
    while (t--) {
        int n, k;
        cin >> n >> k;
        for (int i = 1; i <= n; i++)
            cin >> a[i];
        sort(a + 1, a + n + 1);
        int ans = 1e9;
        for (int i = 1; i <= n - k + 1; i++)
            ans = min(ans, (a[i + k - 1] - a[i]) * 2);
        cout << ans << endl;
    }
    return 0;
}

M

垃圾模拟题,写了一年(
差一点抢到一血,自闭(

#include <bits/stdc++.h>
using namespace std;
bool isn(char x) {
    return x == '0' || x == '1';
}
bool check(string s) {
    for (int i = 1; i < s.size(); i++)
        if (s[i] == s[i - 1])
            return 0;
    return 1;
}
string bin(int x) {
    string res = "";
    bool fl = 0;
    for (int i = 14; i >= 0; i--)
        if (x >= (1 << i)) {
            fl = 1;
            x -= (1 << i);
            res.push_back('1');
        }
        else if (fl) res.push_back('0');
    return res;
}
string calc(string s) {
    for (int i = 0; i < s.size(); i++) {
        int j = i;
        char a = s[i];
        while (j + 1 < s.size() && s[j + 1] == s[i])
            j++;
        j++;
        if (j - i == 1 || !isn(a)) continue;
        string x, y, z;
        x = s.substr(0, i);
        y = bin(j - i);
        z = s.substr(j, s.size() - j);
        s = x + a + '(' + y + ')' + z;
    }
    for (int i = 1; i < s.size(); i++)
        if (isn(s[i]) && s[i - 1] == ')') {
            string x, y;
            x = s.substr(0, i);
            y = s.substr(i, s.size() - i);
            s = x + '+' + y;
        }
    for (int i = 2; i < s.size(); i++)
        if (s[i] == '(' && isn(s[i - 2])) {
            string x, y;
            x = s.substr(0, i - 1);
            y = s.substr(i - 1, s.size() - (i - 1));
            s = x + '+' + y;
        }
    return s;
}
int main() {
    int t;
    cin >> t;
    while (t--) {
        int n;
        string s;
        cin >> n >> s;
        string ns = calc(s);
        cout << (ns.size() < s.size() ? "YES" : "NO") << endl;
        cout << ns << endl;
    }
    return 0;
}

总结

rk 17
当时最好排名是rk 12
然后F调不出来,GH不会
就一直在祈祷(
最后保住了一个16G
感觉最好发挥的话(不读错题,调出F)应该能进前9
代码太丑了,不要d我(
自闭了 /kk

posted @ 2020-12-27 22:49  71rats  阅读(98)  评论(0编辑  收藏  举报