Rinne Loves Data Structure

思路

我们插入的位置大概分了四种:
第一种
图片说明

显然我们找到比当前插入的值的pre,也就是比当前节点大的最小值。
第二种
图片说明

我们只要找到当前节点的suc,也就是比当前节点小的,最大值。

第三种
图片说明

我们只要找到当前节点的suc,也就是比当前节点小的,最大值。

第四种

图片说明

显然我们找到比当前插入的值的pre,也就是比当前节点大的最小值。

综上,一,三我们可以直接去
第二种是没有的,我们也可以直接特判,得到它的,更新
第四种是没有的,我们可以直接特判,然后得到它的,所以

插入第一个元素的时候我们既没有前驱,也没有后驱,需要单独考虑。

最后加一个相同值的判定,这道题目没有明确说明是否这n个数都是不一样的。

代码

/*
  Author : lifehappy
*/
#pragma GCC optimize(2)
#pragma GCC optimize(3)
#include <bits/stdc++.h>
#define mp make_pair
#define pb push_back
#define endl '\n'

using namespace std;

typedef long long ll;
typedef unsigned long long ull;
typedef pair<int, int> pii;

const double pi = acos(-1.0);
const double eps = 1e-7;
const int inf = 0x3f3f3f3f;

inline ll read() {
  ll f = 1, x = 0;
  char c = getchar();
  while(c < '0' || c > '9') {
    if(c == '-')    f = -1;
    c = getchar();
  }
  while(c >= '0' && c <= '9') {
    x = (x << 1) + (x << 3) + (c ^ 48);
    c = getchar();
  }
  return f * x;
}

void print(ll x) {
  if(x < 10) {
    putchar(x + 48);
    return ;
  }
  print(x / 10);
  putchar(x % 10 + 48);
}

const int N = 3e5 + 10;

int dep[N], n;

set<int> st;

int main() {
    // freopen("in.txt", "r", stdin);
    // freopen("out.txt", "w", stdout);
    // ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
    int n = read();
    ll ans = 0;
    while(n--) {
        int x = read();
        if(st.size() == 0) {
            puts("0");
            st.insert(x);
            continue;
        }
        // auto p = lower_bound(st.begin(), st.end(), x);
        //用这个给tle了,不懂原理。
        auto p = st.lower_bound(x);
        if(*p == x) {
            printf("%lld\n", ans);
            continue;
        }
        if(p == st.begin()) {
            dep[x] = dep[*p] + 1;
            ans += dep[x];
        }
        else if(p == st.end()) {
            p--;
            dep[x] = dep[*p] + 1;
            ans += dep[x];
        }
        else {
            dep[x] = dep[*p] + 1;
            p--;
            dep[x] = max(dep[x], dep[*p] + 1);
            ans += dep[x];
        }
        st.insert(x);
        printf("%lld\n", ans);
    }
    return 0;
}