description:
所有子区间中逆序对的个数

solution:
暴力肯定是不可取的 考虑一个逆序对的贡献,当且仅当一个区间包含了该逆序对才对该区间有贡献,根据这点,假设左边界为i,右边界为j,则贡献为i * (n - j + 1)。
根据这个思路,我们枚举右边界j,来计算有多少符合的左边界i来计算贡献,求他们的下标和,下标和用树状数组维护即可。

code:

#include <bits/stdc++.h>

using namespace std;

#define LL __int128

const int N = 1e6 + 5;

LL c[N];

LL lowbit(LL x){
    return x & (-x);
}

void update(LL i,LL x){
    for(;i < N;i += lowbit(i)){
        c[i] += x;
    }
}

LL query(LL i){
    LL sum = 0;

    for(;i > 0;i -= lowbit(i)){
        sum += c[i];
    }

    return sum;
}

void out(LL x){
    if(x < 10){
        putchar(x + '0');
        return ;
    }
    out(x / 10);
    putchar(x % 10 + '0');
}

vector <int> a,b;

int main(){
    ios::sync_with_stdio(0);
    int n;
    cin >> n;

    for(int i = 0;i < n;i ++){
        int x;
        cin >> x;
        a.push_back(x);
        b.push_back(x);
    }

    sort(a.begin(),a.end());
    a.erase(unique(a.begin(),a.end()),a.end());

    LL res = 0;
    for(int i = 0;i < n;i ++){
        int pos = lower_bound(a.begin(),a.end(),b[i]) -a.begin() + 1;
        res += 1LL*(query(n) - query(pos)) *(n - i);
        update(pos,i + 1);
    }

    out(res);

    return 0;
}