zoukankan      html  css  js  c++  java
  • [codevs1026]逃跑的拉尔夫

    常规的宽搜,每个方向上都一路走到’X‘为止

    如果不加以判重,理论上是对的,但是会做大量无用的计算,要么超时要么数组越界,只能得30分

    不过,这里的判重并不是指每个点只能经过一次,而是指在一层搜索中,每个点只能经过一次,搜索下一层时,判重数组要清空

    程序如下:

    program ex1026;
    type node=record
           x,y,d:longint;
         end;
    var r,c,n,i,j,cen:longint;
        t:string;
        hash:array[0..51,0..51] of boolean;//判重数组
        map:array[0..51,0..51] of char;
        dir:array[1..3000] of longint;
        a:array[1..1000000] of node;//宽搜队列
    
    procedure bfs;
    var l,r,i:longint;
    begin
      l:=0;
      r:=1;
      while l<r do
      begin
        inc(l);
        if a[l].d<>cen then//如果进入下一层搜索判重数组就清空
        begin
          fillchar(hash,sizeof(hash),true);
          cen:=a[l].d;//层数加一
        end;
        case dir[a[l].d] of
          1://begin
            i:=1;
            while map[a[l].x-i,a[l].y]<>'X' do
            begin
              if a[l].d=n then//如果是最后一个方向,下一个点就变成’*begin
                map[a[l].x-i,a[l].y]:='*';
                inc(i);
              end
              else
                if hash[a[l].x-i,a[l].y] then
                begin
                  hash[a[l].x-i,a[l].y]:=false;
                  inc(r);
                  a[r].x:=a[l].x-i;
                  a[r].y:=a[l].y;
                  a[r].d:=a[l].d+1;
                  inc(i);
                end
                else
                  inc(i);
            end;
          end;
          2://begin
            i:=1;
            while map[a[l].x+i,a[l].y]<>'X' do
            begin
              if a[l].d=n then
              begin
                map[a[l].x+i,a[l].y]:='*';
                inc(i);
              end
              else
                if hash[a[l].x+i,a[l].y] then
                begin
                  hash[a[l].x+i,a[l].y]:=false;
                  inc(r);
                  a[r].x:=a[l].x+i;
                  a[r].y:=a[l].y;
                  a[r].d:=a[l].d+1;
                  inc(i);
                end
                else
                  inc(i);
            end;
          end;
          3://西
          begin
            i:=1;
            while map[a[l].x,a[l].y-i]<>'X' do
            begin
              if a[l].d=n then
              begin
                map[a[l].x,a[l].y-i]:='*';
                inc(i);
              end
              else
                if hash[a[l].x,a[l].y-i] then
                begin
                  hash[a[l].x,a[l].y-i]:=false;
                  inc(r);
                  a[r].x:=a[l].x;
                  a[r].y:=a[l].y-i;
                  a[r].d:=a[l].d+1;
                  inc(i);
                end
                else
                  inc(i);
            end;
          end;
          4://begin
            i:=1;
            while map[a[l].x,a[l].y+i]<>'X' do
            begin
              if a[l].d=n then
              begin
                map[a[l].x,a[l].y+i]:='*';
                inc(i);
              end
              else
                if hash[a[l].x,a[l].y+i] then
                begin
                  hash[a[l].x,a[l].y+i]:=false;
                  inc(r);
                  a[r].x:=a[l].x;
                  a[r].y:=a[l].y+i;
                  a[r].d:=a[l].d+1;
                  inc(i);
                end
                else
                  inc(i);
            end;
          end;
        end;
      end;
    end;
    
    begin
      cen:=0;
      readln(r,c);
      for i:=0 to r+1 do
        for j:=0 to c+1 do
          map[i,j]:='X';
      for i:=1 to r do
      begin
        for j:=1 to c do
        begin
          read(map[i,j]);
          if map[i,j]='*' then
          begin
            a[1].x:=i;
            a[1].y:=j;
            map[i,j]:='.';//起点变为’.’
            a[1].d:=1;//第1方向
          end;
        end;
        readln;
      end;
      readln(n);
      for i:=1 to n do
      begin
        readln(t);
        if t='NORTH' then dir[i]:=1;
        if t='SOUTH' then dir[i]:=2;
        if t='WEST' then dir[i]:=3;
        if t='EAST' then dir[i]:=4;
      end;
      bfs;
      for i:=1 to r do
      begin
        for j:=1 to c do
          write(map[i,j]);
        writeln;
      end;
    end.
  • 相关阅读:
    vue-element-admin实战 | 第二篇: 最小改动接入后台实现根据权限动态加载菜单
    设置git同时推送github和gitee远程仓库
    Spring Cloud实战 | 第一篇:Windows搭建Nacos服务
    winfrom 打开文件夹并定位到指定的文件
    winfrom 关于textbox回车事件有换行的问题
    winfrom切换账号功能
    解决winfrom最大化 窗体被任务栏挡住的问题
    winfrom解决控件闪烁
    winfrom防止程序多开
    c# 对象,IntPtr互转
  • 原文地址:https://www.cnblogs.com/victorslave/p/4798569.html
Copyright © 2011-2022 走看看