HarmonyOS 小游戏《对战五子棋》开发第14篇 - 困难AI实现:Minimax算法原理详解

向前看两步------Minimax让AI学会"换位思考"

设计截图如下:

为什么需要Minimax

普通AI的局限:只看当前一步,不考虑对手的反击。

场景:AI可以选择形成活三(8000分)或冲四(10000分)。普通AI选冲四,但对手下一步会堵住冲四,AI的活三机会丢失了。

Minimax的核心思想:假设对手也会做出最优选择,选择对自己最不坏的结果

Minimax算法原理

复制代码
        AI选择(最大化)
       /    |    \
     候选1  候选2  候选3
     / \    / \    / \
   对手选择(最小化)
   ↓   ↓  ↓   ↓  ↓   ↓
  评估 评估 评估 评估 评估 评估
  • Max层(AI回合):选择分数最高的走法
  • Min层(对手回合):选择分数最低的走法(对AI最不利)
  • 叶节点:用评估函数计算当前局面的分数

代码实现

typescript 复制代码
private getHardMove(board: number[][]): Move {
  const candidates = this.getSortedCandidates(board);
  const maxCandidates = Math.min(12, candidates.length);
  let bestMove: Move = candidates[0];
  let bestScore: number = -Infinity;
  let alpha: number = -Infinity;
  const beta: number = Infinity;

  for (let i = 0; i < maxCandidates; i++) {
    const move = candidates[i];
    board[move.row][move.col] = this.aiColor;

    // 如果直接获胜,立即返回
    if (this.checkWin(board, move.row, move.col, this.aiColor)) {
      board[move.row][move.col] = EMPTY;
      return move;
    }

    // Minimax递归(对手回合,最小化)
    const score = this.minimax(board, 2, alpha, beta, false);
    board[move.row][move.col] = EMPTY;

    if (score > bestScore) {
      bestScore = score;
      bestMove = move;
    }
    alpha = Math.max(alpha, score);
  }
  return bestMove;
}

minimax递归函数

typescript 复制代码
private minimax(board: number[][], depth: number, alpha: number, beta: number,
  isMaximizing: boolean): number {
  // 终止条件:深度为0时评估局面
  if (depth === 0) {
    return this.evaluateBoard(board);
  }

  const candidates = this.getSortedCandidates(board);
  const maxCandidates = Math.min(8, candidates.length);

  if (isMaximizing) {
    // AI回合:找最大值
    let maxEval: number = -Infinity;
    for (let i = 0; i < maxCandidates; i++) {
      const move = candidates[i];
      board[move.row][move.col] = this.aiColor;

      if (this.checkWin(board, move.row, move.col, this.aiColor)) {
        board[move.row][move.col] = EMPTY;
        return SCORE_FIVE;  // AI获胜
      }

      const evalScore = this.minimax(board, depth - 1, alpha, beta, false);
      board[move.row][move.col] = EMPTY;

      maxEval = Math.max(maxEval, evalScore);
      alpha = Math.max(alpha, evalScore);
      if (beta <= alpha) break;  // Alpha-Beta剪枝
    }
    return maxEval;
  } else {
    // 对手回合:找最小值
    let minEval: number = Infinity;
    for (let i = 0; i < maxCandidates; i++) {
      const move = candidates[i];
      board[move.row][move.col] = this.humanColor;

      if (this.checkWin(board, move.row, move.col, this.humanColor)) {
        board[move.row][move.col] = EMPTY;
        return -SCORE_FIVE;  // 对手获胜(对AI最不利)
      }

      const evalScore = this.minimax(board, depth - 1, alpha, beta, true);
      board[move.row][move.col] = EMPTY;

      minEval = Math.min(minEval, evalScore);
      beta = Math.min(beta, evalScore);
      if (beta <= alpha) break;  // Alpha-Beta剪枝
    }
    return minEval;
  }
}

搜索树图解

假设AI在搜索深度2,候选3个:

复制代码
深度2           AI选择(MAX)
              /     |      \
深度1       对手(MIN) 对手(MIN) 对手(MIN)
           /  \     /  \     /  \
深度0    评估  评估  评估  评估  评估  评估
          80   50   60   30   90   70

自底向上计算:
  深度1: min(80,50)=50  min(60,30)=30  min(90,70)=70
  深度2: max(50,30,70)=70 → 选择候选1

关键设计决策

1. 深度2的选择

typescript 复制代码
const score = this.minimax(board, 2, alpha, beta, false);
  • 深度1:只看对手反应------不够
  • 深度2:看AI→对手→AI------合理
  • 深度3:AI→对手→AI→对手------更好但计算量大

移动端选择深度2是性能与棋力的平衡。

2. 候选数量限制

typescript 复制代码
// 顶层:12个候选
const maxCandidates = Math.min(12, candidates.length);
// 递归层:8个候选
const maxCandidates = Math.min(8, candidates.length);

搜索树大小 = 12 × 8 × 8 = 768,在移动端可接受。

3. 立即获胜检查

typescript 复制代码
if (this.checkWin(board, move.row, move.col, this.aiColor)) {
  board[move.row][move.col] = EMPTY;
  return move;  // 不需要继续搜索
}

找到必胜走法立即返回,避免不必要的搜索。

4. 评估函数的差异

困难模式使用evaluateBoard(全盘评估),而非普通模式的evaluatePosition(单点评估):

typescript 复制代码
private evaluateBoard(board: number[][]): number {
  let aiScore: number = 0;
  let humanScore: number = 0;
  aiScore += this.evaluateLines(board, this.aiColor);
  humanScore += this.evaluateLines(board, this.humanColor);
  return aiScore - humanScore * 1.1;
}

总结

Minimax算法是博弈树搜索的经典方法:

  1. 换位思考:假设对手做出最优选择
  2. 最大最小:AI最大化,对手最小化
  3. 递归搜索:从叶节点向上回传
  4. 深度控制:平衡棋力与性能

困难模式通过深度2的Minimax搜索,能预见2步之后的局面变化,显著强于普通AI的单步评估。

相关推荐
艾络迅Acceleronix4 小时前
从连接到落地|移远艾络迅携手NAXEON构建电摩智能化能力
人工智能
尺度商业4 小时前
摩尔线程迎来解禁:谁在割肉,谁在捡筹?
人工智能
月华路4 小时前
《模型不玄学》第24章 第二个标签怎么造:层级标签
人工智能·深度学习·机器学习
咖啡星人k4 小时前
2026 上下文缓存进阶:把前缀契约写进SPEC,MonkeyCode 云端跑通
人工智能·机器学习·缓存
维克兜率天4 小时前
【维克】特征归一化与标准化:为什么模型对数据的“尺度“很敏感?
人工智能·笔记·python·机器学习·量化
朝阳5814 小时前
如何用 AI 自动生成规范的 Git 提交信息:从暂存区 diff 到 Conventional Commit
人工智能·git
CV山月4 小时前
大模型强化学习对齐:从 RLHF 框架到 PPO 算法原理
人工智能·python·大模型·强化学习·多模态·研究生
地平线开发者4 小时前
bevformer算法模型详细解读
算法
Profile排查笔记4 小时前
指纹浏览器推荐:用一套验收清单筛选 Profile、代理与自动化能力
前端·人工智能·后端·自动化
CET中电技术4 小时前
预付费电表计费系统是什么?云综能Lite如何重构水电费管理?
人工智能·物联网·重构