0

我遵循Charles Dierbach的書,使用Python介紹計算機科學。我的python井字棋難題

我在第5章。我正在嘗試對tic-tac-toe自動播放進行這個練習。

我有困難創建一個函數爲電腦選擇一個空框([])。

這裏是我的代碼

import re 
import random 
def template(): 
    mylst = list() 
    for i in range(0, 3): 
     my_temp = [] 
     for j in range(0, 3): 
      my_temp.append([]) 
     mylst.append(my_temp) 
    return mylst 
def template_2(alst): 
    print() 
    al = ("A", "B", "C") 
    for a in al: 
     if a == "A": 
      print (format(a, ">6"), end="") 
     if a == "B": 
      print (format(a, ">5"), end="") 
     if a == "C": 
      print (format(a, ">5"), end="") 

    print() 
    for j in range(len(alst)): 
     print(str(j + 1), format(" ", ">1"), end="") 
     print(alst[j]) 
     print() 

def print_template(alst): 
    print() 
    al = ("A", "B", "C") 
    for a in al: 
     if a == "A": 
      print (format(a, ">6"), end="") 
     if a == "B": 
      print (format(a, ">4"), end="") 
     if a == "C": 
      print (format(a, ">3"), end="") 

    print() 
    for j in range(len(alst)): 
     print(str(j + 1), format(" ", ">1"), end="") 
     print(alst[j]) 
     print() 

def first_player(lst): 
    print() 
    print ("Your symbol is 'X'. ") 
    alpha = ("A", "B", "C") 
    #check it was entered correctly 
    check = True 
    temp_lst1 = [] 
    while check: 
     correct_entry = False 
     while not correct_entry: 
      coord = input("Please enter your coordinates ") 
      player_regex = re.compile(r'(\w)(\d)') 
      aSearch = player_regex.search(coord) 
      if aSearch == None: 
       correct_entry = False 
      if aSearch.group(1) != "A" or aSearch.group(1) != "B" or aSearch.group(1) != "C" or aSearch.group(2) != 1 or aSearch.group(2) == 2 or aSearch.group(3) != 3: 
       correct_entry = False 
      if aSearch.group(1) == "A" or aSearch.group(1) == "B" or aSearch.group(1) == "C" or aSearch.group(2) == 1 or aSearch.group(2) == 2 or aSearch.group(3) == 3: 
       correct_entry = True 
      else: 
       correct_entry = True 
     blank = False 
     while not blank: 
      if lst[(int(coord[-1])) - 1][alpha.index(coord[0])] == []: 
       lst[(int(coord[-1])) - 1][alpha.index(coord[0])] = "X" 
       temp_lst1.append((int(coord[-1])-1)) 
       temp_lst1.append((alpha.index(coord[0]))) 
       blank = True 
      else: 
       blank = True 
       correct_entry = False 
     if blank == True and correct_entry == True: 
      check = False 
    return True 









def pc_player(lst): 
    print() 
    print ("PC symbol is 'O'. ") 
    alpha = ("A", "B", "C") 
    num_list = (0, 1, 2) 

    for i in range(0, len(lst)): 
     for j in range(0, len(lst[i])): 
      if lst[i][j] ==[]: 
       lst[i][j] = "O" 
      break 
     break 

    return True 








def check_1st_player(lst): 
    if lst[0][0] == "X" and lst[0][1] == "X" and lst[0][2] == "X": 
     return True 
    elif lst[1][0] == "X" and lst[1][1] == "X" and lst[1][2] == "X": 
     return True 
    elif lst[2][0] == "X" and lst[2][1] == "X" and lst[2][2] == "X": 
     return True 
    elif lst[0][0] == "X" and lst[1][0] == "X" and lst[2][0] == "X": 
     return True 
    elif lst[0][1] == "X" and lst[1][1] == "X" and lst[2][1] == "X": 
     return True 
    elif lst[0][2] == "X" and lst[1][2] == "X" and lst[2][2] == "X": 
     return True 
    elif lst[0][0] == "X" and lst[1][1] == "X" and lst[2][2] == "X": 
     return True 
    elif lst[2][0] == "X" and lst[1][1] == "X" and lst[0][2] == "X": 
     return True 
    else: 
     return False 


def check_pc_player(lst): 

    if lst[0][0] == "O" and lst[0][1] == "O" and lst[0][2] == "O": 
     return True 
    elif lst[1][0] == "O" and lst[1][1] == "O" and lst[1][2] == "O": 
     return True 
    elif lst[2][0] == "O" and lst[2][1] == "O" and lst[2][2] == "O": 
     return True 
    elif lst[0][0] == "O" and lst[1][0] == "O" and lst[2][0] == "O": 
     return True 
    elif lst[0][1] == "O" and lst[1][1] == "O" and lst[2][1] == "O": 
     return True 
    elif lst[0][2] == "O" and lst[1][2] == "O" and lst[2][2] == "O": 
     return True 
    elif lst[0][0] == "O" and lst[1][1] == "O" and lst[2][2] == "O": 
     return True 
    elif lst[2][0] == "O" and lst[1][1] == "O" and lst[0][2] == "O": 
     return True 
    else: 
     return False 

def play_game(): 
    ask = input("Do you want to play a two player game of Tic-Tac-Toe game? (y/n) ") 

    if ask in yes_response: 

     # contruct the template for tic-tac-toe 
     print() 
     print("How many rounds do you want to play? ") 
     print("Please enter only odd integers") 
     print("Please enter your coordinates", end="") 
     print(" using format A1 or B2") 
     print("New Round") 
     return True 


