Skip to content
Author: lllyouo
Date: 20250921
tag: 笛卡尔树
link: https://www.luogu.com.cn/problem/P5854

问题描述

link

分析

参考代码

cpp
#include <bits/stdc++.h>
#define int long long
using namespace std;

const int N = 1e7 + 10;
int n, v[N], ls[N], rs[N], st[N], top;

void build() {
    for (int i = 1; i <= n; i++) {
        int k = top;
        while (k > 0 && v[st[k]] > v[i]) k--;
        if (k) rs[st[k]] = i; // 栈顶元素的右儿子 = 当前元素
        if (k < top) ls[i] = st[k + 1]; // 当前元素的左儿子 = 上一个被弹出的元素
        st[++k] = i; // 当前元素入栈
        top = k;
    }
}

signed main() {
    scanf("%lld", &n);
    for (int i = 1; i <= n; i++) scanf("%lld", &v[i]);

    build();

    int lans = 0, rans = 0;
    for (int i = 1; i <= n; i++) {
        lans ^= i * (ls[i] + 1);
        rans ^= i * (rs[i] + 1);
    }
    cout << lans << " " << rans << endl;

    return 0;
}