现在的位置: 首页 > 综合 > 正文

DVD。。。

2017年11月21日 ⁄ 综合 ⁄ 共 2744字 ⁄ 字号 评论关闭

终于过了,比赛的时候一直在TLE,然后赛后好不容易不TLE了,就开始wa。。。。

题意:典型的线段树操作吧。。。。如果给的操作指示是0 就交换a b 两个格子所在位置的DV,如果是1,就查询a b区间内是否都是a b区间内的值。是的话,YES,否则,NO。

其实比赛的时候觉得线段树肯定会TLE,所以都没想着改他。。。

要注意一点,就是在query的时候,是要保存寻找到的最大值的最大值,最小值的最小值,如果只是判断是否相等,就会错,因为不一定在原来的位置,只要在区间内就好。

然后代码有点拖沓。

#include <stdio.h>
#include <iostream>
using namespace std;
#define maxn 100010
#define inf 0x3f3f3f3f
struct node
{
    int low,hig;
    int quan;
}tree[maxn*3];
int top,que[maxn],loc[maxn];
 int n,m;
 int maxx,minn;
int min(int x,int y)
{
    if(x>y) return y;
    else return x;
}
int max(int x,int y)
{
    if(x>y) return x;
    else return y;
}
void creat(int l,int r,int rt)
{
    tree[rt].low=l;
    tree[rt].hig=r;
    if(l==r) {loc[top++]=rt;return;}
    int mid=(l+r)/2;
    creat(l,mid,rt<<1);
    creat(mid+1,r,rt<<1|1);
}
/*void update(int ll,int rr,int l,int r,int rt)
{
    if(ll==l||rr==r)
    {
      //  printf("l=%d  ll=%d tree.low=%d   r=%d  rr=%d  tree.hig=%d\n",l,ll,tree[rt].low,r,rr,tree[rt].hig);
       // printf("tree.low=%d  ll=%d  l=%d\n",tree[rt].low,ll,l);printf("tree.hig=%d  rr=%d  d=%d\n",tree[rt].hig,rr,r);
        tree[rt].low=max(que[ll],tree[rt].low);
        tree[rt].hig=min(que[rr],tree[rt].hig);
        return;
    }
    int mid=(l+r)/2;
    if(rr<=mid) update(ll,rr,l,mid,rt<<1);
    else if(ll>mid) update(ll,rr,mid+1,r,rt<<1|1);
    else {update(ll,mid,l,mid,rt<<1);update(mid+1,rr,mid+1,r,rt<<1|1);}
    tree[rt].low=min(tree[rt<<1].low,tree[rt<<1|1].low);
    tree[rt].hig=max(tree[rt<<1].hig,tree[rt<<1|1].hig);
}
void update(int x,int y,int l,int r,int rt)
{

}*/
void query(int ll,int rr,int l,int r,int rt)
{
    if(ll==l&&rr==r)
    {
        maxx=max(maxx,tree[rt].hig);
        minn=min(minn,tree[rt].low);
        return;
    }
    int mid=(l+r)/2,tmp,ans;
    if(rr<=mid)  query(ll,rr,l,mid,rt<<1);
    else if(ll>mid)  query(ll,rr,mid+1,r,rt<<1|1);
    else {query(ll,mid,l,mid,rt<<1);query(mid+1,rr,mid+1,r,rt<<1|1);}
   // return tmp&&ans;
}

template<class T>
inline char read(T &n){
    T x = 0, tmp = 1; char c = getchar();
    while((c < '0' | c > '9') && c != '-' && c != EOF) c = getchar();
    if(c == '-') c = getchar(), tmp = -1;
    while(c >= '0' && c <= '9') x *= 10, x += (c - '0'),c = getchar();
    n = x*tmp;
    return c;
}
template <class T>
inline void write(T n) {
    if(n < 0) {
        putchar('-');
        n = -n;
    }
    int len = 0,data[20];
    while(n) {
        data[len++] = n%10;
        n /= 10;
    }
    if(!len) data[len++] = 0;
    while(len--) putchar(data[len]+48);
}
void init()
{
    int i;
    for(i=0;i<n;i++)
        que[i]=i;
}
void find(int x,int y)
{
    int xx=loc[x],yy=loc[y];
    tree[xx].low=que[x];
    tree[xx].hig=que[x];
    tree[yy].low=que[y];
    tree[yy].hig=que[y];
    xx/=2;
    while(xx>0)
    {
        tree[xx].low=min(tree[xx<<1].low,tree[xx<<1|1].low);
        tree[xx].hig=max(tree[xx<<1].hig,tree[xx<<1|1].hig);
        xx/=2;
    }
    yy/=2;
    while(yy>0)
    {
        tree[yy].low=min(tree[yy<<1].low,tree[yy<<1|1].low);
        tree[yy].hig=max(tree[yy<<1].hig,tree[yy<<1|1].hig);
        yy/=2;
    }
}
int main()
{
    int t;
    read(t);
    while(t--)
    {
        read(n);read(m);
        top=0;
        init();
        creat(0,n-1,1);
        int a,b,c;
        while(m--)
        {
         read(a);read(b);read(c);
            if(a==0)
            {
                int tmp=que[c];
                que[c]=que[b];
                que[b]=tmp;

                find(b,c);
            //    find(c);
           //     update(b,c,0,n-1,1);
            }
            if(a==1)
            {
              //  put(0,n-1,1);
              maxx=-1;minn=inf;
              query(b,c,0,n-1,1);
                if(maxx==c&&minn==b) puts("YES");
                else puts("NO");
            }
        }
    }
    return 0;
}

抱歉!评论已关闭.