def play_again(): 
    tell_me = input("Do you want you play a game ? (y/n)") 
    if tell_me == "Y" or "y": 
     return True 
    else: 
     return False 

def is_full(lst): 
    count = 0 
    for i in lst: 
     for j in i: 
      if j != []: 
       count += 1 
    if count == 9: 
     return True 
# 
#-- main 
print("Welcome to Awesome 2 Player Tic-Tac-Toe Game? ") 
print() 

answer = False 
yes_response =("Y", "y") 
no_response = ("N", "n") 
while not answer: 
    print("Enter an even integer to exit") 
    ask = int(input("How many matches do you want to play? (odd integers only)? ")) 
    game = play_game() 
    structure = template() 
    print_template(structure) 
    if ask % 2 == 1: 
     score_player1 = 0 
     score_pc = 0 
     count = 0 
     while count < ask: 
      pc_lst = [] 
      if count >= 1: 
       structure = template() 
       print_template(structure) 

      while game: 

       check_pc = True 
       while check_pc: 

        pc_player(structure) 
        template_2(structure) 
        check_pc = False 

       check_pc_winner = True 
       while check_pc_winner: 
        game_pc = check_pc_player(structure) 
        check_pc_winner = False 
       if game_pc == True: 
        print("Congratulations PC won") 
        score_pc += 1 
        game = False 
        break 
       check_player1 = True 
       while check_player1: 
        first_player(structure) 
        template_2(structure) 
        check_player1 = False 
       check_first_winner = True 
       while check_first_winner: 
        game_first = check_1st_player(structure) 
        check_first_winner = False 
       if game_first == True: 
        print("Congratulations Player 1 won") 
        score_player1 += 1 
        game = False 
        break 

       board_full = False 
       while not board_full: 
        check_board = is_full(structure) 
        board_full = True 
       if check_board == True: 
        print("This round was a tie.") 
        game = False 

      print("Player 1 : ", score_player1, " PC : ", score_pc) 
      count += 1 
      game = True 

    if score_player1 > score_pc: 
     print("Player 1 won") 
    elif score_player1 < score_pc: 
     print("PC won") 
    if play_again() == False: 
      answer = True 
    else: 
     answer = False 

我的問題是,在def pc_player():

我想知道如何循環列表和子列表,以便AI可以選擇一個空框作爲其選擇放置一個「O」

我當前的循環不起作用。 AI只選擇第一個框。

+0

如何保證列表中始終包含一個*空框*? –

回答

0

開始通過尋找所有空箱:

empty= [(i,j) for i in range(len(lst)) for j in range(len(lst[i])) if lst[i][j]==[]] 

然後選擇一個隨機一個:

import random 
chosen_i, chosen_j= random.choice(empty) 

,最後把一個O有:

lst[chosen_i][chosen_j]= 'O' 
+0

非常感謝你回答我的問題,並給我一個解決方案,我會理解 – user6277136

1

我當前的循環不起作用。 AI只選擇第一個框。

我想你指的這個部分:

def pc_player(lst): 
    print() 
    print ("PC symbol is 'O'. ") 
    alpha = ("A", "B", "C") 
    num_list = (0, 1, 2) 

    for i in range(0, len(lst)): 
     for j in range(0, len(lst[i])): 
      if lst[i][j] ==[]: 
       lst[i][j] = "O" 
      break 
     break 

    return True 

break說明連同你的方式初始化for循環只會嘗試設置lst[0][0]。其他細胞未被考慮。

要做出均勻分佈的隨機選擇,首先要收集可能性至關重要。對於這一點,它是方便的所有單元格在一個普通的列表第一:

from itertools import chain 
all_cells = list(chain.from_iterable(lst)) 

然後,您可以過濾掉非空單元格:

empty_cells = filter(lambda l: len(l) == 0, all_cells) 
# empty_cells = filter(lambda l: not l, all_cells) 
# empty_cells = [cell for cell in all_cells if not cell] 

在此基礎上,你現在可以觸發隨機選擇和符號位置:

import random 
cell_to_place = random.choice(empty_cells) 
cell_to_place.append('O') 

如果你需要的細胞的指標被修改,你可以做到以下幾點:

import itertools 
indices = list(itertools.product(range(3), range(3))) 
indexed_cells = zip(indices, map(lambda (i, j): lst[i][j], indices)) 
indexed_cells = filter(lambda (_, l): not l, indexed_cells) # filter non-empty 
(i,j), cell_to_place = random.choice(indexed_cells) 
# ... 

這些代碼示例考慮到有可能是沒有留下任何空單元格。另外,你的代碼有一些一般的設計問題。例如:

  • 爲什麼您首先使用列表作爲單元格項?您可以簡單地使用None,'X''O'作爲二維列表的元素。
  • check_pc_playercheck_1st_player可以很容易地通過使符號檢查函數的參數來推廣。
  • 爲什麼這是一個while循環?

    while check_first_winner: 
         game_first = check_1st_player(structure) 
         check_first_winner = False 
    
+0

我把它放在一個while循環來檢查玩家1是否贏得 – user6277136

+0

謝謝你的回答,但我沒有被教過lambda或大部分你寫的東西我只是一個初學者 – user6277136

+0

是的,我明白你爲什麼要執行代碼在一個條件下。但重新考慮循環。不是一個足夠的?你開始學習沒什麼大不了的。蘭巴達斯並不難。只要保持開放的心態,並谷歌你不明白的東西。我認爲上述步驟足夠描述。 – mhoff