F题

首先考虑将状态用一个串表示。

对于每个灯,将按下它的同时改变的所有灯的下标置1,其他的置0.

表示的取反。题目的要求就转化为,用这些串异或组合出.

线性基维护即可。由于位,选择用bitset或者用两个long long的数字维护线性基。

#include <bits/stdc++.h>
using namespace std;
using ll = long long;
#define int long long 
#define endl '\n'

const int B = 100;
struct liner_base {
    vector<bitset<101>> a;
    vector<vector<int>> b;
    int cnt = 0;
    liner_base() {
        a.resize(B + 1);
        b.resize(B + 1);
    }
    int insert(bitset<101> x, int id) {
        vector<int> v = { id };
        for (int i = B;i >= 0;i--) {
            if (x[i]) {
                if (a[i].count() == 0) {
                    a[i] = x;
                    b[i] = v;
                    cnt++;
                    return 1;
                }
                else {
                    x ^= a[i];
                    for (auto y : b[i]) v.push_back(y);
                }
            }
        }
        return 0;
    }
    int size() {
        return cnt;
    }
    vector<int> ask(bitset<101> x) {
        vector<int> res;
        for (int i = B;i >= 0;i--) {
            if (x[i]) {
                x ^= a[i];
                for (auto y : b[i]) res.push_back(y);
            }
        }
        if (x.count() != 0) {
            res.clear();
        }
        return res;
    }
};

void Prework() {

}
void Solve() {
    int n;cin >> n;
    string s;cin >> s;s = ' ' + s;
    map<int, vector<int>> X, Y;
    vector<array<int, 2>> a(n + 1);
    for (int i = 1;i <= n;i++) {
        int x, y;cin >> x >> y;
        X[x].push_back(i);
        Y[y].push_back(i);
        a[i] = { x,y };
    }
    bitset<101> dp;
    liner_base lb;
    for (int i = 1;i <= n;i++) {
        auto [x, y] = a[i];
        dp.reset();
        for (auto u : X[x]) {
            dp[u] = 1;
        }

        for (auto u : Y[y]) {
            dp[u] = 1;
        }
        lb.insert(dp, i);
    }
    bitset<101> tar;
    for (int i = 1;i <= n;i++) {
        if (s[i] == '0') tar[i] = 1;
    }
    if (count(s.begin() + 1, s.end(), '1') == n) return cout << "0\n", void();
    auto res = lb.ask(tar);
    if (res.size() == 0) {
        cout << "-1\n";
    }
    else {
        vector<int> ans(n + 1);
        for (auto i : res) ans[i] ^= 1;
        int sum = 0;
        for (int i = 1;i <= n;i++) {
            if (ans[i]) sum += 1;
        }
        cout << sum << endl;
        for (int i = 1;i <= n;i++) {
            if (ans[i]) cout << i << " ";
        }
        cout << endl;
    }
}

signed main() {
    ios::sync_with_stdio(0);
    cin.tie(0);cout.tie(0);
    int T = 1;
    //cin >> T;
    Prework();
    while (T--) Solve();
}