2022软工K班结对编程任务
一.结对探索(4分)
1.1队伍基本信息(1分)
结对编号:55;队伍名称:算法佬与小白;
姓名 | 学号 | 博客链接) | 具体分工 |
---|---|---|---|
翁熠霆 | 032004124 | 博客链接 | 学习进行UI设计 |
吴兴元 | 032004127 | 博客链接 | 进行程序的算法设计(C++和Python) |
1.2描述结对的过程(1分)
-
翁熠霆
我环顾了一圈同班的同学,自觉我这样的菜鸡可能入队困难。可能只有同宿舍有强大算法基础的兴元大大可能可以收留我。然后前去软磨硬泡,最后兴元大大无奈,想到舍友做队友,团队沟通可能可以更顺畅一些,也就屈尊接受了我的恳求。然后我就取了这个队名。 -
吴兴元
没有熠霆说得这么夸张,就是他问我是否组队,我考虑到在同一个宿舍交流比较方便,就与他组队了
1.3非摆拍的两人在讨论设计或解读编程过程的照片(2分)
《非摆拍图》
二.原型设计(16分)
2.1原型工具的选择(2分)
本来使用的墨刀,设计了一版后发现自己没能学会用python GUI tkinter 库将设计好的原型接入。而后就只能完全迁就自己羸弱的代码能力。用最基础的GUI pack布局和grid布局来说实现所谓的UI设计(所以从成果上来看,这个UI和设计是十分的粗糙和青涩的)
2.2遇到的困难和解决方法(3分)
一开始完全没有思路,根本不知道从哪里下手,总是开发从前玩4399的丰富经验,想了好多东西,然后想法非常美好,实际操作起来,发现好复杂做不来。之后一个一个分解功能,一步一步简化功能,从最基础的学起。
开始查找资料,在bilibli学习。秉持着,不要看我想要什么想做什么,要看我会什么,我要怎么用我会的那三脚猫功夫整出来一个看起来还那么像回事的窗口界面。最后,也是在一步一步的妥协下,在DDL之前整出来一个粗糙的产品。
2.3 原型作品链接(5分)
暂无(因为最开始最开始设计的那一版本原型设计因为代码工具选择的原因,最终没能实际应用到最后的成品)
2.4原型界面图片展示
(上传的图片都被压缩过了,有点糊,但信息可见。见谅)
游戏窗口一:
登录尝试失败窗口一:
登录尝试成功窗口二:
选择难度窗口
实操游戏窗口界面(因为python tkinter库的多块区域画布创建操作存在难点使得我难以将18张骰子贴图链接绑定到相应的位置,见谅)
三.编程实现(16分)
3.1网络接口的使用(2分)
暂无。因为只设计了单机模式人机对战,没有设计本地双人对抗,更谈不上设计联网的联机对抗了
3.2 代码组织和内部实现设计(2分)
U的设计结构(这里的1-6的gif是我寻找的骰子点数抠图素材)
代码实现:
初始化
def init():
for i in range(0,3) :
player.append([0,0,0])
ai.append([0,0,0])
判断是否为已经填满
def check():
p=0
a=0
for i in range(0,3):
for j in range(0,3):
if(player[i][j]==0):
p=1
if(ai[i][j]==0):
a=1
if(p==1 and a==1):
return True
else:
return False
玩家移动
def player_move(x):
c = input()
i = 0
if(c=='K'):
i=0
elif(c=='E'):
i=1
elif(c=='X'):
i=2
else:
print(c,' line does not exist,please input again:')
player_move(x)
return
flag=False
for j in range(0,3):
if(player[i][j]==0):
flag=True
player[i][j]=x
for l in range(0,3):
if(ai[i][l]==x):
ai[i][l]=0
break
if(flag==False):
print(c,' line is full,please input again:')
player_move(x)
return
电脑移动
def ai_move(y):
i=random.randint(0, 2)
flag = False
for j in range(0,3):
if(ai[i][j]==0):
flag = True
ai[i][j]=y
for l in range(0,3):
if(player[i][l]==y):
player[i][l]=0
break
if (flag == False):
ai_move(y)
return
if (i == 1):
print("the computer moves in K line")
elif (i == 2):
print("the computer moves in E line")
elif (i == 2):
print("the computer moves in X line")
判断胜负
def win():
ai_score = 0
player_score = 0
cnt = []
fg = []
for i in range(0,3):
cnt.append([0, 0, 0, 0, 0, 0, 0])
cnt.append([0, 0, 0, 0, 0, 0, 0])
fg.append([0, 0, 0, 0, 0, 0, 0])
fg.append([0, 0, 0, 0, 0, 0, 0])
for j in range(0,3):
if(player[i][j]!=0):
cnt[0][player[i][j]]+=1
if(ai[i][j]!=0):
cnt[1][ai[i][j]]+=1
for j in range(0,3):
if(player[i][j]!=0):
if(fg[0][player[i][j]]==0):
fg[0][player[i][j]]=1
player_score+=player[i][j]*cnt[0][player[i][j]]*cnt[0][player[i][j]]
if(ai[i][j]!=0):
if(fg[1][ai[i][j]]==0):
fg[1][ai[i][j]]=1
ai_score+=ai[i][j]*cnt[1][ai[i][j]]*cnt[1][ai[i][j]]
cnt = []
fg = []
print("your score is:",player_score)
print("computer score is:",ai_score)
if(player_score>ai_score):
return True
else:
return False
设计三种难度
def easy_num():
a=random.randint(3, 5)
b=random.randint(0, 1)
x=a+b
return x
def normal_num():
x=random.randint(1, 6)
return x
def hard_num():
a=random.randint(1, 2)
b=random.randint(0, 1)
c=random.randint(0, 1)
d=random.randint(0, 1)
x=a+b+c+d
return x
def easy_mode():
cnt=0
while(check()):
cnt+=1
if(cnt&1):
x=0
if(cnt%3==0):
x=normal_num()
else:
x=easy_num()
print("the score you get is:",x)
print("please input the line you want to move:")
player_move(x)
else:
y=0
if(cnt%4==0):
y=normal_num()
else:
y=hard_num()
print("the score computer get is:",y)
ai_move(y)
show()
def normal_mode():
cnt=0
while(check()):
cnt+=1
if(cnt&1):
x=normal_num()
print("the score you get is:",x)
print("please input the line you want to move:")
else:
y=normal_num()
print("the score computer get is:",y)
ai_move(y)
show()
def hard_mode():
cnt=0
while(check()):
cnt+=1
if(cnt&1):
x=0
if(cnt%3==0):
x=normal_num()
else:
x=hard_num()
print("the score you get is:",x)
print("please input the line you want to move:")
player_move(x)
else:
y=0
if(cnt%4==0):
y=normal_num()
else:
y=hard_num()
print("the score computer get is:")
ai_move(y)
show()
3.3 说明算法关键以及关键部分的流程图(2分)
3.4 贴出重要的/有价值的代码片段并解释(2分)
AI算法时间紧迫,学习成本和调试都太过费时,就直接使用随机数的代码逻辑实现了简单的AI策略
生成一定概率较大的数,即通过在3到5之间取随机数a并在0到1取随机数b,两者相加而得:
def easy_num():
a=random.randint(3, 5)
b=random.randint(0, 1)
x=a+b
return x
生成一定概率较小的数:
def hard_num():
a=random.randint(1, 2)
b=random.randint(0, 1)
c=random.randint(0, 1)
d=random.randint(0, 1)
x=a+b+c+d
return x
生成一个正常概率的数:
def normal_num():
x=random.randint(1, 6)
return x
简单模式:玩家更倾向于得到较大的数,电脑更倾向于得到较小的数
def easy_mode():
cnt=0
while(check()):
cnt+=1
if(cnt&1):
x=0
if(cnt%3==0):
x=normal_num()
else:
x=easy_num()
print("the score you get is:",x)
print("please input the line you want to move:")
player_move(x)
else:
y=0
if(cnt%4==0):
y=normal_num()
else:
y=hard_num()
print("the score computer get is:",y)
ai_move(y)
show()
普通模式:玩家与电脑得到每个数字的概率相同
def normal_mode():
cnt=0
while(check()):
cnt+=1
if(cnt&1):
x=normal_num()
print("the score you get is:",x)
print("please input the line you want to move:")
else:
y=normal_num()
print("the score computer get is:",y)
ai_move(y)
show()
困难模式:玩家更倾向于得到较小的数,电脑更倾向于得到较大的数
def hard_mode():
cnt=0
while(check()):
cnt+=1
if(cnt&1):
x=0
if(cnt%3==0):
x=normal_num()
else:
x=hard_num()
print("the score you get is:",x)
print("please input the line you want to move:")
player_move(x)
else:
y=0
if(cnt%4==0):
y=normal_num()
else:
y=hard_num()
print("the score computer get is:")
ai_move(y)
show()
3.5性能分析与改进(2分)
原先只有设计了一个简单模式。
之后经过兴元的算法更新,实现了三种模式的本地人机对战
3.6 单元测试(2分)
判断是否游戏结束,并弹出窗口说明获胜者
def check():
p=0
a=0
for i in range(0,3):
for j in range(0,3):
if(player[i][j]==0):
p=1
if(ai[i][j]==0):
a=1
if(p==1 and a==1):
return True
else:
return False
self.label07 = Label(self, text="恭喜玩家,游戏胜利!", width=3, height=1,
fg="black", bg="white"command = win).grid(row=9, column=3, sticky=NSEW)
3.7 贴出GitHub的代码签入记录,合理记录commit信息(2分)
暂无。(并没有来得及使用GITHUB进行版本管理)
四、总结反思(11分)
4.1本次任务的PSP表格(2分)
PSP2.1 | Personal Software Process Stages | 预估耗时(分钟) | 实际耗时(分钟) |
---|---|---|---|
Planning | 计划 | 30 | 72 |
· Estimate | · 估计这个任务需要多少时间 | 10 | 10 |
Development | 开发 | 600 | 700 |
· Analysis | · 需求分析 (包括学习新技术) | 1200 | 1200 |
· Design Spec | · 生成设计文档 | 10 | 55 |
· Design Review | · 设计复审 | 10 | 55 |
· Coding Standard | · 代码规范 (为目前的开发制定合适的规范) | 60 | 55 |
· Design | · 具体设计 | 60 | 120 |
· Coding | · 具体编码 | 300 | 720 |
· Code Review | · 代码复审 | 50 | 50 |
· Test | · 测试(自我测试,修改代码,提交修改) | 30 | 50 |
Reporting | 报告 | 90 | 180 |
· Test Repor | · 测试报告 | 30 | 60 |
· Size Measurement | · 计算工作量 | 10 | 20 |
· Postmortem & Process Improvement Plan | · 事后总结, 并提出过程改进计划 | 10 | 100 |
· 合计 | 2500 | 3567 |
4.2学习进度条(每周追加)(2分)
- 吴兴元
第N周 | 新增代码(行) | 累计代码(行) | 本周学习耗时(小时) | 累计学习耗时(小时) | 重要成长 |
---|---|---|---|---|---|
1 | 218 | 218 | 1.5 | 1.5 | 理解算法逻辑,设计并调试debug出一个可行的本地人机对战的逍遥骰玩法 |
2 | 233 | 451 | 3 | 4.5 | 理解并深化了算法逻辑,并根据实验设计的要求,基于随机数算法设计出了三种不同难度的电脑投点 |
- 翁熠霆
第N周 | 新增代码(行) | 累计代码(行) | 本周学习耗时(小时) | 累计学习耗时(小时) | 重要成长 |
---|---|---|---|---|---|
2 | 290 | 741 | 30 | 40 | 学习并强化了python GUI的使用,了解设计原型及工具墨刀(虽然后面没有用上) |
4.3最初想象的产品形态,原型设计产品,软件开发成果三者的差距如何(2分)
差距是真的非常大,最初想象的产品形态想着,做个看的过去的4399中等质量的小游戏应该也就是洒洒水(画大饼),原型设计设计的非常便利人性化,尽可能的代入玩家游玩的角度来设计游戏——直到自己要来用简单局限的python GUI来实现我的设计…当然比最初想象的差距很大,毕竟增加一个需求,就要增加代码,一加代码,bug和错误就来了,就需要debug慢慢找。然而一个初学者,真的没那个能力Debug.随着DDL一步一步逼近,最终不断否决最初的设想,不断缩减需求。转变为能跑的动就是胜利,躺平了。
4.4评价你的队友(2分)
-
翁熠霆
兴元很忙。一方面本学年担任两位老师的理论课助教,另一方面,还在学习算法。兴元在拿到题目的当天晚上就以一个非常高的效率,个把小时内就用他擅长的C++ 实现了逍遥骰的随机数本地对战代码。并且非常高效的向我分享了自己的畅享,并且在后续的工作起到了很好的督促我进度的工作。奈何术业有专攻,我和兴元夸下海口,有我全权负责原型设计和UI实现,最终却力有不逮,只能交出这样一份马马虎虎的答卷。
-
吴兴元
熠霆其实已经相当努力了,几乎是零基础可以达到现在的水平,真的是相当不容易。
4.5 结对编程作业的心得体会(3分)
- 翁熠霆
这次作业的只用了python的tkinter库来实现简易的GUI编写,交互全部用python的tkinter库实现,没能及时学习并运用任何框架,交互的实现不仅对我的框架模块调用能力带来了很大的挑战费,而且就结果呈现的来说,实现的效果也不尽如人意。没能做到实时显示分数——主要是归结于DeBug的能力不足,之前都没写过大代码,基本没用DeBug,现在浏览器的DeBug也会一些,总的心得体会就是项目看着很难,自己做下来,初期学会做简易的UI还是有一些笑笑的成就感的。但后期传参出现了诸多问题,而且没能继续更进一步,也是给了我浇了一盆冷水。最后也没能力实现全部需求,以及AI,以及网络,以及小程序下,说到最后,就是能跑就行,唉…
- 吴兴元
原本想设计一些人工智能算法去训练的,但是能力与时间都不充足,实在是力有未逮,就只能写随机数了。