Bootstrap

cf 988 div3 C 将一些特定的元素拿出来考虑 E(交互,考虑多询问一位,以此判断这一位的情况)

C题意:
[1 n] 的排列,我们要任意相邻的数相加得到的和是合数。
如果对于n 不存在这个一个排列,那么输出-1

一个比较显然的思路
就是奇数放一起,偶数放一起。奇数之间相加是偶数
偶数之间相加是偶数。那么他们都是合数。
但是还有 奇偶相邻的地方,会出现一个奇数+偶数的情况。
我们应该怎么安排这个位置上的数字?
考虑一些特定的元素,
5 +4 =9
再小的 奇数+偶数不会出现合数了。
所以对于n <=4 的情况,直接输出-1 了。
当n >4 的时候,直接将奇偶相接的地方规定为 5 4 就可以了

E题意:
长度为n 的二进制串,可以询问 l r 之内的01 的子序列个数。
至多询问n 次,确定这个字符串或者判定没有这样的字符串

其实一直很不会做这种有点构造感觉的题。呃呃,还是得多练
先来思考在 一段知道01 子序列个数的段之后,我们在多询问一位,如果变多了那么这一位 是1,如果没有变那么这一位只能是0。
因为只能询问n次,我们询问(0 1)(0 2)…(0 n-1)这些前缀。确定每一位上的数字。
最后我们将我们生成的01串,在和每个前缀的01 序列作比较。因为我们之前只是将增多变成这一位是1,但是可能增加的数量不对。
我第一个不是零的下标。如果是 i ,那么前面有 (i-t)个1,有t 个0.

丑陋的代码~~

#include <bits/stdc++.h>
using namespace std;
#define ll long long
int ask(int x, int y)
{
    cout << "? " << x + 1 << " " << y + 1 << endl;
    int ans;
    cin >> ans;
    return ans;
}
void solve()
{
    int n;
    cin >> n;
    string s = " ";
    vector<int> a(n);
    int la = 0;
    bool f = 0;
    for (int i = 1; i < n; i++)
    {
        int t = ask(0, i);
        a[i] = t;
        if (t == la)
            s += '0';
        else
        {
            if (!f)
            {
                if (t == i)
                    s[0] = '0';
                else
                {
                    int t1 = i - t;
                    int t2 = t;
                    s.clear();
                    for (int i = 0; i < t1; i++)
                        s += '1';
                    for (int i = 0; i < t2; i++)
                        s += '0';
                }
            }
            s += '1';
            la = t;
            f = 1;
        }
    }
    bool f1 = 0;
    for (int i = 0; i < n; i++)
        if (a[i] != 0)
        {
            f1 = 1;
        }
    if (!f1)
    {
        cout << "! IMPOSSIBLE" << endl;
        return;
    }

    int cnt0 = 0;
    int ans = 0;
    for (int i = 0; i < n; i++)
    {
        if (s[i] == '0')
            cnt0++;
        else
        {
            ans += cnt0;
            if (a[i] != ans)
            {
                cout << "! IMPOSSIBLE" << endl;
                return;
            }
        }
    }
    cout << "! " << s << endl;
}
int main()
{
    std::cin.tie(nullptr)->sync_with_stdio(false);
    int t;
    cin >> t;
    while (t--)
    {
        solve();
    }
    return 0;
}

;