1 条题解

  • 0
    @ 2026-4-30 0:56:07

    Solution

    发现直接贪心不好做,注意到答案有单调性,考虑二分答案。

    这样看似还需要一个贪心策略,实际上二分答案后确定了更加优秀的性质。

    每一个合法的塔一定有最后一个是 I,前面有一个 O,最前面有一个 IJ

    所以倒着枚举,每次尽可能选靠后的,维护当前最后一位,第二位和第一位的数量,问题在 I 怎么决策。

    当目前第三位的数量小于二分的答案 midmid 时,将 I 作为第三位,否则作为第一位。

    Code

    // Code By CommandSR (uid 844860)
    const int N = 1e6 + 5;
    int n;
    string s;
    bool check(int x) {
    	int c1 = 0, c2 = 0, c3 = 0;
    	D(i, n, 1) {
    		if (s[i] == 'I') {
    			if (c3 < x) ++c3;
    			else if (c1 < c2) ++c1;
    		} else if (s[i] == 'O') {
    			if (c2 < c3) ++c2;
    		} else if (s[i] == 'J') {
    			if (c1 < c2) ++c1;
    		}
    	}
    	return (c3 == x && c1 == x);
    }
    void sol() {
    	cin >> n >> s;
    	s = " " + s;
    	int l = 0, r = n/3, mid, res;
    	while (l <= r) {
    		mid = (l + r) >> 1;
    		if (check(mid)) l = mid + 1, res = mid;
    		else r = mid - 1;
    	}
    	cout << res << '\n';
    }
    
    • 1

    信息

    ID
    9004
    时间
    3000ms
    内存
    256MiB
    难度
    10
    标签
    递交数
    2
    已通过
    1
    上传者