js-chess-engine 1.0.3 → 2.0.1-rc.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (104) hide show
  1. package/README.md +586 -205
  2. package/dist/adapters/APIAdapter.d.ts +88 -0
  3. package/dist/adapters/APIAdapter.d.ts.map +1 -0
  4. package/dist/adapters/APIAdapter.js +225 -0
  5. package/dist/adapters/APIAdapter.js.map +1 -0
  6. package/dist/ai/AIEngine.d.ts +42 -0
  7. package/dist/ai/AIEngine.d.ts.map +1 -0
  8. package/dist/ai/AIEngine.js +62 -0
  9. package/dist/ai/AIEngine.js.map +1 -0
  10. package/dist/ai/Evaluator.d.ts +48 -0
  11. package/dist/ai/Evaluator.d.ts.map +1 -0
  12. package/dist/ai/Evaluator.js +248 -0
  13. package/dist/ai/Evaluator.js.map +1 -0
  14. package/dist/ai/MoveOrdering.d.ts +60 -0
  15. package/dist/ai/MoveOrdering.d.ts.map +1 -0
  16. package/dist/ai/MoveOrdering.js +173 -0
  17. package/dist/ai/MoveOrdering.js.map +1 -0
  18. package/dist/ai/Search.d.ts +62 -0
  19. package/dist/ai/Search.d.ts.map +1 -0
  20. package/dist/ai/Search.js +340 -0
  21. package/dist/ai/Search.js.map +1 -0
  22. package/dist/ai/TranspositionTable.d.ts +100 -0
  23. package/dist/ai/TranspositionTable.d.ts.map +1 -0
  24. package/dist/ai/TranspositionTable.js +176 -0
  25. package/dist/ai/TranspositionTable.js.map +1 -0
  26. package/dist/core/AttackDetector.d.ts +52 -0
  27. package/dist/core/AttackDetector.d.ts.map +1 -0
  28. package/dist/core/AttackDetector.js +387 -0
  29. package/dist/core/AttackDetector.js.map +1 -0
  30. package/dist/core/Board.d.ts +109 -0
  31. package/dist/core/Board.d.ts.map +1 -0
  32. package/dist/core/Board.js +410 -0
  33. package/dist/core/Board.js.map +1 -0
  34. package/dist/core/MoveGenerator.d.ts +48 -0
  35. package/dist/core/MoveGenerator.d.ts.map +1 -0
  36. package/dist/core/MoveGenerator.js +678 -0
  37. package/dist/core/MoveGenerator.js.map +1 -0
  38. package/dist/core/Position.d.ts +135 -0
  39. package/dist/core/Position.d.ts.map +1 -0
  40. package/dist/core/Position.js +351 -0
  41. package/dist/core/Position.js.map +1 -0
  42. package/dist/core/index.d.ts +9 -0
  43. package/dist/core/index.d.ts.map +1 -0
  44. package/dist/core/index.js +25 -0
  45. package/dist/core/index.js.map +1 -0
  46. package/dist/core/zobrist.d.ts +93 -0
  47. package/dist/core/zobrist.d.ts.map +1 -0
  48. package/dist/core/zobrist.js +273 -0
  49. package/dist/core/zobrist.js.map +1 -0
  50. package/dist/index.d.ts +154 -0
  51. package/dist/index.d.ts.map +1 -0
  52. package/dist/index.js +353 -0
  53. package/dist/index.js.map +1 -0
  54. package/dist/types/ai.types.d.ts +97 -0
  55. package/dist/types/ai.types.d.ts.map +1 -0
  56. package/dist/types/ai.types.js +17 -0
  57. package/dist/types/ai.types.js.map +1 -0
  58. package/dist/types/board.types.d.ts +140 -0
  59. package/dist/types/board.types.d.ts.map +1 -0
  60. package/dist/types/board.types.js +34 -0
  61. package/dist/types/board.types.js.map +1 -0
  62. package/dist/types/index.d.ts +7 -0
  63. package/dist/types/index.d.ts.map +1 -0
  64. package/dist/types/index.js +26 -0
  65. package/dist/types/index.js.map +1 -0
  66. package/dist/types/move.types.d.ts +70 -0
  67. package/dist/types/move.types.d.ts.map +1 -0
  68. package/dist/types/move.types.js +53 -0
  69. package/dist/types/move.types.js.map +1 -0
  70. package/dist/utils/constants.d.ts +123 -0
  71. package/dist/utils/constants.d.ts.map +1 -0
  72. package/dist/utils/constants.js +259 -0
  73. package/dist/utils/constants.js.map +1 -0
  74. package/dist/utils/conversion.d.ts +152 -0
  75. package/dist/utils/conversion.d.ts.map +1 -0
  76. package/dist/utils/conversion.js +288 -0
  77. package/dist/utils/conversion.js.map +1 -0
  78. package/dist/utils/environment.d.ts +33 -0
  79. package/dist/utils/environment.d.ts.map +1 -0
  80. package/dist/utils/environment.js +71 -0
  81. package/dist/utils/environment.js.map +1 -0
  82. package/dist/utils/fen.d.ts +28 -0
  83. package/dist/utils/fen.d.ts.map +1 -0
  84. package/dist/utils/fen.js +203 -0
  85. package/dist/utils/fen.js.map +1 -0
  86. package/package.json +25 -29
  87. package/.eslintrc.json +0 -16
  88. package/.github/workflows/main.yml +0 -20
  89. package/.nvmrc +0 -1
  90. package/CHANGELOG.md +0 -597
  91. package/dist/js-chess-engine.js +0 -1
  92. package/example/aiMatch.mjs +0 -21
  93. package/example/console.mjs +0 -37
  94. package/example/server.mjs +0 -27
  95. package/lib/Board.mjs +0 -946
  96. package/lib/const/board.mjs +0 -838
  97. package/lib/js-chess-engine.mjs +0 -99
  98. package/lib/utils.mjs +0 -154
  99. package/test/.eslintrc.json +0 -11
  100. package/test/ai.test.mjs +0 -132
  101. package/test/badge.svg +0 -1
  102. package/test/importExport.mjs +0 -108
  103. package/test/moves.test.mjs +0 -798
  104. package/webpack.config.js +0 -12
