【发布时间】:2021-06-05 15:38:23
【问题描述】:
我正在尝试以面向对象的方式为井字游戏实现极小极大算法。一旦算法确定了最佳移动,我有点不知道如何处理恢复我的board 对象的状态。在运行程序时,我注意到minimax方法对当前board对象的操作并不理想。
我添加了一个方法来撤消 minimax 方法所做的移动:board.[]=(empty_square, Square::INITIAL_MARKER)
我注意到算法做出了错误的选择。这里,X 是播放器,O 是计算机。如果这是board的状态:
| |
| |
| |
-----+-----+-----
| |
| X |
| |
-----+-----+-----
| |
| | O
| |
当玩家X移动并选择方格2时,minimax(计算机,O)将选择7而不是8,这将是一个更好的选择:
| |
| X |
| |
-----+-----+-----
| |
| X |
| |
-----+-----+-----
| |
O | | O
| |
由于我缺乏经验,我对如何进行有点迷茫,希望得到任何指导!
这里是minimax 方法:
def minimax
best_move = 0
score_current_move = nil
best_score = -10000 if @current_marker == COMPUTER_MARKER
best_score = 10000 if @current_marker == HUMAN_MARKER
board.unmarked_keys.each do |empty_square|
board.[]=(empty_square, @current_marker)
if board.full?
score_current_move = 0
elsif board.someone_won?
score_current_move = -1 if board.winning_marker == HUMAN_MARKER
score_current_move = 1 if board.winning_marker == COMPUTER_MARKER
else
alternate_player
score_current_move = minimax[0]
end
if ((@current_marker == COMPUTER_MARKER) && (score_current_move >= best_score))
best_score = score_current_move
best_move = empty_square
elsif ((@current_marker == HUMAN_MARKER) && (score_current_move <= best_score))
best_score = score_current_move
best_move = empty_square
end
board.[]=(empty_square, Square::INITIAL_MARKER)
end
[best_score, best_move]
end
【问题讨论】:
-
你能不能把你的问题浓缩一点,这样就不需要阅读和理解 350 行代码了?请尝试将其简化为显示您的问题的最小示例。然后准确描述您想要实现的目标,您当前的代码到底有什么不适用的(您是否看到不正确的行为、异常/错误,还有其他什么?)。请尽可能具体,并包含任何错误消息和示例代码以专门显示您的问题。请参阅stackoverflow.com/help/minimal-reproducible-example 了解一些指南。您可以使用下方的编辑链接编辑您的问题。
-
您可能想考虑为您的类定义一个
initialize_copy方法,这应该会改变dup的行为。
标签: ruby algorithm oop minimax minmax