当前位置: 首页 > article >正文

蓝桥与力扣刷题(1275 找出井字棋的获胜者)

题目:

井字棋 是由两个玩家 A 和 B 在 3 x 3 的棋盘上进行的游戏。井字棋游戏的规则如下:

  • 玩家轮流将棋子放在空方格 (' ') 上。
  • 第一个玩家 A 总是用 'X' 作为棋子,而第二个玩家 B 总是用 'O' 作为棋子。
  • 'X' 和 'O' 只能放在空方格中,而不能放在已经被占用的方格上。
  • 只要有 3 个相同的(非空)棋子排成一条直线(行、列、对角线)时,游戏结束。
  • 如果所有方块都放满棋子(不为空),游戏也会结束。
  • 游戏结束后,棋子无法再进行任何移动。

给你一个数组 moves,其中 moves[i] = [rowi, coli] 表示第 i 次移动在 grid[rowi][coli]。如果游戏存在获胜者(A 或 B),就返回该游戏的获胜者;如果游戏以平局结束,则返回 "Draw";如果仍会有行动(游戏未结束),则返回 "Pending"

你可以假设 moves 都 有效(遵循 井字棋 规则),网格最初是空的,A 将先行动。

示例 1:

输入:moves = [[0,0],[2,0],[1,1],[2,1],[2,2]]
输出:"A"
解释:"A" 获胜,他总是先走。

示例 2:

输入:moves = [[0,0],[1,1],[0,1],[0,2],[1,0],[2,0]]
输出:"B"
解释:"B" 获胜。

示例 3:

输入:moves = [[0,0],[1,1],[2,0],[1,0],[1,2],[2,1],[0,1],[0,2],[2,2]]
输出:"Draw"
解释:由于没有办法再行动,游戏以平局结束。

解题思路+代码:

代码:

class Solution {
    public String tictactoe(int[][] moves) {
        /*
        思路:
        1.判断回合数
        2.确定最后下棋的玩家(根据回合数的奇偶性确定最后下棋的玩家,奇A偶B)
        3.初始3✖3的棋盘
        4.模拟落子(只模拟最后下棋的玩家的落子)
        5.判断胜负:从第5或第6回合开始,每次落子后判断当前回合的棋子所在行、列以及两条对角线是否满足三子连线的条件。
        6.平局判断:如果所有位置都已填满(即回合数为9)
        7.回合少于9,也没有玩家获胜,提醒游戏未结束返回pending
        */
        int len = moves.length; // 数组长度(回合数)

        // 小于5回合无法分出胜负
        if (len < 5) {
            return "Pending";
        }

        /**
         * 赢家一定是最后一回合下棋的玩家
         * 所以我们只需要分析一名玩家的棋
         * A先手,B后手
         * A的回合数组下标是:0, 2, 4, 6, 8  (偶数)
         * B的回合数组下标是:1, 3, 5, 7     (奇数)
         */

        // 先默认是A
        int index = 0; // 从0开始
        String winner = "A";
        if ((len & 1) == 0){ // (偶数)最后下棋的是B,注意:B的回合下标是奇数,对应的数组长度是偶数
            index = 1; // 从1开始
            winner = "B";
        }

        int[][] map = new int[3][3];
        for (int i=index; i<len; i+=2) { // 只模拟一名玩家棋
            map[moves[i][0]][moves[i][1]] = 1;
        }

        /**
         * 玩家A只需要判断5,7,9回合
         * 玩家B只需要判断6,8回合
         * 每次落子判断当前回合棋子所在行,列以及两条对接线是否满足条件
         * (0,1), (1,0), (1, 2), (2,1) 这四个点不用判断对角线
         * 用 row + col == 1 和 row + col == 3 来判断是不是这四个点
         */
        int row, col;
        for (int i=4+index; i<len; i+=2) { // 从5/6回合开始判断
            row = moves[i][0]; // 获取行
            col = moves[i][1]; // 获取列

            // 判断行,列
            if (map[row][0] + map[row][1] + map[row][2] == 3 || // 行
                map[0][col] + map[1][col] + map[2][col] == 3) { // 列
                return winner;
            }

            // 当前点不用判断对角线
            if (row + col == 1 || row + col == 3){
                continue;
            }

            // 判断两条对角线
            if (map[0][0] + map[1][1] + map[2][2] == 3 ||
                map[0][2] + map[1][1] + map[2][0] == 3) { 
                return winner;
            }
        }

        if (len == 9) { // 下满未分胜负平局
            return "Draw";
        }

        return "Pending"; // 未下满,未分胜负
    }
}

总结:个人认为这题比较偏重逻辑思路,怎么判断谁是获胜者?怎么判断三子连线?获胜者我们可以通过奇A偶B来判断,三子连线我们也可以划分出情况逐一分析,垂直、水平、对角线三种情况,分别列举出来进行判断。


http://www.kler.cn/a/508922.html

相关文章:

  • PyBroker:利用 Python 和机器学习助力算法交易
  • XML在线格式化 - 加菲工具
  • Matplotlib基础
  • Java设计模式——单例模式(特性、各种实现、懒汉式、饿汉式、内部类实现、枚举方式、双重校验+锁)
  • AAPM:基于大型语言模型代理的资产定价模型,夏普比率提高9.6%
  • ThreeJs能力演示——图层导入导出
  • 【第三十周】文献阅读:Mask R-CNN
  • Golang——常用库context和runtime
  • Go 语言 select 的实现原理
  • React中用到的Javascript设计模式详解
  • Chromium 132 编译指南 Mac篇(一)- 环境准备
  • C#高级:用Csharp操作鼠标
  • Vue.js组件开发案例(比较两个数字大小)
  • 数据库:Redis命令行帮助解释
  • HarmonyOS NEXT开发进阶(九):UIAbility 组件生命周期及启动模式讲解
  • Google Titans 是否会终结基于 Transformer 的大语言模型(LLMs)
  • sort(函数模板)和priority_queue(类模板)的比较器重载
  • Dexie.js 事务管理详解
  • 读spring官方文档的一些关键知识点介绍
  • Node-Red使用笔记
  • 关于安科瑞Acrel-1000DP分布式光伏监控系统的实际案例分析-安科瑞 蒋静
  • 【JavaEE】Spring(1)
  • ASP .NET Core 学习 (.NET 9)- 创建 API项目,并配置Swagger及API 分组或版本
  • 论文浅尝 | 从大型语言模型进行情境化提炼以完成知识图谱(ACL2024)
  • 人脸识别【python-基于OpenCV】
  • 一文读懂服务器的HBA卡