最近在学习Python的时候看到一个乌龟吃鱼的练习,下面是我做这个练习的过程。

游戏规则如下:

1. 游戏背景为10*10; 
2. 游戏会自动生成1个乌龟和10条鱼; 
3. 它们移动方向随机; 
4. 乌龟最大移动能力为2; [-2,-1,1,2] 
5. 鱼最大移动能力为1; [-1,1] 
6. 当移动到场景边界,自动反方向移动; 
7. 乌龟初始化体能为100;每移动一次消耗体能1; 
8. 当乌龟和鱼的坐标重合,代表乌龟吃掉鱼,体能增加20;

9. 乌龟无体力或者鱼吃光,游戏结束;

因为乌龟和鱼移动方向是随机的,而且乌龟的移动步长也是随机的,因此引入random模块

import random as r

首先定义一个乌龟类

class Tortoise:step = 2 # 步长axis = [0, 0] # 初始化坐标area = [0, 0] # 初始化游戏场景大小def __init__(self, a, b): # 定义游戏场景大小self.area[0] = aself.area[1] = bdef start_axis(self, x = 0, y = 0): # 设定乌龟开始的坐标self.axis[0] = xself.axis[1] = yreturn self.axisdef move(self): # 乌龟的移动while True:temp_x = r.randint(-self.step, self.step)temp_y = r.randint(-self.step, self.step)if temp_x == 0 and temp_y == 0:continueself.axis[0] = self.axis[0] + temp_xself.axis[1] = self.axis[1] + temp_yfor i in range(0, 2): # 当移动到边界时往反方向移动if self.axis[i] < 0: # 0 --> -2 = 0 --> 2self.axis[i] = 0 - self.axis[i]if self.axis[i] > 10: # 10 --> 12 = 10 --> 8self.axis[i] = 20 - self.axis[i]return self.axis

定义一个鱼类

class Fish:step = 1 # 步长area = [0, 0] # 初始化坐标axis = [0, 0] # 初始化游戏场景大小def __init__(self, a, b): # 定义游戏场景大小self.area[0] = aself.area[1] = bdef start_axis(self): # 设定鱼开始的坐标self.axis[0] = r.randint(self.area[0], self.area[1])self.axis[1] = r.randint(self.area[0], self.area[1])return self.axisdef move(self, axis): # 鱼的移动self.axis = axiswhile True:temp_x = r.randint(-self.step, self.step)temp_y = r.randint(-self.step, self.step)if temp_x == 0 and temp_y == 0:continueself.axis[0] = self.axis[0] + temp_xself.axis[1] = self.axis[1] + temp_yfor i in range(0, 2): # 当移动到边界时往反方向移动if self.axis[i] < 0: # 0 --> -1 = 0 --> 1self.axis[i] = 0 - self.axis[i]if self.axis[i] > 10: # 10 --> 11 = 10 --> 9self.axis[i] = 20 - self.axis[i]return self.axis

接下来就可以开始写游戏的主程序了,首先,将乌龟和10条鱼放进游戏场景中

energy = 100
tort = Tortoise(1, 10)
tort_axis = tort.start_axis(1, 1) # 将乌龟放入场景内,设定初始坐标为(1,1)
print('-----------------------------')
print('乌龟的位置是:',tort_axis)
print('乌龟的体力:%d' % energy)
fish = Fish(1, 10)
fish_axis = {}
flag = 1
while True: # 将10条鱼分别放入不同的坐标中temp_axis = fish.start_axis()if flag == 1 and temp_axis != tort_axis:fish_axis.setdefault(flag, 0)fish_axis[flag] = temp_axisprint('Fish%d的位置是:' % flag, fish_axis[flag])flag += 1if  flag > 1 and temp_axis != fish_axis[flag - 1] and temp_axis != tort_axis:fish_axis.setdefault(flag, 0)fish_axis[flag] = temp_axisprint('Fish%d的位置是:' % flag, fish_axis[flag])flag += 1if flag > 10:break

然后实现乌龟和鱼在场景中移动,并设立胜利条件