@@ -0,0 +1,248 @@
1
+ "use strict";
2
+ /**
3
+ * Position evaluator for js-chess-engine v2
4
+ *
5
+ * Evaluates chess positions using material count and piece-square tables.
6
+ * Based on v1 implementation for API parity.
7
+ */
8
+ Object.defineProperty(exports, "__esModule", { value: true });
9
+ exports.Evaluator = exports.SCORE_MAX = exports.SCORE_MIN = void 0;
10
+ const types_1 = require("../types");
11
+ // ==================== Constants ====================
12
+ /**
13
+ * Material values (base unit = 1 pawn)
14
+ */
15
+ const PIECE_VALUES = {
16
+ [types_1.Piece.WHITE_PAWN]: 1,
17
+ [types_1.Piece.WHITE_KNIGHT]: 3,
18
+ [types_1.Piece.WHITE_BISHOP]: 3,
19
+ [types_1.Piece.WHITE_ROOK]: 5,
20
+ [types_1.Piece.WHITE_QUEEN]: 9,
21
+ [types_1.Piece.WHITE_KING]: 10,
22
+ [types_1.Piece.BLACK_PAWN]: 1,
23
+ [types_1.Piece.BLACK_KNIGHT]: 3,
24
+ [types_1.Piece.BLACK_BISHOP]: 3,
25
+ [types_1.Piece.BLACK_ROOK]: 5,
26
+ [types_1.Piece.BLACK_QUEEN]: 9,
27
+ [types_1.Piece.BLACK_KING]: 10,
28
+ };
29
+ /**
30
+ * Score bounds for special positions
31
+ */
32
+ exports.SCORE_MIN = -1000;
33
+ exports.SCORE_MAX = 1000;
34
+ /**
35
+ * Material score multiplier (v1 compatibility)
36
+ */
37
+ const PIECE_VALUE_MULTIPLIER = 10;
38
+ /**
39
+ * Piece-square table multiplier (v1 compatibility)
40
+ */
41
+ const PST_MULTIPLIER = 0.5;
42
+ // ==================== Piece-Square Tables ====================
43
+ // From white's perspective (rank 0 = rank 1, rank 7 = rank 8)
44
+ /**
45
+ * Pawn piece-square table (white perspective)
46
+ */
47
+ const PAWN_PST = [
48
+ [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0],
49
+ [5.0, 5.0, 5.0, 5.0, 5.0, 5.0, 5.0, 5.0],
50
+ [1.0, 1.0, 2.0, 3.0, 3.0, 2.0, 1.0, 1.0],
51
+ [0.5, 0.5, 1.0, 2.5, 2.5, 1.0, 0.5, 0.5],
52
+ [0.0, 0.0, 0.0, 2.0, 2.0, 0.0, 0.0, 0.0],
53
+ [0.5, 0.0, 1.0, 0.0, 0.0, 1.0, 0.0, 0.5],
54
+ [0.5, 0.0, 0.0, -2.0, -2.0, 0.0, 0.0, 0.5],
55
+ [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0],
56
+ ];
57
+ /**
58
+ * Knight piece-square table
59
+ */
60
+ const KNIGHT_PST = [
61
+ [-4.0, -3.0, -2.0, -2.0, -2.0, -2.0, -3.0, -4.0],
62
+ [-3.0, -2.0, 0.0, 0.0, 0.0, 0.0, -2.0, -3.0],
63
+ [-2.0, 0.0, 1.0, 1.5, 1.5, 1.0, 0.0, -2.0],
64
+ [-2.0, 0.5, 1.5, 2.0, 2.0, 1.5, 0.5, -2.0],
65
+ [-2.0, 0.0, 1.5, 2.0, 2.0, 1.5, 0.0, -2.0],
66
+ [-2.0, 0.5, 1.0, 1.5, 1.5, 1.0, 0.5, -2.0],
67
+ [-3.0, -2.0, 0.0, 0.5, 0.5, 0.0, -2.0, -3.0],
68
+ [-4.0, -3.0, -2.0, -2.0, -2.0, -2.0, -3.0, -4.0],
69
+ ];
70
+ /**
71
+ * Bishop piece-square table
72
+ */
73
+ const BISHOP_PST = [
74
+ [-2.0, -1.0, -1.0, -1.0, -1.0, -1.0, -1.0, -2.0],
75
+ [-1.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, -1.0],
76
+ [-1.0, 0.0, 0.5, 1.0, 1.0, 0.5, 0.0, -1.0],
77
+ [-1.0, 0.5, 0.5, 1.0, 1.0, 0.5, 0.5, -1.0],
78
+ [-1.0, 0.0, 1.0, 1.0, 1.0, 1.0, 0.0, -1.0],
79
+ [-1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, -1.0],
80
+ [-1.0, 0.5, 0.0, 0.0, 0.0, 0.0, 0.5, -1.0],
81
+ [-2.0, -1.0, -1.0, -1.0, -1.0, -1.0, -1.0, -2.0],
82
+ ];
83
+ /**
84
+ * Rook piece-square table
85
+ */
86
+ const ROOK_PST = [
87
+ [0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0],
88
+ [0.5, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 0.5],
89
+ [-0.5, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, -0.5],
90
+ [-0.5, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, -0.5],
91
+ [-0.5, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, -0.5],
92
+ [-0.5, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, -0.5],
93
+ [-0.5, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, -0.5],
94
+ [0.0, 0.0, 0.0, 0.5, 0.5, 0.0, 0.0, 0.0],
95
+ ];
96
+ /**
97
+ * Queen piece-square table
98
+ */
99
+ const QUEEN_PST = [
100
+ [-2.0, -1.0, -1.0, -0.5, -0.5, -1.0, -1.0, -2.0],
101
+ [-1.0, 0.0, 0.0, 0.0, 0.0, 0.0, 0.0, -1.0],
102
+ [-1.0, 0.0, 0.5, 0.5, 0.5, 0.5, 0.0, -1.0],
103
+ [-0.5, 0.0, 0.5, 0.5, 0.5, 0.5, 0.0, -0.5],
104
+ [0.0, 0.0, 0.5, 0.5, 0.5, 0.5, 0.0, -0.5],
105
+ [-1.0, 0.5, 0.5, 0.5, 0.5, 0.5, 0.0, -1.0],
106
+ [-1.0, 0.0, 0.5, 0.0, 0.0, 0.0, 0.0, -1.0],
107
+ [-2.0, -1.0, -1.0, -0.5, -0.5, -1.0, -1.0, -2.0],
108
+ ];
109
+ /**
110
+ * King piece-square table (middlegame)
111
+ */
112
+ const KING_PST = [
113
+ [-3.0, -4.0, -4.0, -5.0, -5.0, -4.0, -4.0, -3.0],
114
+ [-3.0, -4.0, -4.0, -5.0, -5.0, -4.0, -4.0, -3.0],
115
+ [-3.0, -4.0, -4.0, -5.0, -5.0, -4.0, -4.0, -3.0],
116
+ [-3.0, -4.0, -4.0, -5.0, -5.0, -4.0, -4.0, -3.0],
117
+ [-2.0, -3.0, -3.0, -4.0, -4.0, -3.0, -3.0, -2.0],
118
+ [-1.0, -2.0, -2.0, -2.0, -2.0, -2.0, -2.0, -1.0],
119
+ [2.0, 2.0, 0.0, 0.0, 0.0, 0.0, 2.0, 2.0],
120
+ [2.0, 3.0, 1.0, 0.0, 0.0, 1.0, 3.0, 2.0],
121
+ ];
122
+ /**
123
+ * Piece-square table map
124
+ * White pieces use tables as-is, black pieces use vertically flipped tables
125
+ */
126
+ const PST_MAP = {
127
+ [types_1.Piece.WHITE_PAWN]: reverseTable(PAWN_PST),
128
+ [types_1.Piece.BLACK_PAWN]: PAWN_PST,
129
+ [types_1.Piece.WHITE_KNIGHT]: reverseTable(KNIGHT_PST),
130
+ [types_1.Piece.BLACK_KNIGHT]: KNIGHT_PST,
131
+ [types_1.Piece.WHITE_BISHOP]: reverseTable(BISHOP_PST),
132
+ [types_1.Piece.BLACK_BISHOP]: BISHOP_PST,
133
+ [types_1.Piece.WHITE_ROOK]: reverseTable(ROOK_PST),
134
+ [types_1.Piece.BLACK_ROOK]: ROOK_PST,
135
+ [types_1.Piece.WHITE_QUEEN]: reverseTable(QUEEN_PST),
136
+ [types_1.Piece.BLACK_QUEEN]: QUEEN_PST,
137
+ [types_1.Piece.WHITE_KING]: reverseTable(KING_PST),
138
+ [types_1.Piece.BLACK_KING]: KING_PST,
139
+ };
140
+ /**
141
+ * Reverse table vertically (for white pieces)
142
+ */
143
+ function reverseTable(table) {
144
+ return table.slice().reverse();
145
+ }
146
+ // ==================== Evaluator Class ====================
147
+ class Evaluator {
148
+ /**
149
+ * Evaluate a position from the perspective of the specified color
150
+ *
151
+ * @param board - Board to evaluate
152
+ * @param playerColor - Color to evaluate for (positive = good for this color)
153
+ * @param depth - Current search depth (used for mate scoring)
154
+ * @returns Score in centipawns (positive = good for playerColor)
155
+ */
156
+ static evaluate(board, playerColor, depth = 0) {
157
+ // Check for checkmate
158
+ if (board.isCheckmate) {
159
+ if (board.turn === playerColor) {
160
+ // We're in checkmate - very bad
161
+ return exports.SCORE_MIN + depth; // Prefer longer mates (from opponent's perspective)
162
+ }
163
+ else {
164
+ // Opponent is in checkmate - very good
165
+ return exports.SCORE_MAX - depth; // Prefer shorter mates
166
+ }
167
+ }
168
+ // Check for stalemate (draw)
169
+ if (board.isStalemate) {
170
+ return 0; // Draw is neutral
171
+ }
172
+ // Material + piece-square tables
173
+ const materialScore = this.evaluateMaterial(board, playerColor);
174
+ const positionalScore = this.evaluatePieceSquareTables(board, playerColor);
175
+ return materialScore + positionalScore;
176
+ }
177
+ /**
178
+ * Evaluate material balance
179
+ *
180
+ * @param board - Board to evaluate
181
+ * @param playerColor - Color to evaluate for
182
+ * @returns Material score
183
+ */
184
+ static evaluateMaterial(board, playerColor) {
185
+ let score = 0;
186
+ for (let square = 0; square < 64; square++) {
187
+ const piece = board.mailbox[square];
188
+ if (piece === types_1.Piece.EMPTY)
189
+ continue;
190
+ const pieceValue = PIECE_VALUES[piece] * PIECE_VALUE_MULTIPLIER;
191
+ const pieceColor = piece <= types_1.Piece.WHITE_KING ? types_1.InternalColor.WHITE : types_1.InternalColor.BLACK;
192
+ if (pieceColor === playerColor) {
193
+ score += pieceValue;
194
+ }
195
+ else {
196
+ score -= pieceValue;
197
+ }
198
+ }
199
+ return score;
200
+ }
201
+ /**
202
+ * Evaluate piece-square table bonuses
203
+ *
204
+ * @param board - Board to evaluate
205
+ * @param playerColor - Color to evaluate for
206
+ * @returns Positional score
207
+ */
208
+ static evaluatePieceSquareTables(board, playerColor) {
209
+ let score = 0;
210
+ for (let square = 0; square < 64; square++) {
211
+ const piece = board.mailbox[square];
212
+ if (piece === types_1.Piece.EMPTY)
213
+ continue;
214
+ const table = PST_MAP[piece];
215
+ if (!table)
216
+ continue;
217
+ const rank = Math.floor(square / 8);
218
+ const file = square % 8;
219
+ const tableValue = table[rank][file] * PST_MULTIPLIER;
220
+ const pieceColor = piece <= types_1.Piece.WHITE_KING ? types_1.InternalColor.WHITE : types_1.InternalColor.BLACK;
221
+ if (pieceColor === playerColor) {
222
+ score += tableValue;
223
+ }
224
+ else {
225
+ score -= tableValue;
226
+ }
227
+ }
228
+ return score;
229
+ }
230
+ /**
231
+ * Get total material value on the board (used for endgame detection)
232
+ *
233
+ * @param board - Board to evaluate
234
+ * @returns Total material value
235
+ */
236
+ static getTotalMaterialValue(board) {
237
+ let total = 0;
238
+ for (let square = 0; square < 64; square++) {
239
+ const piece = board.mailbox[square];
240
+ if (piece === types_1.Piece.EMPTY)
241
+ continue;
242
+ total += PIECE_VALUES[piece];
243
+ }
244
+ return total;
245
+ }
246
+ }
247
+ exports.Evaluator = Evaluator;
248
+ //# sourceMappingURL=Evaluator.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Evaluator.js","sourceRoot":"","sources":["../../src/ai/Evaluator.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,60 @@
1
+ /**
2
+ * Move ordering for js-chess-engine v2
3
+ *
4
+ * Orders moves to improve alpha-beta pruning efficiency.
5
+ * Better move ordering = more cutoffs = faster search.
6
+ */
7
+ import { InternalMove } from '../types';
8
+ /**
9
+ * Killer moves storage
10
+ * Stores moves that caused beta cutoffs at each ply
11
+ */
12
+ export declare class KillerMoves {
13
+ private killers;
14
+ private maxPly;
15
+ constructor();
16
+ /**
17
+ * Store a killer move
18
+ *
19
+ * @param move - Move that caused beta cutoff
20
+ * @param ply - Current ply
21
+ */
22
+ store(move: InternalMove, ply: number): void;
23
+ /**
24
+ * Check if a move is a killer move
25
+ *
26
+ * @param move - Move to check
27
+ * @param ply - Current ply
28
+ * @returns true if killer move
29
+ */
30
+ isKiller(move: InternalMove, ply: number): boolean;
31
+ /**
32
+ * Clear all killer moves
33
+ */
34
+ clear(): void;
35
+ /**
36
+ * Check if two moves are the same
37
+ */
38
+ private isSameMove;
39
+ }
40
+ /**
41
+ * Score a move for ordering
42
+ *
43
+ * @param move - Move to score
44
+ * @param pvMove - PV move from transposition table (if any)
45
+ * @param killerMoves - Killer moves instance
46
+ * @param ply - Current ply
47
+ * @returns Move score (higher = better)
48
+ */
49
+ export declare function scoreMove(move: InternalMove, pvMove: InternalMove | null, killerMoves: KillerMoves | null, ply: number): number;
50
+ /**
51
+ * Order moves for search
52
+ *
53
+ * @param moves - Moves to order
54
+ * @param pvMove - PV move from transposition table (if any)
55
+ * @param killerMoves - Killer moves instance
56
+ * @param ply - Current ply
57
+ * @returns Ordered moves (best first)
58
+ */
59
+ export declare function orderMoves(moves: InternalMove[], pvMove?: InternalMove | null, killerMoves?: KillerMoves | null, ply?: number): InternalMove[];
60
+ //# sourceMappingURL=MoveOrdering.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"MoveOrdering.d.ts","sourceRoot":"","sources":["../../src/ai/MoveOrdering.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAAE,YAAY,EAAmB,MAAM,UAAU,CAAC;AA8BzD;;;GAGG;AACH,qBAAa,WAAW;IACpB,OAAO,CAAC,OAAO,CAA4B;IAC3C,OAAO,CAAC,MAAM,CAAc;;IAO5B;;;;;OAKG;IACH,KAAK,CAAC,IAAI,EAAE,YAAY,EAAE,GAAG,EAAE,MAAM,GAAG,IAAI;IAgB5C;;;;;;OAMG;IACH,QAAQ,CAAC,IAAI,EAAE,YAAY,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO;IAOlD;;OAEG;IACH,KAAK,IAAI,IAAI;IAIb;;OAEG;IACH,OAAO,CAAC,UAAU;CAIrB;AAkBD;;;;;;;;GAQG;AACH,wBAAgB,SAAS,CACrB,IAAI,EAAE,YAAY,EAClB,MAAM,EAAE,YAAY,GAAG,IAAI,EAC3B,WAAW,EAAE,WAAW,GAAG,IAAI,EAC/B,GAAG,EAAE,MAAM,GACZ,MAAM,CAuCR;AAED;;;;;;;;GAQG;AACH,wBAAgB,UAAU,CACtB,KAAK,EAAE,YAAY,EAAE,EACrB,MAAM,GAAE,YAAY,GAAG,IAAW,EAClC,WAAW,GAAE,WAAW,GAAG,IAAW,EACtC,GAAG,GAAE,MAAU,GAChB,YAAY,EAAE,CAYhB"}
@@ -0,0 +1,173 @@
1
+ "use strict";
2
+ /**
3
+ * Move ordering for js-chess-engine v2
4
+ *
5
+ * Orders moves to improve alpha-beta pruning efficiency.
6
+ * Better move ordering = more cutoffs = faster search.
7
+ */
8
+ Object.defineProperty(exports, "__esModule", { value: true });
9
+ exports.KillerMoves = void 0;
10
+ exports.scoreMove = scoreMove;
11
+ exports.orderMoves = orderMoves;
12
+ const types_1 = require("../types");
13
+ /**
14
+ * Piece values for MVV-LVA (Most Valuable Victim - Least Valuable Attacker)
15
+ */
16
+ const MVV_LVA_VALUES = {
17
+ [types_1.Piece.EMPTY]: 0,
18
+ [types_1.Piece.WHITE_PAWN]: 1,
19
+ [types_1.Piece.BLACK_PAWN]: 1,
20
+ [types_1.Piece.WHITE_KNIGHT]: 3,
21
+ [types_1.Piece.BLACK_KNIGHT]: 3,
22
+ [types_1.Piece.WHITE_BISHOP]: 3,
23
+ [types_1.Piece.BLACK_BISHOP]: 3,
24
+ [types_1.Piece.WHITE_ROOK]: 5,
25
+ [types_1.Piece.BLACK_ROOK]: 5,
26
+ [types_1.Piece.WHITE_QUEEN]: 9,
27
+ [types_1.Piece.BLACK_QUEEN]: 9,
28
+ [types_1.Piece.WHITE_KING]: 10,
29
+ [types_1.Piece.BLACK_KING]: 10,
30
+ };
31
+ /**
32
+ * Move ordering scores
33
+ */
34
+ const SCORE_PV_MOVE = 1000000; // PV move (from transposition table)
35
+ const SCORE_WINNING_CAPTURE = 900000; // Captures with positive SEE
36
+ const SCORE_QUEEN_PROMOTION = 800000; // Queen promotion
37
+ const SCORE_KILLER_MOVE = 700000; // Killer move
38
+ const SCORE_LOSING_CAPTURE = -100000; // Captures with negative SEE (bad)
39
+ /**
40
+ * Killer moves storage
41
+ * Stores moves that caused beta cutoffs at each ply
42
+ */
43
+ class KillerMoves {
44
+ killers;
45
+ maxPly = 64;
46
+ constructor() {
47
+ // Store 2 killer moves per ply
48
+ this.killers = Array.from({ length: this.maxPly }, () => [null, null]);
49
+ }
50
+ /**
51
+ * Store a killer move
52
+ *
53
+ * @param move - Move that caused beta cutoff
54
+ * @param ply - Current ply
55
+ */
56
+ store(move, ply) {
57
+ if (ply >= this.maxPly)
58
+ return;
59
+ // Don't store captures as killers (they're ordered separately)
60
+ if (move.flags & types_1.MoveFlag.CAPTURE)
61
+ return;
62
+ const moves = this.killers[ply];
63
+ // Don't duplicate
64
+ if (this.isSameMove(moves[0], move))
65
+ return;
66
+ // Shift and insert (keep 2 most recent)
67
+ moves[1] = moves[0];
68
+ moves[0] = move;
69
+ }
70
+ /**
71
+ * Check if a move is a killer move
72
+ *
73
+ * @param move - Move to check
74
+ * @param ply - Current ply
75
+ * @returns true if killer move
76
+ */
77
+ isKiller(move, ply) {
78
+ if (ply >= this.maxPly)
79
+ return false;
80
+ const moves = this.killers[ply];
81
+ return this.isSameMove(moves[0], move) || this.isSameMove(moves[1], move);
82
+ }
83
+ /**
84
+ * Clear all killer moves
85
+ */
86
+ clear() {
87
+ this.killers = Array.from({ length: this.maxPly }, () => [null, null]);
88
+ }
89
+ /**
90
+ * Check if two moves are the same
91
+ */
92
+ isSameMove(m1, m2) {
93
+ if (!m1 || !m2)
94
+ return false;
95
+ return m1.from === m2.from && m1.to === m2.to;
96
+ }
97
+ }
98
+ exports.KillerMoves = KillerMoves;
99
+ /**
100
+ * Calculate MVV-LVA score for a capture
101
+ *
102
+ * @param capturedPiece - Piece being captured
103
+ * @param attackerPiece - Piece doing the capture
104
+ * @returns MVV-LVA score (higher = better)
105
+ */
106
+ function getMVVLVAScore(capturedPiece, attackerPiece) {
107
+ const victimValue = MVV_LVA_VALUES[capturedPiece] || 0;
108
+ const attackerValue = MVV_LVA_VALUES[attackerPiece] || 0;
109
+ // Most valuable victim first, then least valuable attacker
110
+ // Multiply victim value by 10 to prioritize victim over attacker
111
+ return victimValue * 10 - attackerValue;
112
+ }
113
+ /**
114
+ * Score a move for ordering
115
+ *
116
+ * @param move - Move to score
117
+ * @param pvMove - PV move from transposition table (if any)
118
+ * @param killerMoves - Killer moves instance
119
+ * @param ply - Current ply
120
+ * @returns Move score (higher = better)
121
+ */
122
+ function scoreMove(move, pvMove, killerMoves, ply) {
123
+ // 1. PV move (from transposition table) - highest priority
124
+ if (pvMove && move.from === pvMove.from && move.to === pvMove.to) {
125
+ return SCORE_PV_MOVE;
126
+ }
127
+ // 2. Queen promotions
128
+ if ((move.flags & types_1.MoveFlag.PROMOTION) &&
129
+ (move.promotionPiece === types_1.Piece.WHITE_QUEEN || move.promotionPiece === types_1.Piece.BLACK_QUEEN)) {
130
+ return SCORE_QUEEN_PROMOTION;
131
+ }
132
+ // 3. Captures - use MVV-LVA
133
+ if (move.flags & types_1.MoveFlag.CAPTURE) {
134
+ const mvvLvaScore = getMVVLVAScore(move.capturedPiece, move.piece);
135
+ // Winning captures (capturing more valuable piece)
136
+ if (mvvLvaScore > 0) {
137
+ return SCORE_WINNING_CAPTURE + mvvLvaScore;
138
+ }
139
+ // Equal captures (e.g., pawn takes pawn)
140
+ if (mvvLvaScore === 0) {
141
+ return SCORE_WINNING_CAPTURE;
142
+ }
143
+ // Losing captures (capturing less valuable piece) - usually bad
144
+ return SCORE_LOSING_CAPTURE + mvvLvaScore;
145
+ }
146
+ // 4. Killer moves (non-captures that caused beta cutoff)
147
+ if (killerMoves && killerMoves.isKiller(move, ply)) {
148
+ return SCORE_KILLER_MOVE;
149
+ }
150
+ // 5. All other moves get neutral score
151
+ return 0;
152
+ }
153
+ /**
154
+ * Order moves for search
155
+ *
156
+ * @param moves - Moves to order
157
+ * @param pvMove - PV move from transposition table (if any)
158
+ * @param killerMoves - Killer moves instance
159
+ * @param ply - Current ply
160
+ * @returns Ordered moves (best first)
161
+ */
162
+ function orderMoves(moves, pvMove = null, killerMoves = null, ply = 0) {
163
+ // Score all moves
164
+ const scoredMoves = moves.map(move => ({
165
+ move,
166
+ score: scoreMove(move, pvMove, killerMoves, ply),
167
+ }));
168
+ // Sort by score (descending - highest first)
169
+ scoredMoves.sort((a, b) => b.score - a.score);
170
+ // Return ordered moves
171
+ return scoredMoves.map(sm => sm.move);
172
+ }
173
+ //# sourceMappingURL=MoveOrdering.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"MoveOrdering.js","sourceRoot":"","sources":["../../src/ai/MoveOrdering.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,62 @@
1
+ /**
2
+ * Alpha-beta search implementation for js-chess-engine v2
3
+ *
4
+ * Implements minimax with alpha-beta pruning and extensions for checks and captures.
5
+ * Phase 5: Enhanced with transposition table, move ordering, and iterative deepening.
6
+ */
7
+ import { InternalBoard } from '../types';
8
+ import { SearchResult } from '../types/ai.types';
9
+ /**
10
+ * Search engine with alpha-beta pruning, transposition table, and move ordering
11
+ */
12
+ export declare class Search {
13
+ private nodesSearched;
14
+ private transpositionTable;
15
+ private killerMoves;
16
+ private useOptimizations;
17
+ constructor(ttSizeMB?: number);
18
+ /**
19
+ * Enable or disable optimizations (for testing)
20
+ */
21
+ setOptimizations(enabled: boolean): void;
22
+ /**
23
+ * Clear search data structures
24
+ */
25
+ clear(): void;
26
+ /**
27
+ * Find the best move using alpha-beta search with iterative deepening
28
+ *
29
+ * @param board - Current board position
30
+ * @param baseDepth - Base search depth
31
+ * @param extendedDepth - Extended search depth (for checks and captures)
32
+ * @returns Best move with score
33
+ */
34
+ findBestMove(board: InternalBoard, baseDepth: number, extendedDepth: number): SearchResult | null;
35
+ /**
36
+ * Search at a specific depth (used for iterative deepening)
37
+ */
38
+ private searchDepth;
39
+ /**
40
+ * Alpha-beta search with extensions, transposition table, and move ordering
41
+ *
42
+ * @param board - Current position
43
+ * @param rootPlayerColor - Player color at root (for evaluation perspective)
44
+ * @param baseDepth - Base search depth
45
+ * @param extendedDepth - Extended search depth
46
+ * @param depth - Current depth
47
+ * @param wasCapture - Whether last move was a capture
48
+ * @param initialScore - Initial score (optimization)
49
+ * @param alpha - Alpha bound
50
+ * @param beta - Beta bound
51
+ * @returns Score from current player's perspective
52
+ */
53
+ private alphaBeta;
54
+ /**
55
+ * Copy board for search (fast struct copy)
56
+ *
57
+ * @param board - Board to copy
58
+ * @returns New board instance
59
+ */
60
+ private copyBoard;
61
+ }
62
+ //# sourceMappingURL=Search.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Search.d.ts","sourceRoot":"","sources":["../../src/ai/Search.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,EAAE,aAAa,EAAgD,MAAM,UAAU,CAAC;AAIvF,OAAO,EAAS,YAAY,EAAE,MAAM,mBAAmB,CAAC;AAIxD;;GAEG;AACH,qBAAa,MAAM;IACf,OAAO,CAAC,aAAa,CAAa;IAClC,OAAO,CAAC,kBAAkB,CAA4B;IACtD,OAAO,CAAC,WAAW,CAAc;IACjC,OAAO,CAAC,gBAAgB,CAAiB;gBAE7B,QAAQ,GAAE,MAAW;IAMjC;;OAEG;IACH,gBAAgB,CAAC,OAAO,EAAE,OAAO,GAAG,IAAI;IAIxC;;OAEG;IACH,KAAK,IAAI,IAAI;IAOb;;;;;;;OAOG;IACH,YAAY,CACR,KAAK,EAAE,aAAa,EACpB,SAAS,EAAE,MAAM,EACjB,aAAa,EAAE,MAAM,GACtB,YAAY,GAAG,IAAI;IA2ItB;;OAEG;IACH,OAAO,CAAC,WAAW;IAsDnB;;;;;;;;;;;;;OAaG;IACH,OAAO,CAAC,SAAS;IAoKjB;;;;;OAKG;IACH,OAAO,CAAC,SAAS;CA6BpB"}