2023/03/28
進まないな。
30年?前頃は、駒が移動できるかを、只管、こんなコードを書いていた。
先手、後手も別にあったから、当然、自分でも理解出来なくなって、管理不能。
function TPieceList.IsMovableBishop(wx, wy, sx, sy: Integer): Boolean;
var
i: integer;
snx: integer;
sny: integer;
begin
if Abs(wx-sx) = Abs(wy-sy) then begin
Result := true;
if sy<wy then
sny := -1
else if sy > wy then
sny := 1
else sny := 0;
if sx<wx then
snx := -1
else if sx> wx then
snx := 1
else snx := 0;
for i := 1 to Abs(wx - sx)-1 do begin
if BoardPiece(sx-snx*i, sy - sny* i) <> nil then begin
result := false;
Break;
end;
end;
end
else Result := false;
end;
この頃書いていた、似たような判定をするコードは、普通駒と、線駒で、似たようなコード一つずつで済む。データは作らなくてならないが。
元ネタは、某ベトナム人が作った xiangqi の コードだ。BigBoardSizeを使い、 OB 判定で楽ができるのだった。
const
OB = -1;
box169: array[1..BigBoardSize] of integer =
(OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,
OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,
OB,OB, 1, 2, 3, 4, 5, 6, 7, 8, 9,OB,OB,
OB,OB,10,11,12,13,14,15,16,17,18,OB,OB,
OB,OB,19,20,21,22,23,24,25,26,27,OB,OB,
OB,OB,28,29,30,31,32,33,34,35,36,OB,OB,
OB,OB,37,38,39,40,41,42,43,44,45,OB,OB,
OB,OB,46,47,48,49,50,51,52,53,54,OB,OB,
OB,OB,55,56,57,58,59,60,61,62,63,OB,OB,
OB,OB,64,65,66,67,68,69,70,71,72,OB,OB,
OB,OB,73,74,75,76,77,78,79,80,81,OB,OB,
OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,
OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB,OB);
box81: array[1..BoardSize] of integer =
(29, 30, 31, 32, 33, 34, 35, 36, 37,
42, 43, 44, 45, 46, 47, 48, 49, 50,
55, 56, 57, 58, 59, 60, 61, 62, 63,
68, 69, 70, 71, 72, 73, 74, 75, 76,
81, 82, 83, 84, 85, 86, 87, 88, 89,
94, 95, 96, 97, 98, 99,100,101,102,
107,108,109,110,111,112,113,114,115,
120,121,122,123,124,125,126,127,128,
133,134,135,136,137,138,139,140,141);
// 単移動
MovabilitySimple: array[spGyoku..spTokin, 1..DIRECTIONMAX] of integer = (
(-14, -13, -12, -1, 1, 12, 13, 14), // 玉
( 0, 0, 0, 0, 0, 0, 0, 0), // 飛
( 0, 0, 0, 0, 0, 0, 0, 0), // 角
(-14, -13, -12, -1, 1, 13, 0, 0), // 金
(-14, -13, -12, 12, 14, 0, 0, 0), // 銀
(-27, -25, 0, 0, 0, 0, 0, 0), // 桂
( 0, 0, 0, 0, 0, 0, 0, 0), // 香
(-13, 0, 0, 0, 0, 0, 0, 0), // 歩
(-14, -12, 12, 14, 0, 0, 0, 0), // 龍
(-13, -1, 1, 13, 0, 0, 0, 0), // 馬
(-14, -13, -12, -1, 1, 13, 0, 0), // 成銀
(-14, -13, -12, -1, 1, 13, 0, 0), // 成桂
(-14, -13, -12, -1, 1, 13, 0, 0), // 成香
(-14, -13, -12, -1, 1, 13, 0, 0)); // と
// 複数移動 queen や nightrider の拡張を見込み 8方向
MovabilityLine: array[spGyoku..spTokin, 1..DIRECTIONMAX] of integer = (
( 0, 0, 0, 0, 0, 0, 0, 0),
(-13, -1, 1, 13, 0, 0, 0, 0),
(-14, -12, 12, 14, 0, 0, 0, 0),
( 0, 0, 0, 0, 0, 0, 0, 0),
( 0, 0, 0, 0, 0, 0, 0, 0),
( 0, 0, 0, 0, 0, 0, 0, 0),
(-13, 0, 0, 0, 0, 0, 0, 0),
( 0, 0, 0, 0, 0, 0, 0, 0),
(-13, -1, 1, 13, 0, 0, 0, 0),
(-14, -12, 12, 14, 0, 0, 0, 0),
( 0, 0, 0, 0, 0, 0, 0, 0),
( 0, 0, 0, 0, 0, 0, 0, 0),
( 0, 0, 0, 0, 0, 0, 0, 0),
( 0, 0, 0, 0, 0, 0, 0, 0)
);
procedure SetSimpleMove;
var
i : integer;
direction: integer;
begin
for i := 1 to DIRECTIONMAX do begin
direction := MovabilitySimple[sp, i]; // Simple
if direction <> 0 then begin
if ti = tiGote then
direction := 0 - direction;
target169 := ind169 + direction;
target81 := box169[target169];
SetTarget(target81, ti); // 返り値は使わない
end;
end;
end;
procedure SetLineMove;
var
i: integer;
direction: integer;
cnt: Boolean;
begin
for i := 1 to DIRECTIONMAX do begin
direction := MovabilityLine[sp, i]; // Line
if direction <> 0 then begin
if ti = tiGote then
direction := 0 - direction;
target169 := ind169 + direction; // 駒位置から
target81 := box169[target169];
cnt := SetTarget(target81, ti);
while cnt do begin
target169 := target169 + direction; // 動いた位置から
target81 := box169[target169];
cnt := SetTarget(target81, ti);
end;
end;
end;
end;