chesslib: A threefold repetition not detected

The threefold repetition after 5… Bf8 for the below moves is not detected. Why is that the case? Can you please check? The positions, possibilities to capture en passant and castle rights after 1… e5, 3… Bf8 and 5… Bf8 are the same. This is a threefold repetition after 5… Bf8.

final MoveList moveList = new MoveList(); //use MoveList to play moves on the board using SAN
moveList.loadFromSan("1. e4 e5 2. Be2 Be7 3. Bf1 Bf8 4. Bd3 Bd6 5. Bf1 Bf8");

final Board board = new Board();
final Iterator<Move> moves = moveList.iterator();
while (moves.hasNext()) {
  board.doMove(moves.next());
}
System.out.println(board.isRepetition()); // false but should be true

About this issue

  • Original URL
  • State: closed
  • Created 4 years ago
  • Comments: 25 (12 by maintainers)

Commits related to this issue

Most upvoted comments

There must be something wrong here. Probably only a small problem in the code, I can’t see through, but there is something off.

In the first example, both players lose all castling rights by moving their kings. So the position after 5… Ke8 and the initial position are not the same. The position after 7… N8 is the same as after 5… Ke8, so this is a twofold repetition, but flagged as threefold.

// after loosing castling rights
final MoveList moveList = new MoveList();
moveList.loadFromSan("1. e4 e5 2. Nf3 Nf6 3. Ng1 Ng8 4. Ke2 Ke7 5. Ke1 Ke8 6. Na3 Na6 7. Nb1 Nb8");

final Board board = new Board();
final Iterator<Move> moves = moveList.iterator();
while (moves.hasNext()) {
  board.doMove(moves.next());
}
System.out.println(board.isRepetition()); // true but should be false (repetition count is 2)

In the second example, there is a pawn two square advance involved. After 3… d5 capturing en passant is not possible. So this is the same position as after 5… Nf6 and 7… Nf6. See “9.2.2.1 at the start of the sequence a pawn could have been captured en passant” in the rules. 7… Nf6 is a threefold repetition but not flagged as such.

// after two square advance
final MoveList moveList = new MoveList();
moveList.loadFromSan("1. Nf3 Nf6 2. Nc3 c5 3. e3 d5 4. Be2 Ne4 5. Bf1 Nf6 6. Be2 Ne4 7. Bf1 Nf6");

final Board board = new Board();
final Iterator<Move> moves = moveList.iterator();
while (moves.hasNext()) {
  board.doMove(moves.next());
}
System.out.println(board.isRepetition()); // false but should be true

For the third example, I chose a real game mentioned in Wikipedia. Wikipedia states that there is a threefold repetition after 38… Kf8. But this is not flagged as threefold. Again there is a pawn two square advance at the beginning of the sequence. But because there is no en passant capture possible the positions after 34…h5 36…Kf8 and 38…Kf8 are the same, which gives the threefold repetition after 38…Kf8.

// capablanca - lasker 1921
final MoveList moveList = new MoveList();
moveList.loadFromSan(
    "1. d4 d5 2. Nf3 Nf6 3. c4 e6 4. Bg5 Nbd7 5. e3 Be7 6. Nc3 O-O 7. Rc1 b6 8. cxd5 exd5 9. Qa4 c5 10. Qc6 Rb8 11. Nxd5 Bb7 12. Nxe7+ Qxe7 13. Qa4 Rbc8 14. Qa3 Qe6 15. Bxf6 Qxf6 16. Ba6 Bxf3 17. Bxc8 Rxc8 18. gxf3 Qxf3 19. Rg1 Re8 20. Qd3 g6 21. Kf1 Re4 22. Qd1 Qh3+ 23. Rg2 Nf6 24. Kg1 cxd4 25. Rc4 dxe3 26. Rxe4 Nxe4 27. Qd8+ Kg7 28. Qd4+ Nf6 29. fxe3 Qe6 30. Rf2 g5 31. h4 gxh4 32. Qxh4 Ng4 33. Qg5+ Kf8 34. Rf5 h5 35. Qd8+ Kg7 36. Qg5+ Kf8 37. Qd8+ Kg7 38. Qg5+ Kf8");

final Board board = new Board();
final Iterator<Move> moves = moveList.iterator();
while (moves.hasNext()) {
  board.doMove(moves.next());
}
System.out.println(board.isRepetition()); // false but should be true

Should I not overlook something, there is something missing here and your API could improve greatly by addressing this. The method board.isRepetition() says in the code Verify threefold repetition so is definitely meant for threefold repetition detection!