Featured image of post Codeforces Round #1091(Div.2)

Codeforces Round #1091(Div.2)

B

题目大意:

数据范围:

思路:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
void solve() {
    int n, k;
    cin >> n >> k;
    vi a(n);
    rep(i, 0, n - 1) cin >> a[i];
    vi p(k);
    rep(i, 0, k - 1) {
        cin >> p[i];
        p[i]--;
    }
    int tem = p[0];
    int las = tem;
    int ans = 0;
    rep(i, tem + 1, n - 1) {
        if (a[i] != a[tem] && a[i] != a[i - 1]) ans++;
    }
    las = tem;
    int ans2 = 0;
    frep(i, tem - 1, 0) {
        if (a[i] != a[tem] && a[i] != a[i + 1]) ans2++;
    }
    int maxx = max(ans, ans2);
    cout << 2 * maxx << endl;
    return;
}

C

题目大意:

数据范围:

思路:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
void solve() {
    ll n, m, a, b;
    cin >> n >> m >> a >> b;
    if (__gcd(n, a) != 1 || __gcd(m, b) != 1) {
        cout << "NO" << endl;
        return;
    }
    if (__gcd(n, m) > 2) {
        cout << "NO" << endl;
        return;
    }
    cout << "YES" << endl;
    return;
}

D

题目大意:

数据范围:

思路:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
void solve() {
    int n, k;
    cin >> n >> k;
    vi a(n);
    rep(i, 0, n - 1) cin >> a[i];
    vi p(k);
    rep(i, 0, k - 1) {
        cin >> p[i];
        p[i]--;
    }
    vi tem;
    rep(i, 0, k - 1) {
        if (i == 0) {
            int ans = 0;
            frep(j, p[i] - 1, 0) {
                if (a[j] != a[p[i]] && a[j] != a[j + 1]) ans++;
            }
            tem.push_back(ans);
        }
        if (i == k - 1) {
            int ans = 0;
            rep(j, p[i] + 1, n - 1) {
                if (a[j] != a[p[i]] && a[j] != a[j - 1]) ans++;
            }
            tem.push_back(ans);
        } else {
            int idx = p[i], idx2 = p[i + 1];
            int ans = 0;
            int ans2 = 0;
            rep(j, p[i] + 1, p[i + 1]) {
                if (a[j] != a[p[i]] && a[j] != a[j - 1]) ans++;
            }
            tem.push_back(ans);
        }
    }
    int ans = 0;
    int maxx = 0;
    rep(i, 0, k) {
        ans += tem[i];
        maxx = max(maxx, tem[i]);
    }
    cout << max(ans, maxx * 2) << endl;
    return;
}

E

题目大意:

数据范围:

思路:

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
template <typename T = long long>
class Tree {
    vector<T> tree;

public:
    // 构造函数:初始化大小为 n 的树状数组,初始所有元素值为 val(外部表现为 0-based)
    Tree(int n, T val = 0) : tree(n + 1) {
        for (int i = 1; i <= n; i++) {
            tree[i] += val;
            int nxt = i + (i & -i);
            if (nxt <= n) {
                tree[nxt] += tree[i];
            }
        }
    }

    // 构造函数:使用给定的 vector 在 O(N) 时间内快速初始化建树
    Tree(const vector<T>& data) {
        int n = data.size();
        tree.resize(n + 1);
        for (int i = 1; i <= n; i++) {
            tree[i] += data[i - 1];  // data是 0-based
            int nxt = i + (i & -i);
            if (nxt <= n) {
                tree[nxt] += tree[i];
            }
        }
    }

    // 单点修改:将 0-based 下标 i 处的元素增加 val
    void add(int i, T val = 1) {
        for (++i; i < tree.size(); i += i & (-i)) {
            tree[i] += val;
        }
    }

    // 前缀求和:计算 0-based 下标区间 [0, i] 内的所有元素之和
    T pre(int i) const {
        T res = 0;
        for (++i; i > 0; i &= i - 1) {
            res += tree[i];
        }
        return res;
    }

    // 区间求和:计算 0-based 下标区间 [l, r] 内的所有元素之和
    T query(int l, int r) const {
        if (r < l) {
            return 0;
        }
        return pre(r) - pre(l - 1);  // 当 l=0 时, pre(-1) 会合理地返回 0
    }

    // 树上二分查找:返回满足前缀和 >= val 的最小 0-based 下标
    int lower_bound(T val) const {
        int w = bit_width(tree.size() - 1);
        int res = 0;
        T s = 0;
        for (int i = w - 1; i >= 0; i--) {
            int nxt = res + (1 << i);
            if (nxt < tree.size() && tree[nxt] + s < val) {
                res += (1 << i);
                s += tree[nxt];
            }
        }
        return res;  // 返回 0-based 下标:内部 1-based 下标为 res + 1,因此 0-based 为 res
    }
};
void solve() {
    int n;
    cin >> n;
    vi a(n);
    rep(i, 0, n - 1) cin >> a[i];
    vi d(n);
    rep(i, 0, n - 1) cin >> d[i];
    Tree tree(n + 1);
    Tree tree2(n + 1, 1);
    vi res(n, INT_MAX);
    frep(i, n - 1, 0) {
        int tem2 = n - 1 - i - tree.pre(a[i]);
        if (tem2 < d[i]) {
            cout << -1 << endl;
            return;
        }
        tree.add(a[i], 1);
    }
    vi res2;
    frep(i, n - 1, 0) {
        vi tem3;
        rep(j, 0, sz(res2) - 1) {
            if (a[res2[j]] > a[i]) {
                tem3.push_back(res2[j]);
            }
        }
        int tem2 = sz(tem3) - d[i];
        if (tem2 == 0)
            res2.insert(res2.begin(), i);
        else {
            int tem4 = tem3[tem2 - 1];
            int idx = -1;
            rep(j, 0, sz(res2)) {
                if (tem4 == res2[j]) {
                    idx = j;
                    break;
                }
            }
            res2.insert(res2.begin() + idx + 1, i);
        }
    }
    rep(i, 0, n - 1) res[res2[i]] = i + 1;
    for (int& p : res) cout << p << ' ';
    cout << endl;
    return;
}