codevs1026

来源:互联网 发布:2016淘宝怎么注册 编辑:程序博客网 时间:2024/05/16 08:10

题目地址:http://codevs.cn/problem/1026/

分析:

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

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

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

代码:

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.


0 0