Is it possible to take a FEN aka forsyth-edward notation and flip it from black to play and win to white

949 Views Asked by At

Lets say we have a chess fen and the fen is a black to play and win problem. Many times chess puzzle websites want to avoid the confusion of having to keep indicating who's turn it is to move so they rather just put all the puzzles as white to play and win or black to play and win. In a case or scenario where I have a array or db of 1000 fens where its black to play and win is there a way I can run it through a function or algo that will spit out the fen for the exact same position except white to play and win?

I've tried setting editing the board to have all the black pieces be white pieces and white pieces be black pieces but ran into the issue that the board was upside down and pawns move in only one direction.

starting fen for black to play and win.

7k/8/7K/8/ppp5/8/PPP5/8 b - - 0 1

Fen I want to arrive at from running:

function flipfen(fen) {
    return (fen*(algorithm)) 
};

˚console.log(flipfen(7k/8/7K/8/ppp5/8/PPP5/8 b - - 0 1))

And the desired result:

8/5ppp/8/5PPP/8/k7/8/K7 w - - 0 1

Maybe I can use regular expressions? it looks like the second fen (in this case not sure if it will work in all cases is just the other one backwards with some slight changes? ) `

8/5ppp/8/5PPP/8/k7/8/K7 w - - 0 1
1

There are 1 best solutions below

0
On

I tried to think of every possible valid FEN.

  • invert the letters case
  • reverse the rows order
  • switch who's to move
  • swap castling rights
  • mirror the en passant square

function flipFEN(FEN) {
  const invertCase = (char) => {
    if (char == char.toLowerCase())
      return char.toUpperCase();
    return char.toLowerCase();
  }
  
  let position = FEN.split(" ")[0].split("/");
  position = position.map((row) => {
    return row.split("").map(invertCase).join("");
  });
  position = position.reverse().join("/");

  let turn = FEN.split(" ")[1];
  turn = turn == "w" ? "b" : "w";
  
  let castle = FEN.split(" ")[2];
  if (castle != "-") {
    castle = castle.split("").map(invertCase);
    castle.sort();
    castle = castle.join("");
  }
  
  let ep = FEN.split(" ")[3];
  if (ep != "-") {
    ep = ep.split("");
    ep[1] = ep[1] == "6" ? "3" : "6";
    ep = ep.join("");
  }
  
  const rest = FEN.split(" ").slice(4);
  
  return [position, turn, castle, ep, ...rest].join(" ");
}

console.log(flipFEN("r1bq1r2/pp2n3/4N2k/3pPppP/1b1n2Q1/2N5/PP3PP1/R1B1K2R w KQ g6 0 15"));

// > "r1b1k2r/pp3pp1/2n5/1B1N2q1/3PpPPp/4n2K/PP2N3/R1BQ1R2 b kq g3 0 15"