zoukankan      html  css  js  c++  java
  • bzoj2165

    类似于bzoj1706,考虑到楼层是等价的
    我们令f[p,i,j]为用了2^p次电梯,从房间i到j最多上升了多少层
    然后从2^p很容易推到2^(p+1),类似于floyd的转移即可
    下面我们要用最小的电梯次数
    可以考虑每一个数都有其唯一的而二进制拆分
    从p到0贪心得到一个最接近上了m层的次数ans,ans+1即为答案

     1 const inf=-1000000000000000000;
     2 var f:array[0..64,0..100,0..100] of int64;
     3     w,v:array[0..100] of int64;
     4     e,t,i,j,k,n,p,h:longint;
     5     fl:boolean;
     6     ans,m:int64;
     7 
     8 function max(a,b:int64):int64;
     9   begin
    10     if a>b then exit(a) else exit(b);
    11   end;
    12 
    13 function check(p:longint):boolean;
    14   var i:longint;
    15   begin
    16     for i:=1 to n do
    17       if f[p,1,i]>=m then exit(true);
    18     exit(false);
    19   end;
    20 
    21 begin
    22   readln(t);
    23   for e:=1 to t do
    24   begin
    25     readln(n,m);
    26     for i:=1 to n do
    27     begin
    28       for j:=1 to n do
    29       begin
    30         read(f[0,i,j]);
    31         if f[0,i,j]=0 then f[0,i,j]:=inf;
    32       end;
    33       readln;
    34     end;
    35     p:=0;
    36     while true do
    37     begin
    38       for i:=1 to n do
    39         for j:=1 to n do
    40         begin
    41           f[p+1,i,j]:=inf;
    42           for k:=1 to n do
    43           begin
    44             f[p+1,i,j]:=max(f[p+1,i,j],f[p,i,k]+f[p,k,j]);
    45             if f[p+1,i,j]>m then  
    46             begin
    47               f[p+1,i,j]:=m;
    48               break;
    49             end;
    50           end;
    51         end;
    52       if not check(p+1) then inc(p)  //出现了从房间1到某房间最大上升层数大于m就不用往下穷举了
    53       else break;
    54     end;
    55     w[1]:=0;
    56     for i:=2 to n do
    57       w[i]:=inf;  //w表示在当前所用次数下到i号房间最大上升层数层数
    58     ans:=0;
    59     for h:=p downto 0 do
    60     begin
    61       fl:=true;
    62       for i:=1 to n do
    63       begin
    64         for j:=1 to n do
    65           if w[i]+f[h,i,j]>=m then
    66           begin
    67             fl:=false;
    68             break;
    69           end;
    70         if not fl then break;
    71       end;
    72       if fl then
    73       begin
    74         ans:=ans+int64(1) shl h;
    75         for i:=1 to n do
    76           v[i]:=inf;
    77         for i:=1 to n do
    78           for j:=1 to n do
    79             v[j]:=max(v[j],w[i]+f[h,i,j]);
    80         w:=v;
    81       end;
    82     end;
    83     writeln(ans+1);
    84   end;
    85 end.
    View Code
  • 相关阅读:
    企业应用的互联网化(2010年2月)
    Flex的危局,还是HTML5的盛宴?
    在MBP上自由切换显卡
    Django的中文编码问题
    Jenkins+Maven+SVN快速搭建持续集成环境(转)
    解决 phpmyadmin #2002 无法登录 MySQL 服务器
    Spring框架中获得DataSource对象的方法(转)
    jetty 源代码地址
    eclipse中js文件报missing semicolon
    等额本息贷款月付款额的推导公式
  • 原文地址:https://www.cnblogs.com/phile/p/4473025.html
Copyright © 2011-2022 走看看