CodeStar2023年春第1周周赛普及奠基组

发布时间 2023-04-03 15:48:56作者: V_Melville

T1:最大数量

本题难度简单,考察二维数组计数,注意枚举小时和分钟从 \(0\) 开始。

代码实现
#include <bits/stdc++.h>
#define rep(i, n) for (int i = 0; i < (n); ++i)

using namespace std;

int f[30][70]; // f[i][j] 记录 i 时 j 分这个时刻进入商场的人数

int main() {
    int n;
    cin >> n;
    
    rep(i, n) {
        int h, m;
        cin >> h >> m;
        f[h][m]++;
    }
    
    int maxn = 0, max_h = -1, max_m = -1;
    rep(i, 24)rep(j, 60) {
        if (f[i][j] > maxn) {
            maxn = f[i][j];
            max_h = i;
            max_m = j;
        }
    }
    
    cout << max_h << ' ' << max_m << '\n';
    cout << maxn << '\n';
    
    return 0;
}

T2:字符串拆分

本题难度中等,考察字符串基础、数组计数和前缀和技巧。枚举分界点 \(i\),计算分界点 \(i\) 左右两边各出现不同字符的数量,这里可以使用数组计数+前缀和优化。

当分界点从 \(i-1\) 变为 \(i\) 时:
左子串多了一个字符 \(s_i\),右子串少了一个字符 \(s_i\)
若左子串加入 \(s_i\) 之后且 \(s_i\) 的个数为 \(1\),那么左子串的不同字符的个数 ++
若右子串去掉 \(s_i\) 之后且 \(s_i\) 的个数为 \(0\),那么右子串的不同字符的个数 --

初始时,左子串为空,右子串为 \(s_0 \sim s_{n-1}\)

代码实现
#include <bits/stdc++.h>
#define rep(i, n) for (int i = 0; i < (n); ++i)

using namespace std;

void solve() {
    int n;
    string s;
    cin >> n >> s;
    
    int ans = 0;
    int cntl = 0, cntr = 0;
    vector<int> pre(130), suf(130);
    rep(i, n) if (++suf[s[i]] == 1) cntr++;
    rep(i, n-1) {
        if (++pre[s[i]] == 1) cntl++;
        if (--suf[s[i]] == 0) cntr--;
        ans = max(ans, cntl+cntr);
    }
    cout << ans << '\n';
}

int main() {
    int t;
    cin >> t;
    
    while (t--) solve();
    
    return 0;
}