• NOIP2011解题报告Day1


    题目:

    https://files.cnblogs.com/lijianlin1995/NOIP2011%E6%8F%90%E9%AB%98%E7%BB%84Day1.pdf

            CLJ神犇的NOIP题解应该是最广为流的,但是神犇就是神犇,追求复杂度,方法很高端。所以我写一点能过就行的算法。RQNOJ提交通过了。

    铺地毯

            第一感觉二维线段树,发现只查询一个点,可以朴素。如果halt要注意文件操作。

    View Code
     1 type Tdt=record
     2       x,y,xl,yl:longint;
     3       end;
     4 var dt:array[1..10000] of Tdt;
     5     i,color,n,x,y:longint;
     6 begin
     7   readln(n);
     8   for i:=1 to n do
     9     with dt[i] do
    10       readln(x,y,xl,yl);
    11   readln(x,y);
    12   color:=-1;
    13   for i:=n downto 1 do
    14     if (x>=dt[i].x)and(x<=dt[i].x+dt[i].xl)and
    15        (y>=dt[i].y)and(y<=dt[i].y+dt[i].yl)
    16          then begin
    17               color:=i;
    18               break;
    19               end;
    20   writeln(color);
    21 end.

    旅馆

            考试的时候写的O(n^2)的算法,枚举左右端点,维护区间最小值,得分很低。

    把两个人的住宿位置看做一个闭区间的左右端点。一个合法的区间要求:

            I:含有一个点i满足ok[i]=1

            II:color[l]=color[r]

            求出合法的区间数即为答案。

            维护前缀和,count[i][j]为前1..i颜色j的数量,用指针f记录最后出现ok[i]=1的i。如果一个区间可以由靠左的ok[i]满足,一定可以由区间内靠右的ok[i]满足,不妨让最靠右的ok[i]满足。从1到n枚举区间右端点。通过前缀和计算左端点的方案数。

    1.ok[i]=1 可以在i喝咖啡,右边的人可以住的位置是count[i-1][color[i]],f更改为i;(条件I被右端点满足)

    2.ok[i]=0 在f喝咖啡,inc(ans,count[f][color[i]]);(条件II被f满足)

    View Code
     1 program hotel;
     2 const maxn=200000;
     3 var color:array[0..maxn] of byte;
     4     ok:array[0..maxn] of boolean;
     5     n,p,k,i,f,t:longint;
     6     count:array[0..maxn,0..50] of longint;
     7     ans:int64=0;
     8 begin
     9 fillchar(count,sizeof(count),0);
    10 readln(n,k,p);f:=0;
    11 for i:=1 to n do
    12   begin
    13   readln(color[i],t);
    14   if t<=p then ok[i]:=true
    15           else ok[i]:=false;
    16   count[i]:=count[i-1];
    17   inc(count[i][color[i]]);
    18   end;
    19 for i:=1 to n do
    20   begin
    21   if ok[i] then f:=i-1;
    22   inc(ans,count[f][color[i]]);
    23   if ok[i] then inc(f);
    24   end;
    25 writeln(ans);
    26 end.

     

    Mayan游戏

            DFS,复杂度5*7^5=52521875不大,加上下落和清除,期望得分30—100。要注意横纵坐标和行列的关系。几个剪枝和要注意的问题:

    1.如果一个方块左边有方块,那左边的方块右移比右边的方块左移优。
    2.方块移动以后没有处理下落会WA40
    3.读数据出问题,如果一行有7个方块,会有8个数字(最后一个是0),WA20
    4.处理消除后的方块下落时下标越界。
    5.忘记向左移动 WA60
            2的处理写疵了,索性用了消除后的下落过程。

            考试跟KAC大神同考场,考完大神叹息“我写了3KB”

    View Code
      1 program mayan;
      2 TYPE Tmap=array[0..4,0..7] of shortint;
      3 var n,i,j,step:longint;
      4     a:Tmap;
      5     t:shortint;
      6     x,y,g:array[1..5] of integer;
      7 procedure swap(var a,b:shortint);
      8 var t:shortint;begin t:=a;a:=b;b:=t;end;
      9 procedure print;
     10           var i:longint;
     11           begin
     12           for i:=1 to step do
     13             writeln(x[i],' ',y[i],' ',g[i]);
     14           halt;
     15           end;
     16 function  clean(var map:Tmap):boolean;
     17           var i,j,k:integer;
     18               finish:boolean;
     19               f:array[0..4,0..6] of boolean;
     20           begin
     21           clean:=true;
     22           fillchar(f,sizeof(f),false);
     23           for i:=0 to 4 do
     24             for j:=0 to 6 do
     25               if map[i][j]<>0 then
     26                 begin
     27                 if(i in [1..3])and
     28                   (map[i][j]=map[i-1][j])and
     29                   (map[i][j]=map[i+1][j])
     30                   then begin
     31                        f[i][j]:=true;
     32                        f[i-1][j]:=true;
     33                        f[i+1][j]:=true;
     34                        end;
     35                 if(j in [1..5])and
     36                   (map[i][j]=map[i][j+1])and
     37                   (map[i][j]=map[i][j-1])
     38                   then begin
     39                        f[i][j]:=true;
     40                        f[i][j+1]:=true;
     41                        f[i][j-1]:=true;
     42                        end;
     43                 end;
     44           for i:=0 to 4 do
     45             for j:=6 downto 0 do
     46               if f[i][j] then
     47                 begin
     48                 clean:=false;
     49                 map[i][j]:=0;
     50                 end;
     51           end;
     52 procedure fall(var map:Tmap);
     53           var i,j,k:integer;
     54           begin
     55           for i:=0 to 4 do
     56             for j:=1 to 6 do
     57               if(map[i][j]<>0)and(map[i][j-1]=0)
     58                 then begin
     59                      k:=j;
     60                      while(k>0)and(map[i][k-1]=0)do dec(k);
     61                      map[i][k]:=map[i][j];map[i][j]:=0;
     62                      end;
     63           end;
     64 function  finish(map:Tmap):boolean;
     65           var i,j:longint;
     66           begin
     67           for i:=0 to 4 do
     68             for j:=0 to 6 do
     69               if map[i][j]<>0
     70                 then exit(false);
     71           exit(true);
     72           end;
     73 procedure DFS(map:Tmap);
     74           var i,j,k:integer;
     75           begin
     76           if step<>0 then swap(map[x[step]][y[step]],map[x[step]+g[step]][y[step]]);
     77           repeat fall(map) until clean(map);
     78           if step=n then if finish(map)then print
     79                                        else exit;
     80           for i:=0 to 4 do
     81             for j:=0 to 6 do
     82               begin
     83               if map[i][j]<>0
     84                 then begin
     85                      inc(step);
     86                      if(i>0)and(map[i-1][j]=0)
     87                        then begin
     88                             x[step]:=i;
     89                             y[step]:=j;
     90                             g[step]:=-1;
     91                             DFS(map);
     92                             end;
     93                      if(i<4)
     94                        then begin
     95                             x[step]:=i;
     96                             y[step]:=j;
     97                             g[step]:=1;
     98                             DFS(map);
     99                             end;
    100                      dec(step);
    101                      end;
    102               end;
    103           end;
    104 begin
    105 readln(n);step:=0;
    106 for i:=0 to 4 do
    107   begin
    108   t:=-1;
    109   repeat
    110     inc(t);
    111     read(a[i][t]);
    112   until a[i][t]=0;
    113   end;
    114 DFS(a);
    115 writeln('-1');
    116 end.
  • 相关阅读:
    解决关于 在android studio 出现的 DELETE_FAILED_INTERNAL_ERROR Error while Installing APK 问题
    oracle 时间日期常用语句及函数
    微信小程序 网络请求之re.request 和那些坑
    微信小程序 网络请求之设置合法域名
    开发中常用js记录(三)
    oracle 锁表 and 解锁
    微信小程序 JS动态修改样式
    微信小程序 获得用户输入内容
    微信小程序 引用其他js里的方法
    微信JSAPI支付回调
  • 原文地址:https://www.cnblogs.com/lijianlin1995/p/2634394.html
Copyright © 2020-2023  润新知