zstu 4111 Bread Sorting 线段树求逆序数

来源:互联网 发布:汉字注音软件下载 编辑:程序博客网 时间:2024/06/06 02:24
#include <stdio.h>#include <string.h>#define maxn 100001struct node{    int l,r,w;}e[maxn*4];void build(int a,int b,int c){    e[c].l=a;    e[c].r=b;    e[c].w=0;    if(a==b)        return;    int mid=(a+b)/2;    build(a,mid,2*c);    build(mid+1,b,2*c+1);}void update(int a,int b,int c,int val){    if(e[c].l==a&&e[c].r==b)    {        e[c].w+=val;        return;    }    int mid=(e[c].l+e[c].r)/2;    if(b<=mid)        update(a,b,2*c,val);    else if(a>mid)        update(a,b,2*c+1,val);    else    {        update(a,mid,2*c,val);        update(mid+1,b,2*c+1,val);    }    e[c].w=e[2*c].w+e[2*c+1].w;}int query(int a,int b,int c){    if(e[c].l==a&&e[c].r==b)        return e[c].w;    int mid=(e[c].l+e[c].r)/2;    if(b<=mid)        return query(a,b,2*c);    else if(a>mid)        return query(a,b,2*c+1);    else        return query(a,mid,2*c)+query(mid+1,b,2*c+1);}int main(){    int n;    while(scanf("%d",&n)!=EOF)    {        int i,j,k,sum,x,p,q;        build(1,n,1);        sum=0;        for(i=0;i<n;i++)        {            scanf("%d",&x);            sum+=query(x,n,1);            update(x,x,1,1);        }        p=sum%2;        sum=0;        build(1,n,1);        for(i=0;i<n;i++)        {            scanf("%d",&x);            sum+=query(x,n,1);            update(x,x,1,1);        }        q=sum%2;        if(p^q)            printf("Impossible\n");        else            printf("Possible\n");    }    return 0;}
用线段树求出两个排序的逆序数,判断奇偶;同奇同偶输出possible,否则输出impossible
怎么证明,I don't know ,问了同学,告诉我是YY出来的。。
原创粉丝点击