BZOJ3668: [Noi2014]起床困难综合症

7 篇文章 0 订阅
1 篇文章 0 订阅

  题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=3668

  OR,XOR,AND都是位运算,其运算结果相当于转化成二进制之后每位分别进行该项位运算,每位之间是相互独立,不存在进位,而在二进制下只存在0/1,所以可以把它看成一个二进制数,从最高位开始扫,每一位分别用0/1试一下是否可行,每次取当前位在合法情况下尽可能的大值(即尽可能取1),因为是从最高位开始扫,所以答案一定是最大值,然后按位乘上权重相加就是答案。

  贴代码:

 var a,b:array[0..100005]of longint;
     n,m,ans,sum:longint;
 procedure init;
  var i,j,x:longint;
      ch,ch1,ch2:char;
  begin
   assign(input,'sleep.in');reset(input);
   assign(output,'sleep.out');rewrite(output);
   readln(n,m);
   for i:=1 to n do
    begin
     read(ch);
     case ch of
      'A':begin
           readln(ch,ch1,ch2,x);
           a[i]:=0;b[i]:=x;
          end;
      'O':begin
           readln(ch,ch1,x);
           a[i]:=1;b[i]:=x;
          end;
      'X':begin
           readln(ch,ch1,ch2,x);
           a[i]:=2;b[i]:=x;
          end;
      end;
     end;
   end;
 function work(x,y,z:longint):longint;
  begin
   case z of
    0:exit(x and y);
    1:exit(x or y);
    2:exit(x xor y);
   end;
  end;
 procedure main;
  var bo,x1,x2,k,i,j,step:longint;
   begin
    step:=31;
    ans:=0;sum:=0;
    for i:=step downto 1 do
     begin
      bo:=0;x1:=0;x2:=1;
      if sum+(1<<(i-1))>m then bo:=1;
      for j:=1 to n do
       begin
        k:=0;
        if b[j] and (1<<(i-1))=1<<(i-1) then k:=1;
        x1:=work(x1,k,a[j]);
        x2:=work(x2,k,a[j]);
       end;
      if bo=1 then ans:=ans+x1*(1<<(i-1))
              else begin
                    if x1=1 then ans:=ans+(1<<(i-1))
                            else if x2=1 then begin ans:=ans+(1<<(i-1));sum:=sum+(1<<(i-1)); end;
                   end;
     end;
  end;
 procedure print;
  begin
   writeln(ans);
   close(input);close(output);
  end;
 begin
  init;
  main;
  print;
 end.


【写的有漏洞的,欢迎路过大神吐槽】

  2017/2/13 18:59:00

  Ending.


  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值