while True:    num = list(fish_axis.keys())length = len(num)for i in range(0, length): # 小鱼的移动flag = 0while True:temp_axis = fish.move(fish_axis[num[i]])if i == 0:fish_axis[num[i]] = temp_axis.copy()print('fish%d的位置是:' % num[i], fish_axis[num[i]])flag = 1elif temp_axis != fish_axis[num[i - 1]]:# 字典中的前一项而不是i-1fish_axis[num[i]] = temp_axis.copy()print('fish%d的位置是:' % num[i], fish_axis[num[i]])flag = 1if flag == 1:breaktort_axis = tort.move() # 乌龟的移动print('乌龟的位置是:',tort_axis)energy -= 1# 判断小鱼是否被乌龟吃掉for i in fish_axis:if fish_axis[i] == tort_axis:print('fish%s被吃掉' % i)fish_axis.pop(i)print('乌龟回复20点体力')energy += 20print('乌龟的体力:%d' % energy)print('-----------------------------')if fish_axis == {}:print('乌龟获胜')breakelif energy == 0:print('小鱼获胜')break

完成以后开始运行,结果......居然进入了死循环!!!

用ctrl+c终结程序后观察错误信息发现错误 temp_axis = fish.start_axis()位置

Traceback (most recent call last):File "C:\Users\Administrator\AppData\Local\Programs\Python\Python36\example\test_37_1.py", line 64, in <module>temp_axis = fish.start_axis()File "C:\Users\Administrator\AppData\Local\Programs\Python\Python36\example\test_37_1.py", line 36, in start_axisself.axis[1] = random.randint(self.area[0], self.area[1])File "C:\Users\Administrator\AppData\Local\Programs\Python\Python36\lib\random.py", line 220, in randintreturn self.randrange(a, b+1)File "C:\Users\Administrator\AppData\Local\Programs\Python\Python36\lib\random.py", line 196, in randrangereturn istart + self._randbelow(width)File "C:\Users\Administrator\AppData\Local\Programs\Python\Python36\lib\random.py", line 233, in _randbelowwhile r >= n:
KeyboardInterrupt

在仔细观察错误所在位置的程序发现错误位置为下面划线部分,原因是我使用的是赋值语句,这就说明fish_axis[flag]和temp_axis的地址是一样的,也就是说在temp_axis = fish.start_axis()改变temp_axis的值时fish_axis[flag]的值也改变了,因此if语句中的条件temp_axis != fish_axis[flag - 1]永远不成立,while语句进入死循环。

while True: # 将10条鱼分别放入不同的坐标中temp_axis = fish.start_axis()if flag == 1 and temp_axis != tort_axis:fish_axis.setdefault(flag, 0)fish_axis[flag] = temp_axisprint('Fish%d的位置是:' % flag, fish_axis[flag])flag += 1if  flag > 1 and temp_axis != fish_axis[flag - 1] and temp_axis != tort_axis:fish_axis.setdefault(flag, 0)fish_axis[flag] = temp_axisprint('Fish%d的位置是:' % flag, fish_axis[flag])flag += 1if flag > 10:break

于是我将赋值语句改为浅复制fish_axis[flag] = temp_axis.copy(),这然fish_axis[flag]的地址和temp_axis的地址就不一样了。

解决了这个问题之后,我又运行了一遍,结果又又又报错了

Traceback (most recent call last):File "C:\Users\Administrator\AppData\Local\Programs\Python\Python36\example\test_37_1.py", line 125, in <module>for i in fish_axis:
RuntimeError: dictionary changed size during iteration

错误信息显示错误在for i in fish_axis:语句中,错误类型为RuntimeError,在反反复复前前后后看了几遍之后还是看不出来有什么地方不对,只好求助万能的度娘,在大佬的指导下终于发现了错误。

for i in fish_axis:if fish_axis[i] == tort_axis:print('fish%s被吃掉' % i)fish_axis.pop(i)print('乌龟回复20点体力')energy += 20

上面这种写法在python2中是可与运行的,但是在python3中就会报错,因为在python3中keys()返回的是dict_keys而不是list此如果想遍历的同时删除字典中的元素应该改写为:

for i in list(fish_axis.keys()):if fish_axis[i] == tort_axis:print('fish%s被吃掉' % i)fish_axis.pop(i)print('乌龟回复20点体力')energy += 20

这个问题解决之后终于可以运行了,下面附上完整的程序。

