BZOJ 1018

program bzoj1018;
type
  node=array [0..5] of boolean;
  pair=array [0..1] of boolean;
var
  tot,c,i,j,k,x1,y1,x2,y2:longint;
  ans:boolean;
  ch:char;
  x,y,z:node;
  left,right:array [0..200001] of longint;
  stu:array [0..200001] of node;
  had:array [0..200001]of pair;

procedure swap(var a,b:longint);
begin
    if a=b then exit;
    a:=a xor b;
    b:=a xor b;
    a:=a xor b;
end;

procedure build(s,e,now:longint);
var    mid:longint;
begin
    if s=e then
        begin
            stu[now][0]:=true;
            stu[now][3]:=true;
            exit;
        end;
    mid:=(s+e) >>1;
    inc(tot);
    left[now]:=tot;
    build(s,mid,tot);
    inc(tot);
    right[now]:=tot;
    build(mid+1,e,tot);
end;

function update(a,b:node;had:pair):node;
var i,j,k:longint;
    now:node;
begin
  fillchar(now,sizeof(now),false);
  if had[0] and a[0] and b[0] then now[0]:=true;
  if had[1] and a[1] and b[2] then now[0]:=true;
  if had[0] and a[0] and b[1] then now[1]:=true;
  if had[1] and a[1] and b[3] then now[1]:=true;
  if had[0] and a[2] and b[0] then now[2]:=true;
  if had[1] and a[3] and b[2] then now[2]:=true;
  if had[0] and a[2] and b[1] then now[3]:=true;
  if had[1] and a[3] and b[3] then now[3]:=true;
  if a[4] then now[4]:=true;
  if a[0] and a[3] and had[0] and had[1] and b[4] then now[4]:=true;
  if b[5] then now[5]:=true;
  if b[0] and b[3] and had[0] and had[1] and a[5] then now[5]:=true;
  exit(now);
end;

procedure insertl(w:boolean;x,l,r,now:longint);
var mid:longint;
begin
  if l=r then
    begin
      if w then
        fillchar(stu[now],sizeof(stu[now]),true)
           else
        begin
          fillchar(stu[now],sizeof(stu[now]),false);
          stu[now][0]:=true;
          stu[now][3]:=true;
        end;
      exit;
    end;
  mid:=(l+r)>>1;
  if x<=mid then insertl(w,x,l,mid,left[now])
            else insertl(w,x,mid+1,r,right[now]);
  stu[now]:=update(stu[left[now]],stu[right[now]],had[now]);
end;

procedure insertr(w:boolean;x,y,l,r,now:longint);
var mid:longint;
begin
  mid:=(l+r)>>1;
  if x=mid then
    begin
      had[now][y]:=w;
      stu[now]:=update(stu[left[now]],stu[right[now]],had[now]);
      exit;
    end;
  if x<=mid then insertr(w,x,y,l,mid,left[now])
            else insertr(w,x,y,mid+1,r,right[now]);
  stu[now]:=update(stu[left[now]],stu[right[now]],had[now]);
end;

function find(x1,x2,l,r,now:longint):node;
var temp:node;
    mid:longint;
begin
  if(x1=l)and(x2=r) then exit(stu[now]);
  mid:=(l+r)>>1;
  if x2<=mid then exit(find(x1,x2,l,mid,left[now]))
             else
  if x1>mid then exit(find(x1,x2,mid+1,r,right[now]))
            else exit(
                      update(find(x1,mid,l,mid,left[now]),
                             find(mid+1,x2,mid+1,r,right[now]),
                             had[now])
                     );
end;

procedure main;
begin
  readln(c);
  build(1,c,0);
  repeat
    read(ch);
    case ch of
      'E':break;
      'O':begin
            read(ch,ch,ch,y1,x1,y2,x2);
            dec(y1);
            dec(y2);
            if x1=x2 then insertl(true,x1,1,c,0)
                     else
            if x1<x2 then insertr(true,x1,y1,1,c,0)
                     else insertr(true,x2,y1,1,c,0);
          end;
      'C':begin
            read(ch,ch,ch,ch,y1,x1,y2,x2);
            dec(y1);
            dec(y2);
            if x1=x2 then insertl(false,x1,1,c,0)
                     else
            if x1<x2 then insertr(false,x1,y1,1,c,0)
                     else insertr(false,x2,y1,1,c,0);
          end;
      'A':begin
            read(ch,ch,y1,x1,y2,x2);
            dec(y1);
            dec(y2);
            if x1>x2 then
              begin
                swap(x1,x2);
                swap(y1,y2);
              end;
            x:=find(1,x1,1,c,0);
            y:=find(x1,x2,1,c,0);
            z:=find(x2,c,1,c,0);
            ans:=false;
            ans:=ans or y[y1*2+y2];
            ans:=ans or(x[5] and y[(1-y1)*2+y2]);
            ans:=ans or(z[4] and y[y1*2+1-y2]);
            ans:=ans or(x[5] and z[4] and y[(1-y1)*2+1-y2]);
            if ans then writeln('Y')
                   else writeln('N');
          end;
    end;
  until false;
end;


begin
  main;
end.

BZOJ1018

posted @ 2014-10-27 17:03  Kiss our dream  阅读(...)  评论(... 编辑 收藏