加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 大数据 > 正文

德尔福 – 连接4:检查获胜者

发布时间:2020-12-15 09:37:54 所属栏目:大数据 来源:网络整理
导读:在Delphi中,我有一个数组形式的Connect 4板表示(7列x 6行): TBoard = Array[1..7,1..6] of SmallInt;Board: TBoard; // instance ob TBoard 每个元素可以有三种不同的状态: 1 =球员1的棋子 0 =空 -1 =玩家2的棋子 现在我需要一个功能来检查是否有赢家或平
在Delphi中,我有一个数组形式的Connect 4板表示(7列x 6行):

TBoard = Array[1..7,1..6] of SmallInt;
Board: TBoard; // instance ob TBoard

每个元素可以有三种不同的状态:

> 1 =球员1的棋子
> 0 =空
> -1 =玩家2的棋子

现在我需要一个功能来检查是否有赢家或平局:

function CheckForWinner(): SmallInt;

…其中1是玩家1的胜利,0是平局,-1是玩家2的胜利,“nil”是尚未结束的游戏.

我的草案如下 – 分为两个单一功能:

function CheckForWinner(): SmallInt;
var playerToCheck: ShortInt;
    s,z: Byte;
    draw: Boolean;
begin
  draw := TRUE;
  for s := 1 to 7 do begin
    for z := 1 to 6 do begin
      if Board[s,z] = 0 then draw := FALSE; // if there are empty fields then it is no draw
    end;
  end;
  if draw then begin
    result := 0;
  end
  else begin
    playerToCheck := Board[lastPieceX,lastPieceY]; // only for last-moving player
    if searchRow(playerToCheck,+1,lastPieceX,lastPieceY) then // search right/left
      result := playerToCheck
    else if searchRow(playerToCheck,lastPieceY) then // search up/down
      result := playerToCheck
    else if searchRow(playerToCheck,lastPieceY) then // search right-down/left-up
      result := playerToCheck
    else if searchRow(playerToCheck,-1,lastPieceY) then // search right-up/left-down
      result := playerToCheck;
    else
      result := nil;
    end;
  end;
end;

function searchRow(player: SmallInt; sChange,zChange: ShortInt; startS,startZ: Byte): Boolean;
var inRow,s,z: SmallInt;
begin
  inRow := 0;
  s := startS;
  z := startZ;
  while (Board[s,z] = player) AND (inRow < 4) AND (s >= 1) AND (s <= 7) AND (z >= 1) AND (z <= 6) do begin
    s := s+sChange;
    z := z+zChange;
    inRow := inRow+1;
  end;
  s := startS-sChange;
  z := startZ-zChange;
  while (Board[s,z] = player) AND (inRow < 4) AND (s >= 1) AND (s <= 7) AND (z >= 1) AND (z <= 6) do begin
    s := s-sChange;
    z := z-zChange;
    inRow := inRow+1;
  end;
  if inRow = 4 then
    result := TRUE
  else
    result := FALSE;
end;

您如何看待这种方法?你有更好的(更快/更短)的解决方案吗?

非常感谢你!

解决方法

以与您相同的方式检查获胜者,只需少量代码.
我想你不需要检查所有字段来确定游戏是否完成.当你在游戏中放下一块时,只需增加一个计数器.如果计数器达到42并且还没有赢家,则该游戏是平局.

function CheckRow(x,y,xd,yd: Integer): Boolean;
var
  c: Integer;

  function RowLength(x,yd: Integer): Integer;
  begin
    Result := 0;
    repeat
      Inc(Result);
      Inc(x,xd);
      Inc(y,yd);
    until not ((x in [1..7]) and (y in [1..6]) and (Board[x,y] = c));
  end;

begin
  c := Board[x,y];

  Result := 4 <= RowLength(x,yd) + RowLength(x,xd*-1,yd*-1) - 1;
end;

function CheckForWinner(x,y: Integer): Integer;
begin
  Result := 0;
  if CheckRow(x,1) or CheckRow(x,1,1) or
     CheckRow(x,0) or CheckRow(x,-1) then
    Result := Board[x,y];
end;

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读