Codeforces Round 915 (Div. 2)

发布时间 2023-12-17 21:43:35作者: 加固文明幻景

基本情况

A题还没进入状态,卡了快10分钟。

B题一开始想复杂了,以为是树的直径,后面推出来发现针对叶子数目讨论就行了,正确思路出来太慢了(一个半小时)。

C题留了半个多小时,随便口胡了一个LIS思路,但是判断无解没思路。

C. Largest Subsequence

Problem - C - Codeforces

首先我们把字典序最大的子序列找出,方法就是从大到小枚举每个字母,然后能加就加入.

然后我们可以发现我们能做的只有对这个子序列排序,每次循环位移之后一定是把子序列最后的字符(最小的字符)放到最前面,然后相当于把这个字符从子序列里删掉了.

所以我们只需要判断把这个序列排序后能否使得原序列有序即可.

操作次数是子序列除了最大的字符以外的其他字符的数量.

void solve()
{
	int n; std::string s;
    std::cin >> n >> s;
    std::vector<std::vector<int> > pos(26);
    for(int i = 0; i < n; i++)
        pos[s[i] - 'a'].push_back(i);
    std::vector<int> p;
    int mx = -1;
    int cnt = 0;
    for(int i = 25; i >= 0; i--)
	{
        auto it = upper_bound(pos[i].begin(), pos[i].end(), mx);
        p.insert(p.end(), it, pos[i].end());
        if (cnt == 0) cnt = p.size();
        if (!p.empty()) mx = p.back();
    }
    auto q = p;
    std::sort(q.begin(), q.end(), [&](int x, int y){return s[x] < s[y];});
    std::string t = s;
    for(int i = 0; i < p.size(); i++)
        t[p[i]] = s[q[i]];
    if (!std::is_sorted(t.begin(), t.end()))
        std::cout << -1 << '\n';
    else
        std::cout << p.size() - cnt << '\n';
}