zoukankan      html  css  js  c++  java
  • bzoj2212 Tree Rotations

    被BZOJ坑了一下午,原以为是我程序有问题一直WA,结果是我数组小了。。。为啥不给我RE!!!

    线段树合并,对于逆序对而言,只能通过交换左右子树来达到,那么我们就可以想到对于一个结点而言,我们当然要取左右子树不叫换产生的逆序对,及交换产生的逆序对,取最小的就好了,另外呢,因为要维护子树中包含的数,在往上递归时需要对该树合并。

    #include<cstdio>
    #include<cstdlib>
    #include<iostream>
    #include<string>
    #include<set>
    #include<algorithm>
    #include<vector>
    #include<queue>
    #include<list>
    #include<cmath>
    #include<cstring>
    #include<map>
    #include<stack>
    using namespace std;
    #define INF 0x3f3f3f3f
    #define maxn 2000005
    #define ull unsigned long long
    #define ll long long
    #define hashmod 99999839
    #define mod 9997
    int n,x,y;
    int ls[maxn],rs[maxn];//结点的左右儿子
    int c[maxn],len;//结点代表的区间中有的个数
    long long ans,s;
    stack<int> st;
    int newnode(){//返回一个新结点
        int p;
        if(st.empty()) p = len++;
        else p = st.top(),st.pop();
        ls[p] = rs[p] = 0,c[p] = 1;
        return p;
    }
    int bulid(int x){//建立叶子结点对应的树并返回根
        int root = newnode();//先申请一个新节点
        int l = 1,r = n,mid,p = root;
        while(l < r){
            mid = (l + r) >> 1;
            if(mid >= x) ls[p] = newnode(),p = ls[p],r = mid;
            else rs[p] = newnode(),p = rs[p],l = mid + 1;
        }
        return root;
    }
    int merge(int p,int q){//合并以p,q为根的树,并返回新的根
        if(!p || !q) return p + q;
        s += (long long)c[rs[p]] * c[ls[q]];
        ls[p] = merge(ls[p],ls[q]);
        rs[p] = merge(rs[p],rs[q]);
        c[p] = c[ls[p]] + c[rs[p]];
        st.push(q);//可将合并了的q结点放入st中
        return p;
    }
    int solve(){
        scanf("%d",&x);
        if(x) return bulid(x);//对叶节点建立一颗线段树
        int p = solve(),q = solve();//建立其左右儿子
        ll t = c[p] * c[q];
        s = 0,p = merge(p,q);//逆序对由非叶子结点产生
        if(s <= t / 2) ans += s;
        else ans += t - s;
        return p;
    }
    void init(){
        while(!st.empty()) st.pop();
        len = 1,ans = 0;
    }
    int main(){
        freopen("a.in","r",stdin);
        freopen("b.out","w",stdout);
        scanf("%d",&n);
        init();
        solve();
        printf("%lld",ans);
        return 0;
    }
  • 相关阅读:
    Web.py Cookbook 简体中文版
    'IContextMenu' : no GUID has been associated with this object问题的解决
    switchflow/switchflow/asiohttp at master · baus/switchflow · GitHub
    面试体验:Facebook 篇
    Nodejs抓取非utf8字符编码的页面
    小体会
    做socket保持长连接的一些心得
    【资料整理】Socket编程之非阻塞connect(二)
    Less copies in Python with the buffer protocol and memoryviews
    » 文档与笔记利器 reStructuredText 和 Sphinx Wow! Ubuntu
  • 原文地址:https://www.cnblogs.com/zhuiyicc/p/9537860.html
Copyright © 2011-2022 走看看