Search code examples
pythonchesspython-chessstockfish

Top 5 moves using chess.engine.SimpleEngine


I'm having trouble with the engine encapsulation of python-chess, I would like to use the Stockfish function top = stockfish.get_top_moves(5) but it seems like there is no way to do it using chess.engine.simpleEngine, do you have any advices?

I already tried getting all the result and then keeping just the top 5 move of the last evaluation using this piece of code:

self.engine.analysis(self.board, chess.engine.Limit(depth=18), multipv=5, root_moves = move_actions)

but it's tricky since the function is asyncronous and I'm integrating with other function that are not changeable I cannot make it asynchronous.

I'm going crazy trying to make it work, thanks to everybody.


Solution

  • The async object returned by that function is empty at first; you can wait until it is done by calling its .wait() method. Instead, if you don't want the async parts of engine.analysis, you can call engine.analyse which blocks until done and returns the result more directly. Both functions work to get the top 5 moves as you requested. Here is an example script:

    import chess
    import chess.engine
    
    stockfish = chess.engine.SimpleEngine.popen_uci("<file path to engine>")
    
    # Using engine.analysis
    analysis_result = stockfish.analysis(chess.Board(), limit=chess.engine.Limit(depth=18), multipv=5)
    analysis_result.wait()  # This is the missing step
    analysed_variations = analysis_result.multipv
    
    # Or instead using engine.analyse
    analysed_variations = stockfish.analyse(chess.Board(), limit=chess.engine.Limit(depth=18), multipv=5)
    
    # Either way you now have a dict of results, with moves under "pv"
    top_five_moves = [variation["pv"][0] for variation in analysed_variations]