基于python纯函数实现井字棋游戏


Posted in Python onMay 27, 2020

1、定义全局变

'''全局变量:
 X 和 O 表示两方的棋子;
 EMPTY 表示棋位为空;
 TIE 表示平局;
 NUM_SQUARES 表示有 9 个棋位
 '''
 X = "X"
 O = "O"
 EMPTY = " "
 TIE = "TIE"
 NUM_SQUARES = 9

2、定义调用到的函数

def ask_yes_no(question):
  '''问一个是或否的问题,用 y 或 n 回答。'''
  response = None
  while response not in ('y', 'n'):
    response = input(question).lower()
  return response


def ask_number(question, low, high):
  '''讯问一个规定范围的数字。'''
  response = None
  while response not in range(low, high):
    response = int(input(question))
  return response


def pieces():
  '''决定在人和机器之间谁先行棋。'''
  go_first = ask_yes_no('你先走? (y/n): ')
  if go_first == 'y':
    print('\n好,你先请。')
    human = X
    computer = O
  else:
    print('\n你放弃先手,我先走。')
    computer = X
    human = O
  return computer, human


def new_board():
  '''创建一个棋盘。'''
  board = []
  for square in range(NUM_SQUARES):
    board.append(EMPTY)
  return board


def display_board(board):
  '''显示棋盘。'''
  print('\n\t', board[0], '|', board[1], '|', board[2])
  print('\t', '---------')
  print('\t', board[3], '|', board[4], '|', board[5])
  print('\t', '---------')
  print('\t', board[6], '|', board[7], '|', board[8], '\n')


def legal_moves(board):
  '''创建合法的行棋位置清单。'''
  moves = []
  for square in range(NUM_SQUARES):
    if board[square] == EMPTY: # 该棋位为空
      moves.append(square)
  return moves


def winner(board):
  '''判定游戏获胜者。'''
  WAYS_TO_WIN = ((0, 1, 2), # 横
          (3, 4, 5),
          (6, 7, 8),
          (0, 3, 6), # 竖
          (1, 4, 7),
          (2, 5, 8),
          (0, 4, 8), # 主对角线
          (2, 4, 6)) # 副对角线
  # 谁先有三个棋子在一条直线上谁就获胜。
  for row in WAYS_TO_WIN:
    if board[row[0]] == board[row[1]] == board[row[2]] != EMPTY:
      winner = board[row[0]]
      return winner
  
  # 没有获胜方,但棋盘已经下满,判为平局
  if EMPTY not in board:
    return TIE

  return None # 没有获胜方,且非平局


def human_move(board, human):
  '''获取玩家的行棋位置。''' 
  legal = legal_moves(board) # 合法的行棋位置清单
  move = None
  while move not in legal:
    move = ask_number('你走哪? (0 - 8):', 0, NUM_SQUARES)
    if move not in legal:
      print('\n你选的棋位已落子,重新选择。\n')
  print('落子无悔...')
  return move


def computer_move(board, computer, human):
  '''获取电脑的行棋位置。'''
  
  board = board[:] # 通过切片复制棋盘, 创建局部变量
  BEST_MOVES = (4, 0, 2, 6, 8, 1, 3, 5, 7) # 优先的行棋位置

  print('我走到:', end=' ')
  
  # 在局部空间确定可以获胜的走法
  for move in legal_moves(board): # 合法的行棋位置列表
    board[move] = computer # 更新棋盘副本
    if winner(board) == computer:
      # 计算机能获胜
      print(move)
      return move
    # 如果计算机在该棋位行棋不能获胜,
    board[move] = EMPTY # 悔棋,更换下一个合法棋位
  
  # 阻止玩家获胜
  for move in legal_moves(board): # 合法的行棋位置列表
    board[move] = human # 更新棋盘
    if winner(board) == human:
      # 在该棋位玩家行棋后将获胜
      print(move)
      return move
    # 玩家不能获胜,不行棋至此
    board[move] = EMPTY

  # 没有能使行棋双方立决胜负的棋位,从优先棋位选择合法行棋位置
  for move in BEST_MOVES:
    if move in legal_moves(board):
      print(move)
      return move


def next_turn(turn):
  '''切换行棋方'''
  if turn == X:
    return O
  else:
    return X

  
def congrat_winner(the_winner, computer, human):
  '''向获胜方表示祝贺或声明平局'''
  if the_winner != TIE:
    print(the_winner, '祝贺你!\n')
  else:
    print('平局。。。\n')

  if the_winner == computer:
    print('如我所料,我又胜了。\n这是否能说明计算机在给方面都优于人类呢?')

  elif the_winner == human:
    print('真是匪夷所思,你没捣鬼吧?人类怎么会胜? \n不会有下次了。' )

  elif the_winner == TIE:
    print('你很厉害嘛,能跟计算机打成平手。')

3、定义主函数