import random as r
class Tortoise:step = 2 # 步长axis = [0, 0] # 初始化坐标area = [0, 0] # 初始化游戏场景大小def __init__(self, a, b): # 定义游戏场景大小self.area[0] = aself.area[1] = bdef start_axis(self, x = 0, y = 0): # 设定乌龟开始的坐标self.axis[0] = xself.axis[1] = yreturn self.axisdef move(self): # 乌龟的移动while True:temp_x = r.randint(-self.step, self.step)temp_y = r.randint(-self.step, self.step)if temp_x == 0 and temp_y == 0:continueself.axis[0] = self.axis[0] + temp_xself.axis[1] = self.axis[1] + temp_yfor i in range(0, 2): # 当移动到边界时往反方向移动if self.axis[i] < 0: # 0 --> -2 = 0 --> 2self.axis[i] = 0 - self.axis[i]if self.axis[i] > 10: # 10 --> 12 = 10 --> 8self.axis[i] = 20 - self.axis[i]return self.axis
class Fish:step = 1 # 步长area = [0, 0] # 初始化坐标axis = [0, 0] # 初始化游戏场景大小def __init__(self, a, b): # 定义游戏场景大小self.area[0] = aself.area[1] = bdef start_axis(self): # 设定鱼开始的坐标self.axis[0] = r.randint(self.area[0], self.area[1])self.axis[1] = r.randint(self.area[0], self.area[1])return self.axisdef move(self, axis): # 鱼的移动self.axis = axiswhile True:temp_x = r.randint(-self.step, self.step)temp_y = r.randint(-self.step, self.step)if temp_x == 0 and temp_y == 0:continueself.axis[0] = self.axis[0] + temp_xself.axis[1] = self.axis[1] + temp_yfor i in range(0, 2): # 当移动到边界时往反方向移动if self.axis[i] < 0: # 0 --> -1 = 0 --> 1self.axis[i] = 0 - self.axis[i]if self.axis[i] > 10: # 10 --> 11 = 10 --> 9self.axis[i] = 20 - self.axis[i]return self.axis
# 游戏开始
energy = 100
tort = Tortoise(1, 10)
tort_axis = tort.start_axis(1, 1) # 将乌龟放入场景内,设定初始坐标为(1,1)
print('-----------------------------')
print('乌龟的位置是:',tort_axis)
print('乌龟的体力:%d' % energy)
fish = Fish(1, 10)
fish_axis = {}
flag = 1
while True: # 将10条鱼分别放入不同的坐标中temp_axis = fish.start_axis()if flag == 1 and temp_axis != tort_axis:fish_axis.setdefault(flag, 0)fish_axis[flag] = temp_axis.copy()print('Fish%d的位置是:' % flag, fish_axis[flag])flag += 1if  flag > 1 and temp_axis != fish_axis[flag - 1] and temp_axis != tort_axis:fish_axis.setdefault(flag, 0)fish_axis[flag] = temp_axis.copy()print('Fish%d的位置是:' % flag, fish_axis[flag])flag += 1if flag > 10:break
print('----------游戏开始-----------')
# 乌龟和小鱼的移动
while True:    num = list(fish_axis.keys())length = len(num)for i in range(0, length): # 小鱼的移动flag = 0while True:temp_axis = fish.move(fish_axis[num[i]])if i == 0:fish_axis[num[i]] = temp_axis.copy()print('fish%d的位置是:' % num[i], fish_axis[num[i]])flag = 1elif temp_axis != fish_axis[num[i - 1]]:# 字典中的前一项而不是i-1fish_axis[num[i]] = temp_axis.copy()print('fish%d的位置是:' % num[i], fish_axis[num[i]])flag = 1if flag == 1:breaktort_axis = tort.move() # 乌龟的移动print('乌龟的位置是:',tort_axis)energy -= 1#-------------------------# 判断小鱼是否被乌龟吃掉for i in num:if fish_axis[i] == tort_axis:print('fish%s被吃掉' % i)fish_axis.pop(i)print('乌龟回复20点体力')energy += 20print('乌龟的体力:%d' % energy)#-------------------------print('-----------------------------')if fish_axis == {}:print('乌龟获胜')breakelif energy == 0:print('小鱼获胜')break

