鱼C论坛

 找回密码
 立即注册
查看: 3626|回复: 46

[作品展示] 井字棋?安排!!

[复制链接]
发表于 2020-3-16 14:04:08 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能^_^

您需要 登录 才可以下载或查看,没有账号?立即注册

x
本帖最后由 一个账号 于 2020-3-16 14:26 编辑

python小白来展示学习成果啦!!!! 希望各位帅气的小哥哥漂亮的小姐姐们能指点一下下

最近在看一本python入门书《python游戏编程快速上手》感觉这本书还是不错滴,很适合像我这个亚子的白白的小白

书里面有一个TicTacToe也就是井字棋游戏,看着书编了一遍又自己实现了一下下,好了废话不多说,先上波儿效果图(让我找找哈,不知道存哪了


井字棋1.png

井字棋2.png
第一次展示作品,不知道该说点啥。。。。

效果呢就上上面这两张图展示的那个亚子,是不是有点小失望呀,这TM是啥破游戏,连个正儿八经的界面都没。

emmmmmm刚开始学Python嘛,嘿嘿,等我以后学成归来,一定要把我的井字棋改成不同寻常的、高端大气上档次的....井字棋

下面我来稍微说一下这个小游戏吧,顺便复习一下。

有兴趣的童鞋们可以自己实现一下子呀,如果大家有啥想法或者发现我有哪里写的不好,欢迎评论交流呦

井字棋流程图.png

这个是书上给出的流程图,emmmm,是不是有点乱呀?! 不用怕,我自己又做了一张流程图(是不是莫名又开始恐慌了???hhhhh)

井字棋思路.png

没错,就是咱们的编辑神器IDLE,hhhhh,大概思路就是这样梓吧,然后就是按照写好的思路来编写程序了

首先呢,咱们稍微看下写好的流程,对于重复出现的操作可考虑一下函数之类的东东,比如咱们看到好多地方要展示游戏板,那就把这一块函数封装到一个函数里呗

就像这样

  1. def draw_board(board, nums=[' ']*10):
  2.     """展示游戏板"""
  3.     # board 是一个含有十个元素的列表,第一个元素不用管,只是抵消差一行为
  4.     print("    |    |")
  5.     print(" " + board[7] + "  | " + board[8] + "  | " + board[9])
  6.     print(nums[7], "  |", nums[8], " |", nums[9])
  7.     print("----------------")
  8.     print("    |    |")
  9.     print(" " + board[4] + "  | " + board[5] + "  | " + board[6])
  10.     print(nums[4], "  |", nums[5], " |", nums[6])
  11.     print("----------------")
  12.     print("    |    |")
  13.     print(" " + board[1] + "  | " + board[2] + "  | " + board[3])
  14.     print(nums[1], "  |", nums[2], " |", nums[3] )
复制代码

说实话,这个游戏板是真的简陋。。。。

然后就像这样依次定义出别的、各种各样的函数,这里就不一一赘述了。

再然后呢,就是游戏的主要股骨架了,其实我感觉可以先写游戏骨架,最后再进行重构,把差不多的代码整到一块,这样是不是更好呢?

  1. # 开始,骚话问候
  2. print("呕吼~~~~决一死战吧,大帅哥!!!!")

  3. # 显示原始游戏板
  4. draw_board([' ']*10, range(0, 10))
  5. print("这个是游戏板,有点简陋哈,不过也要按编号落子呦!!!!")


  6. # 进入游戏主循环
  7. while True:
  8.     # 重置游戏板
  9.     the_board = [' '] * 10
  10.     player_letter, computer_letter = choose_chess() # 让玩家选自棋子类型(x 或 o)
  11.     turn = first_go() # 随机决定谁先走
  12.     if turn == 'computer':
  13.         print("本电脑小哥哥先走,你一边呆着去。。。")
  14.     else:
  15.         print("你先走吧")
  16.     playing = True   # 设定标志,保证游戏正常进行和中断

  17.     # 进入一局游戏的循环
  18.     while playing:
  19.         if turn == 'player':
  20.             # 轮到玩家
  21.             move = get_player_move(the_board)
  22.             make_move(the_board, move, player_letter) # 让玩家落子

  23.             # 显示游戏板
  24.             draw_board(the_board)
  25.             
  26.             if is_winner(the_board, player_letter):
  27.                 # 判断是否获胜
  28.                 print("卧槽,你竟然赢了T_T\n我不服,敢不敢再来一局!?")
  29.                 playing = False
  30.                
  31.             elif is_full_board(the_board):
  32.                 # 判断是否平局(游戏板全装满,胜负未分)
  33.                 print("你的实力也就只配跟我打个平局吧,哼!¬︿̫̿¬")
  34.                 playing = False
  35.                
  36.             else:
  37.                 # 轮到电脑
  38.                 turn = 'computer'
  39.         else:
  40.             # 轮到电脑
  41.             # 算法计算最佳落子位置
  42.             move = get_computer_move(the_board, computer_letter)   
  43.             make_move(the_board, move, computer_letter) # 让电脑落子

  44.             # 显示游戏板
  45.             draw_board(the_board)
  46.             
  47.             if is_winner(the_board, computer_letter):
  48.                 # 判断是否获胜
  49.                 print("呕吼,你怎么输了呢,大帅哥!!!\n啊哈哈哈哈哈~~~///(^v^)\\\~~~")
  50.                 playing = False
  51.                
  52.             elif is_full_board(the_board):
  53.                 # 判断是否平局
  54.                 print("你的实力也就只配跟我打个平局吧,哼!¬︿̫̿¬")
  55.                 playing = False
  56.                
  57.             else:
  58.                 # 轮到玩家
  59.                 turn = 'player'

  60.     # 玩家是否要再玩一次,注意这里的缩进
  61.     if not play_again():
  62.         break

  63. # 游戏结束,表达依依不舍之情
  64. print("大帅哥,记着常来找我玩啊!!!(>人<)")
复制代码


差不多就是这亚子了。

我把剩下的代码也放的这里吧,如果哪里做的还是不是很好,请在评论区留下宁宝贵的建议(此处身体弯成90度)

  1. def choose_chess():
  2.     """让玩家选择棋子类型"""
  3.     print("\n请选择宁心仪的棋子类型(x 或 y) (反正选啥都得输,(¬︿̫̿¬☆))")
  4.     letter = input().upper()
  5.     # 防止玩家选别的字母
  6.     while not (letter == 'X' or letter == 'Y'):
  7.         print("骚凹瑞!宁只能在 X 和 Y 中选择一个呦!!!!")
  8.         letter = input().upper()
  9.    
  10.     # 返回一个列表,第一个元素为玩家的棋子,第二个为电脑的棋子
  11.     if letter == 'X':
  12.         return ['X', 'Y']
  13.     else:
  14.         return ['Y', 'X']


  15. def first_go():
  16.     """随机决定谁先走"""
  17.     if random.randint(0, 1) == 0:
  18.         return 'player'
  19.     else:
  20.         return 'computer'


  21. def is_free(board, move):
  22.     """判断某位置是否为空, 如果为空就返回True"""
  23.     copy = board[:] # 注意这里使用列表复制,防止更改原列表
  24.     return copy[move] == ' '

  25.    
  26. def get_player_move(board):
  27.     """获得玩家的落子位置"""
  28.     print("\n大帅哥,到你了。请输入:(1 - 9)")
  29.     print("快点!我还想早点把你打得落花流水呢!!!")
  30.     move = input()

  31.     # 确保玩家的输入合法
  32.     while not ((move in [str(i) for i in range(1, 10)]) or is_free(board, int(move))):
  33.         print("你咋不按规矩出牌呢。。。")
  34.         print("请重新输入吧!")
  35.         move = input()
  36.     return int(move)


  37. def make_move(board, move, letter):
  38.     """根据所给位置落子"""
  39.     board[move] = letter # 注意这里能修改局部变量board[move] 的原因, 列表引用


  40. def is_winner(bo, le):
  41.     """判断玩家或电脑是否获胜"""
  42.     # 用 bo 代替 board、le 代替 letter,比较方便
  43.     return ((bo[7] == le and bo[8] == le and bo[9] == le) or # 判断最上面一行是否一致
  44.             (bo[4] == le and bo[5] == le and bo[6] == le) or # 判断中间一行
  45.             (bo[1] == le and bo[2] == le and bo[3] == le) or # 判断最下面一行
  46.             (bo[7] == le and bo[4] == le and bo[1] == le) or # 判断最左边一列
  47.             (bo[8] == le and bo[5] == le and bo[2] == le) or # 判断中间一列
  48.             (bo[9] == le and bo[6] == le and bo[3] == le) or # 判断最右边一列
  49.             (bo[7] == le and bo[5] == le and bo[3] == le) or # 判断主对角线
  50.             (bo[1] == le and bo[5] == le and bo[9] == le)) # 判断副对角线


  51. def is_full_board(board):
  52.     """判断游戏板是否全装满,即是否平局"""
  53.     copy = board[:]
  54.     is_full = True
  55.    
  56.     for i in range(1, 10):
  57.         if copy[i] == ' ':
  58.             is_full = False
  59.     return is_full


  60. def get_computer_move(board, computer_letter):
  61.     """计算最佳落子位置"""
  62.     print("\n到我了,你离死亡不远了,啊哈哈哈哈(发出小月般的笑声)")
  63.     if computer_letter == 'X':
  64.         player_letter = 'Y'
  65.     else:
  66.         player_letter = 'X'

  67.     # 通过模拟,判断是否有能让电脑获胜的位置
  68.     for i in range(1, 10):
  69.         copy = board[:]
  70.         if is_free(copy, i):
  71.             make_move(copy, i, computer_letter)
  72.             if is_winner(copy, computer_letter):
  73.                 return i

  74.     # 通过模拟,判断是否有能阻止玩家获胜的位置
  75.     for i in range(1, 10):
  76.         copy = board[:]
  77.         if is_free(copy, i):
  78.             make_move(copy, i, player_letter)
  79.             if is_winner(copy, player_letter):
  80.                 return i

  81.     # 判断是否还有角角是空的
  82.     move = []
  83.     for i in [1, 3, 7, 9]:
  84.         if is_free(board, i):
  85.             move.append(i)
  86.     if move:
  87.         return random.choice(move)

  88.     # 判断中心是否是空的
  89.     if is_free(board, 5):
  90.         return 5

  91.     # 判断剩余位置(每条边的中间)是否为空
  92.     move = []
  93.     for i in [2, 4, 6, 8]:
  94.         if is_free(board, i):
  95.             move.append(i)
  96.     if move:
  97.         return random.choice(move)


  98. def play_again():
  99.     """询问玩家是否要再玩一次"""
  100.     print("\n再来一局呗!!!!(❤ ω ❤)")
  101.     print("请输入: (yes or no)")
  102.     return input().lower().startswith('y')
复制代码


咸小鱼一号:What!!!!!!小先生二号,你这代码西一块东一块的着实把我整懵了。。。。

咸小鱼二号:那我要不再整个发一遍吧

咸小鱼一号:..............

(写在最后:感谢每一位在咸小鱼成长道路上每一位帮助过咸小鱼的人

等等,再让我说一句,如果大家需要这本《python游戏编程快速上手》的话,可以在评论区留言或者私信我哦!!!

不说了,要上课了 ,拜拜啦

井字棋游戏.zip

2.64 KB, 下载次数: 34

评分

参与人数 3荣誉 +14 鱼币 +11 贡献 +7 收起 理由
Stubborn + 4 + 3 + 3 鱼C有你更精彩^_^
liuzhengyuan + 5 + 3 + 1 真厉害
qiuyouzhi + 5 + 5 + 3 鼓励一下~~

查看全部评分

小甲鱼最新课程 -> https://ilovefishc.com
回复

使用道具 举报

发表于 2020-3-16 14:10:41 | 显示全部楼层

回帖奖励 +1 鱼币

前排支持楼主!
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 1 反对 0

使用道具 举报

 楼主| 发表于 2020-3-16 14:13:27 | 显示全部楼层

谢谢宁,第一次写作品展示贴,还以为没人看呢(嘿嘿)
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 1 反对 0

使用道具 举报

发表于 2020-3-16 14:15:09 | 显示全部楼层

回帖奖励 +1 鱼币

加个界面就更好了
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2020-3-16 14:18:56 | 显示全部楼层

嗯嗯,我努力学学,嘿嘿
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-3-16 14:19:59 | 显示全部楼层
时荒小先生 发表于 2020-3-16 14:18
嗯嗯,我努力学学,嘿嘿

加油!!
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-3-16 14:32:45 | 显示全部楼层

回帖奖励 +1 鱼币

逐渐小月化,加油
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2020-3-16 14:40:01 | 显示全部楼层

嘿嘿谢谢宁
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-3-16 14:52:24 | 显示全部楼层

回帖奖励 +1 鱼币

有意思
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-3-16 15:13:40 | 显示全部楼层

回帖奖励 +1 鱼币

博主太可爱了吧
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-3-16 15:52:37 | 显示全部楼层

回帖奖励 +1 鱼币

有意思
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-3-16 18:26:13 | 显示全部楼层

回帖奖励 +1 鱼币

这个是不会赢得吗?我完了好几局都没赢
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2020-3-16 19:23:37 | 显示全部楼层
liuzhengyuan 发表于 2020-3-16 18:26
这个是不会赢得吗?我完了好几局都没赢

可以吧,虽然我也没赢几下
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-3-16 19:30:17 | 显示全部楼层
时荒小先生 发表于 2020-3-16 19:23
可以吧,虽然我也没赢几下

游戏有 Bug,可以走自己或电脑走过的地方
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2020-3-16 20:20:06 | 显示全部楼层
一个账号 发表于 2020-3-16 19:30
游戏有 Bug,可以走自己或电脑走过的地方

啊???我都没试过走已经走过的地方,我赶紧改改
谢谢宁提醒了
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2020-3-16 20:34:32 | 显示全部楼层
一个账号 发表于 2020-3-16 19:30
游戏有 Bug,可以走自己或电脑走过的地方

懂了,get_player_move函数有点问题,那个while语句可以改成这个
  1. while (move not in [str(i) for i in range(1, 10)]) or (not is_free(board, int(move))):
复制代码

我原来那个虽然not 只有一个,可是我加括号了呀
  1. while not ((move in [str(i) for i in range(1, 10)]) or is_free(board, int(move))):
复制代码

这个有点懵,那个is_free函数是空的时候返回True
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-3-16 20:52:33 | 显示全部楼层

回帖奖励 +1 鱼币

楼主有电子资源吗,小弟求一手1322055350@qq.com.另外,刚刚试了一下楼主的代码,出现了棋子可重复,而且九宫格的数字对应不是很清楚
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

 楼主| 发表于 2020-3-16 21:26:20 | 显示全部楼层
beatlemay 发表于 2020-3-16 20:52
楼主有电子资源吗,小弟求一手.另外,刚刚试了一下楼主的代码,出现了棋子可重复,而且九宫格的数字对应不 ...

链接:https://pan.baidu.com/s/1Do7VKvyjQ755AzcQVU2-ZQ
提取码:rwsv

顺带安利一个网站:偶书,上面有好多资源都可免费下载

如果对你有用的话,麻烦好评支持一下呗
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 1 反对 0

使用道具 举报

发表于 2020-3-16 23:06:34 | 显示全部楼层

回帖奖励 +1 鱼币

纯文字,好有耐心啊
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

发表于 2020-3-17 08:25:46 | 显示全部楼层

回帖奖励 +1 鱼币

  want《python游戏编程快速上手》
小甲鱼最新课程 -> https://ilovefishc.com
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2025-6-14 16:02

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表