def main():
  display_instruct() # 显示游戏操作指南
  computer, human = pieces() # 决定谁先行棋
  turn = X # 先行棋方执子 X
  board = new_board() # 创建空棋盘
  display_board(board) # 显示棋盘

  while not winner(board): 
    # 判定结果,在没有获胜方且不是平局时进入循环
    if turn == human:
      # 轮到玩家行棋,玩家行棋
      move = human_move(board, human) # 玩家的行棋位置
      board[move] = human # 更新棋盘
    else:
      # 轮到电脑行棋
      move = computer_move(board, computer, human) # 电脑的行棋位置
      board[move] = computer # 更新棋盘
    display_board(board) # 显示更新后的棋盘
    turn = next_turn(turn) # 切换行棋方

  the_winner = winner(board) # 判定获胜者,返回获胜方的执子,平局返回 None
  congrat_winner(the_winner, computer, human) # 向获胜方表示祝贺或声明是平局

4、调用主函数,启动程序

main()
input('\n\n按回车键退出程序。') # 等待用户

在 jupyter 中演练如下:

基于python纯函数实现井字棋游戏

基于python纯函数实现井字棋游戏

基于python纯函数实现井字棋游戏基于python纯函数实现井字棋游戏

基于python纯函数实现井字棋游戏

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
使用Python解析JSON数据的基本方法
Oct 15 Python
Python协程的用法和例子详解
Sep 09 Python
Python字符串和字典相关操作的实例详解
Sep 23 Python
Python 用Redis简单实现分布式爬虫的方法
Nov 23 Python
Python中str.join()简单用法示例
Mar 20 Python
Python基于socket模块实现UDP通信功能示例
Apr 10 Python
Python 实现日志同时输出到屏幕和文件
Feb 19 Python
如何基于python实现年会抽奖工具
Oct 20 Python
matplotlib部件之矩形选区(RectangleSelector)的实现
Feb 01 Python
python 统计list中各个元素出现的次数的几种方法
Feb 20 Python
Python 如何实现文件自动去重
Jun 02 Python
python基础入门之普通操作与函数(三)
Jun 13 Python
Python实现读取并写入Excel文件过程解析
May 27 #Python
Python正则表达式如何匹配中文
May 27 #Python
使用python创建Excel工作簿及工作表过程图解
May 27 #Python
Python实现疫情通定时自动填写功能(附代码)
May 27 #Python
Python unittest单元测试openpyxl实现过程解析
May 27 #Python
python实现爱奇艺登陆密码RSA加密的方法示例详解
May 27 #Python
python如何求100以内的素数
May 27 #Python
You might like
PHP实现阿里大鱼短信验证的实例代码
2017/07/10 PHP
利用location.hash实现跨域iframe自适应
2010/05/04 Javascript
jquery 圆形旋转图片滚动切换效果
2011/01/19 Javascript
解析John Resig Simple JavaScript Inheritance代码
2012/12/03 Javascript
js调用后台、后台调用前台等方法总结
2014/04/17 Javascript
JavaScript代码应该放在HTML代码哪个位置比较好?
2014/10/16 Javascript
让你一句话理解闭包(简单易懂)
2016/06/03 Javascript
Bootstrap实现带动画过渡的弹出框
2016/08/09 Javascript
JavaScript中常见的八个陷阱总结
2017/06/28 Javascript
layui-laydate时间日历控件使用方法详解
2018/11/15 Javascript
使用apifm-wxapi模块中的问题及解决方法
2019/08/05 Javascript
vue 解决遍历对象显示的顺序不对问题
2019/11/07 Javascript
JS三级联动代码格式实例详解
2019/12/30 Javascript
VUE页面中通过双击实现复制表格中内容的示例代码
2020/06/11 Javascript
js编写简易的计算器
2020/07/29 Javascript
Python实现统计英文单词个数及字符串分割代码
2015/05/28 Python
python创建进程fork用法
2015/06/04 Python
python将字符串转换成json的方法小结
2019/07/09 Python
django-rest-framework解析请求参数过程详解
2019/07/18 Python
Python操作SQLite数据库过程解析
2019/09/02 Python
python使用正则表达式(Regular Expression)方法超详细
2019/12/30 Python
python基于property()函数定义属性
2020/01/22 Python
对CSS3选择器的研究(详解)
2016/09/16 HTML / CSS
7款设计巧妙的css3飘带状3D立体效果的导航菜单和表单窗口
2013/02/04 HTML / CSS
HTML5 画布canvas使用方法
2016/03/18 HTML / CSS
优质美利奴羊毛袜,不只是徒步旅行:Darn Tough Vermont
2018/11/05 全球购物
解释一下ruby中的特殊方法与特殊类
2013/02/26 面试题
《秋姑娘的信》教学反思
2014/02/28 职场文书
家长写给老师的建议书
2014/03/13 职场文书
食品销售计划书
2014/04/26 职场文书
给妈妈洗脚活动方案
2014/08/16 职场文书
商铺租房协议书范本
2014/12/04 职场文书
2014个人年终工作总结范文
2014/12/15 职场文书
社区元宵节活动总结
2015/02/06 职场文书
MySQL 服务和数据库管理
2021/11/11 MySQL
一文了解MySQL二级索引的查询过程
2022/02/24 MySQL