【Python练习】乌龟吃鱼小游戏相关推荐

  1. JavaScript实现猫吃鱼小游戏

    贪吃猫小游戏 作为一名前端人员,撸猫我决定使用面向对象的方式书写贪吃猫小游戏,灵感来自有贪食蛇小游戏. 我们可以把整个游戏看成是一个游戏类,游戏类可以有各种各样的属性. 我们可以把贪吃猫中的猫作为一个 ...

  2. Python实现的吃东西小游戏

    一.设计目的 课程设计教学目的: 本课程设计是本专业的一门重要实践性教学环节.在学习了专业基础课和<Python程序设计>课程的基础上,本课程设计旨在加深对Python程序设计的认识,对P ...

  3. python小鱼_Python面向对象练习-通过pygame改良乌龟吃鱼

    先看看最后效果 图片的话是从网上小鱼儿那个案例里面拿的,实现的功能如下: 是通过方向键操作乌龟,进行吃鱼 吃鱼的时候根据乌龟的x,y坐标和鱼的x,y进行检测,在碰撞区域则干掉这条鱼 背景音乐和吃鱼音乐 ...

  4. python 苹果试玩_python实现吃苹果小游戏

    本文实例为大家分享了python实现吃苹果小游戏的具体代码,供大家参考,具体内容如下 1.公共类模块 import pygame from pygame.rect import Rect def pr ...

  5. 基于Python的水母吃鱼游戏的设计与实现

    源码获取:https://www.bilibili.com/video/BV1Ne4y1g7dC/ 基于Python的水母吃鱼游戏的设计与实现

  6. Python-小游戏-乌龟吃鱼

    #讲道理乌龟吃鱼的嘛? 先上代码,虽然感觉很多地方可以优化 import random import timeclass Tortoise:x = random.randint(0,10)y = ra ...

  7. Python初学者-双人对战小游戏

    --------------------------------------Python初学者 学习历程分享------------------------------------ 小游戏-双人决战之 ...

  8. 学生学python编程---实现贪吃蛇小游戏+源码

    学生学python编程---实现贪吃蛇小游戏+源码 前言 主要设计 1.蛇的表示 2.蛇怎么移动? 3.玩家控制小蛇移动功能的实现 4.如何判定游戏结束? 应用知识点 1.python知识点 1.1 ...

  9. 基于Python实现的吃豆人游戏设计

    资源下载地址:https://download.csdn.net/download/sheziqiong/86817091 资源下载地址:https://download.csdn.net/downl ...

  10. 优秀课程案例:如何用scratch实现小猫吃鱼的游戏

    如何用scratch实现小猫吃鱼的游戏 一.学习目标: 二.程序效果: 三.算法分析: 1.对于角色小鱼,通过移到鼠标指针.重复执行的积木可以实现,小鱼随着鼠标指针动而动,用条件循环:重复执行直到这个 ...

最新文章

  1. 7.Spring Security 退出登录
  2. mysql client 5.1.34_mysql最新版
  3. 【Android 异步操作】手写 Handler ( Handler 发送与处理消息 | Handler 初始化 | 完整 Handler 代码 )
  4. Oracle(21)—— Linux环境部署Oracle11g数据库
  5. WebPart(汇总)[转载]
  6. ARMCM3汇编指令
  7. 【opencv系列07】OpenCV4.X图像基本操作
  8. Android BottomNavigation Demo
  9. 预售┃没有标题,配得上这款“俄罗斯方块”
  10. css3加载中动画效果,CSS3实现加载中的动画效果
  11. jquery添加div实现消息聊天框
  12. 电信路由器怎么设置虚拟服务器,电信宽带怎么设置路由器?
  13. 求邻接矩阵matlab,如何使用MATLAB绘制邻接矩阵
  14. 计算机技术排除故障网站有哪些,电脑技术交流之常见故障排除【详解】
  15. Mac OS X 下安装Tableau Desktop Pro for Mac 10.2.0
  16. 7-3 将整数转换为汉字大写数字
  17. 扫码点餐小程序项目后端开发之“01.搭建服务器基础设施”
  18. 直接插入法(C语言版本)
  19. 基础C语言知识串串香10☞数组字符串结构体联合体枚举
  20. 【逆向工程】在PE结构空白区段插入代码

热门文章

  1. 大数据中心建设一哄而上 人才技术制约产业发展
  2. 51单片机简易MP3程序驱动蜂鸣器播放
  3. html表单有几部分组成,网页制作时表单由哪两部分组成
  4. 数据库工程师中级考试——下午场知识点讲解
  5. python操作word.7.19笔记
  6. lwj_C#_string类方法 可变字符串
  7. win10专业版有必要吗_Win10有哪些版本 Win10各版本有什么区别【区别介绍】
  8. navicat 创建模型
  9. 常见软件非功能性需求描述案例
  10. 计算机u盘能直接拨出吗,电脑怎么直接拔出U盘而不丢失数据|电脑可以不用弹出设备直接拔出U盘吗...