我只想要一些关于如何改进的意见/建议。
#import
import string
import random
import time
import pickle
#create grid
def create_grid(size,lastcell,numberofmines):
grid = []
for i in range(size):
row = ['0']*size
grid.append(row)
mines = create_mines(grid,lastcell,numberofmines,size)
p = surrounding(grid,size)
p.numberofsurrounding(grid,size)
return (grid,mines)
#show the grid
def showgrid(grid,size):
horizontal = ' -'+size*'----'
collum = ' '
#writes the collmum numbers
for i in string.ascii_uppercase[:size]:
collum += (i+ ' ')
print (collum,'\n',horizontal)
# writes row numbers
for idx,i in enumerate(grid, start=1):
row = str(idx)
row += '|'
for j in i:
row = row+' '+j+' |'
print (row+'\n'+horizontal)
#generated random cordinates
def generate_cordinate(size):
a = random.randint(0,size-1)
b = random.randint(0,size-1)
return (a,b)
#class fro surrounding
class surrounding(object):
def __init__(self,grid,size):
self.grid = grid
self.size = size
#creates a list with the surrounding cell for every cell
def surrounding_cells(self,row_num,col_num,size):
surronding = []
for i in range(-1,2):
for j in range(-1,2):
if i == 0 and j == 0:
continue
elif -1<row_num+i<size and -1<col_num+j<size:
surronding.append((row_num+i,col_num+j))
return (surronding)
#checks how many is mines in the surromding cells
def numberofsurrounding(self,grid,size):
for row_num,row in enumerate(grid):
for col_num,col in enumerate(row):
if col!='*':
#finds value of surrounding cell
values = [grid[r][c] for r,c in self.surrounding_cells(row_num, col_num,size)]
# counts how many are mines
grid[row_num][col_num] = str(values.count('*'))
# Generate mines
def create_mines(grid,lastcell,numberofmines,size):
mines = []
for i in range(numberofmines):
cell = generate_cordinate(size)
while cell==(lastcell[0],lastcell[1]) or cell in mines:
cell = generate_cordinate(size)
mines.append(cell)
for i,j in mines: grid[i][j] = '*'
return mines
#"shows the choose cell
def showcell(grid,showngrid,row_num,col_num,size):
#if you pick already shown cell
if showngrid[row_num][col_num]!='-':
return
#shows the cell
showngrid[row_num][col_num] = grid[row_num][col_num]
#if the cells value is 0 controll nearby cells
if grid[row_num][col_num] == '0':
p = surrounding(grid,size)
for r,c in p.surrounding_cells(row_num,col_num,size):
showcell(grid,showngrid,r,c,size)
# replay
def replay():
val = input('What to go to mainmenu?(yes or no):')
if val.lower() == 'yes':
mainmenu('mainmenu')
elif val.lower() == 'no':
print('bye')
quit()
else:
print('\nonly yes or no')
replay()
#function for flags
def putflag(showngrid,row_num,col_num,flags):
# adds flag
if showngrid[row_num][col_num]=='-':
showngrid[row_num][col_num] = 'F'
flags.append((row_num,col_num))
#remove flag
elif showngrid[row_num][col_num]=='F':
showngrid[row_num][col_num] = '-'
flags.remove((row_num,col_num))
#function for picking the size/ number of mines
def pickvalues():
size = goodvalues(4,10,message= '\nPick size of grid(4-9):')
numberofmines = goodvalues(size, ((size**2) -5), message= 'the number of mines has to be between ' + str(size) + ' and '+ str((size**2-6))+ '\nhow many mines::' )
return size,numberofmines
#cheecks the values, (size/numberofmines)
def goodvalues(min,max,message):
a = False
while a == False:
try:
värde = int(input(message))
if värde not in range(min,max):
a = False
if värde in range(min,max):
a = True
except ValueError:
print("\nchoose an interger\n")
a = False
return (värde)
def name(message):
username = input(message)
if len(username) <= 0 or len(username) >10:
name('Pick a username:')
return username
#mainprogramme
def play():
username = name('pick a username(1-10signs):')
size,numberofmines = pickvalues()
start_time = time.time()
showngrid = [['-' for i in range(size)] for i in range(size)] #skapar en kopia av spelplanen utan mines
showgrid(showngrid,size)
first_round = True
flags = []
while True:
while True:
flag = False
lastcell = input('pick cell: ')
try:
if lastcell[2].lower() == 'f':
flag = True
except IndexError:
pass
try:
#Gör om kordinaterna till siffror
lastcell = (int(lastcell[1])-1,string.ascii_lowercase.index(lastcell[0].lower()))
break
except (IndexError,ValueError):
showgrid(showngrid,size)
print ("cant choose that cell")
#skapar spelplanen efter första rundan
if first_round == True:
first_round = False
grid,mines = create_grid(size,lastcell,numberofmines)
row_num = lastcell[0]
col_num = lastcell[1]
#lägger flag
if flag == True:
putflag(showngrid,row_num,col_num,flags)
else:
try:
if grid[row_num][col_num] == '*':
result('Game Over',grid,showngrid,start_time,numberofmines,size,username)
else:
showcell(grid,showngrid,row_num,col_num,size)
except IndexError:
print('\ncant choose that cell\n')
#kcheeks for victory
controll(grid,showngrid,size,numberofmines,start_time,username,flags,mines)
showgrid(showngrid,size)
#kfunction to check fo victory
def controll(grid,showngrid,size,numberofmines,start_time,username,flags,mines):
empty_cells = 0
cellswithmines = 0
for x in range(len(showngrid)):
y = (showngrid[x].count('-'))
empty_cells += y
for x in range(len(grid)):
z = (grid[x].count('*'))
cellswithmines += z
if empty_cells == cellswithmines or set(flags) == set(mines):
result('YOU WON',grid,showngrid,start_time,numberofmines,size,username)
#shows the reuslt (lose/win)
def result(result,grid,showngrid,start_time,numberofmines,size,username):
if result == 'Förlust':
print('Game Over!')
showgrid(grid,size)
replay()
if result == 'Vinst':
print('*********** YOU WON! ************')
showgrid(showngrid,size)
score(start_time,numberofmines,size,username)
# calculates the score
def score(start_time,numberofmines,size,username):
finish_time = time.time()
time = start_time - finish_time
user_score = (int((1000 * ((int(numberofmines))**2 / (int(size))) - (1.5 * time))), username)
highscore(user_score)
#Opens highscore and adds you on the list (if youre good enough)
def highscore(user_score):
with open ('high_scorelist.dat','rb') as file:
high_scorelist = pickle.load(file)
if user_score[0] > high_scorelist[len(high_scorelist)-1][0]:
print ("YOU MADE IT!\n\n")
high_scorelist.append(user_score)
high_scorelist.sort(reverse=True)
del high_scorelist[len(high_scorelist)-1]
with open('high_scorelist.dat','wb') as file:
pickle.dump(high_scorelist,file)
show_highscore(high_scorelist)
return (high_scorelist)
else:
show_highscore(high_scorelist)
#prints the highscore table
def show_highscore(high_scorelist):
print('****highscore***\n\n')
print('| name | score |')
for i in range(10):
print('| ',high_scorelist[i][1],' '*(17-len(high_scorelist[i][1])), end='|')
print(high_scorelist[i][0], ' ' *(12- len(str(high_scorelist[i][0]))), end= '|\n')
replay()
#mainmenu
def mainmenu(message):
print(message)
a = str(input('1. Helpmenu\n2. play\n3. Highscore\n4. quit'))
if a == '1':
help()
elif a =='2':
play()
elif a =='3':
highscore(user_score=(0,'test'))
elif a == '4':
print('Hej då!')
quit()
else:
mainmenu(message='choose 1-4')
#helpmenu
def help():
print('what can i help you with?')
while True:
try:
x = int(input('1. bla\n2. blar\n3. bla\n4. play'))
if x == 1:
a = input(('bla '))
elif x == 2:
a = input(('bla'))
elif x == 3:
a = input('bla')
elif x == 4:
mainmenu(message='here we go')
except ValueError:
print('\nchoose\n')
#opens mainmenu
mainmenu(message='MINeSWeeper!')发布于 2015-12-07 23:07:17
我试着玩你的游戏,无论是在Python 2中(经过一些修改之后),还是在Python 3中,我都无法使游戏逻辑正常工作。所以这里和那里确实有一些bug!
snake_case -不要在一起!通常情况下,您不会这样写,在编写代码时也不会这样做。create_grid()很好,但是showgrid(),numberofsurrounding()等等.保持一致是这里的关键!for和while循环以及if语句之后插入空行,以帮助分隔代码的逻辑部分。所以,与你的原作不同:
#创建网格def create_grid(大小、单元格、地雷数):grid = [] for i in range( size):row = “0”*size grid.append(行) mines =create_mines(网格、单元格、地雷数、大小)p=周围(网格、大小)p.numberofsurrounding(网格、大小)返回(网格、地雷)
将这四个注释应用于您的第一个函数create_grid(),结果如下:
def create_grid(size, lastcell, number_of_mines):
"""Initialize the grid with mines, and return grid and mine posistions."""
grid = []
for i in range(size):
row = ['0']*size
grid.append(row)
mines = create_mines(grid, lastcell, number_of_mines, size)
p = surrounding(grid, size)
p.number_of_surrounding(grid,size)
return (grid, mines)使用+进行大量字符串连接,这实际上不是构建字符串的好方法。您最好使用string.format,并为整个行创建模式。
下面是如何在show_grid(grid, size)中执行此操作的示例:
def show_grid(grid, size):
"""Print the full grid with headers and dividers."""
horizontal_line = ' -{}'.format('-----'*size)
ROW_PATTERN = ' {:>} | {} |'
print(' {}'.format(' '.join(string.ascii_uppercase[:size])))
print(horizontal_line)
# Write rows
for idx, gridrow in enumerate(grid, start=1):
print(ROW_PATTERN.format(idx, ' | '.join(gridrow)))
print(horizontal_line)在目前的代码中,没有任何获胜或松散的可能性,但这是由于在发布到code时进行编辑。但它确实说明了魔术数字或词的一个很好的观点。在您的代码中,您使用了大量的瑞典语注释,但您也使用了Förlust (即“游戏结束”或“失败”和Vinst (即:(“胜利”)作为result()中的国家指标。唯一的问题是,你用play()和controll()把这些翻译成英语,但没有用result()。
因此,按照现在的情况,不可能在代码中获胜或松散。通常,最好使用布尔值、True或False,或者在代码顶部声明的常量。这样你就可以很容易地修改它们,如果你抓住了所有使用它的地方,就不用担心了。
删除一些由post造成的错误是可能的,但与一般游戏逻辑和处理相关的问题很少:
a1f来标记a1单元格。replay()函数,这个函数将依次重新开始。这个巢穴越来越深。最好在顶层有一个主循环,这样当您调用play()和游戏结束时,它会返回到这个级别,然后请求replay()。if __name__ == '__main__':构造--很好的是,您已经创建了一个mainmenu()函数,如果这是在命名的构造中,那就更好了,因为这将允许您的脚本作为一个模块使用,也可以在命令行中运行。即do: if __name__ ==‘__main_’:mainmenu()有关的一些问题
high_scorelist.dat文件.顺便说一句,这是另一个神奇的名字,它应该是顶部的常量。time隐藏在score()函数的- In my环境中,这会破坏一些内容。不能同时使用time作为导入模块和局部变量。总之,您的代码确实在本地工作,但是当发布时,它变得有点混乱和功能失调。您应该清理代码以避免出现神奇的单词和数字,而应该在开始时使用常量。您应该清理您的命名和间距,以使代码更容易阅读和理解。文本处理和文档化(包括代码内部和用户)也是您需要进一步研究的领域。
发布于 2015-12-07 16:37:04
我不是专家,但以下是我要做的几点改进:
创建初始的“0”填充网格:
grid = [['0' for i in range(size)] for j in range(size)]改进show_grid:
def show_grid(grid,size):
horizontal = ' -'+size*'----'
#writes the column numbers
column = ' ' + ' '.join(string.ascii_uppercase[:size])
print (column,'\n',horizontal)
# writes row numbers
for idx,i in enumerate(grid, start=1):
row = str(idx)
row += ' | ' + ' | '.join(i)
print (row+'\n'+horizontal)改进surrounding_cells方法:
def surrounding_cells(self,row,col,size):
surroundings = []
for i in range(max(row-1, 0), min(row+2, size)):
for j in range(max(col-1, 0), min(col+2, size)):
if i == row and j == col:
continue
surroundings.append((i,j))关于goodvalues()的两个注释:不需要if värde not in range(min,max): a = False,您可以直接删除它。而且检查if min <= varde < max比if varde in range(min, max)更快(内存也更少)
管制:
def control(grid, shown_grid, size, number_of_mines, start_time, username, flags, mines):
empty_cells = sum(row.count('-') for row in shown_grid)
cells_with_mines = sum(row.count('*') for row in shown_grid)
if empty_cells == cells_with_mines or set(flags) == set(mines):
result('YOU WON', grid, shown_grid, start_time, number_of_mines, size, username)另外,命名需要一些修正:首先,使用snake_case而不是连接Also,它将使您的代码更具可读性。此外,使用英语也是一种很好的方式(通常是这样),如果您不熟悉正确的拼写,请使用字典(或IDE内置拼写检查器)检查。最后一件事,即使出于某种原因,你使用非英语名称,至少尽量避免非ASCII符号在其中(如奥,奥等)。
我想,你可能想要创建一个游戏类,来存储诸如用户名、网格大小、地雷数量等东西。所以你可以在需要的时候取这些值,而不必每次都要传递它们。(例如,现在还不清楚结果()为什么需要这么多参数)。
https://codereview.stackexchange.com/questions/113153
复制相似问题