简体   繁体   中英

Python Connect Four. Making the computer move

I need some help with my connect four assignment. My make computer move function has problems. In my assignment I am suppose use a list as the board. The number of lists within the list is the row. And the items within the list within the list are the cols.

board=[[" "," "," "," "," "],
       [" "," "," "," "," "],
       [" "," "," "," "," "],
       [" "," "," "," "," "],
       [" "," "," "," "," "]]

There are 5 rows and 5 cols. Therefore 25 free cells. The main function loops 25 times and calls the make_computer_move function.The display_board function is not important. The problem is with the make_computer_move . It should fill the entire board since there are 25 free cells and the main loops 25 times. But it doesn't. There are blank spaces left. Also it doesn't print the coordinates of the move it made. I put a print statement so that whenever a valid move occurs, the coordinates are printed. I noticed that sometimes the board stays the same in the loop and nothing happens. I'm stumped :/

def display_board(board):
    col="   "
    for index1 in range(len(board[0])):
        col+=str(index1)+"   "
    print col
    for index2 in range(len(board)):
        print str(index2)+": "+" | ".join(board[index2])+" |"
        print "  "+"---+"*(len(board[0]))
def make_computer_move(board):
    import random
    col=random.randint(0,(len(board[0])-1)) 
    for row in range(len(board)-1,-1,-1): # counts from the bottom of the board and up
        if board[row][col]==" ": #if there is a blank space it will put a "O" and break
            print "The pairing is("+str(row),str(col)+")" #Print the coordinates
            board[row][col] = 'O'
            break
    else: #if the break does not occur this else statement executes
        col=random.randint(0,(len(board[0])-1)) 
def main():
    board=[[" "," "," "," "," "],[" "," "," "," "," "],[" "," "," "," "," "],[" "," "," "," "," "],[" "," "," "," "," "]]
    for counter in range(25):
        display_board(board)
        make_computer_move(board)
main()

Most simply, you need to make make_computer_move() call itself again if it doesn't find a free slot in that column, as at the moment, you set a new column, and then do nothing with it.

def make_computer_move(board):
    import random
    col=random.randint(0,(len(board[0])-1)) 
    for row in range(len(board)-1,-1,-1): # counts from the bottom of the board and up
        if board[row][col]==" ": #if there is a blank space it will put a "O" and break
            print "The pairing is("+str(row),str(col)+")" #Print the coordinates
            board[row][col] = 'O'
            break
    else: #if the break does not occur this else statement executes
       make_computer_move(board)

Note that the method you are persuing isn't particularly effective, as there is no guarentee it will find a free slot. You might want to at least do something like having columns_not_full=[0, 1, 2, ... n] and then removing columns as the last slot is filled, and use random.choice(columns_not_full) to get a column to play in.

This will give you the index of a random open column (or row, depending on how you look at it).

openColumns = [i for i in range(len(board)) if board[i].count(' ') > 0]
if openColumns: ComputerChoice = openColumns[random.randint(0, len(openColumns)]
else: #do something if there are no open columns (i.e. the board is full)

First you should test for at least one empty space, and generally the imports are at the top of the program.

import random

def make_computer_move(board): for row in board: ## look for first empty space if " " in row: while True: ## infinite loop col=random.randint(0,(len(board[0])-1)) for row in range(len(board)-1,-1,-1): if board[row][col]==" ": print "The pairing is("+str(row),str(col)+")" #Print the coordinates board[row][col] = 'O' return board print "All squares filled -- Game Over"

Another alternative is to create a list of available spaces and choose

available = [] for row in range(5): for col in range(5): if board[row][col] == " ": available.append([row, col]) move = random.choice(available)

The code above works perfectly. It makes make_computer_move(board, avail_col) to return the column number, when a given columns is filled, to main. In main this column is taken out before calling again make_computer_board:

import random

def display_board(board):
    col = "   "
    cols = len(board[0])
    for index1 in range(cols):
        col += "%i   " % index1
    print col
    for index2 in range(len(board)):
        print str(index2) + ": " + " | ".join(board[index2]) + " |"
        print "  " + "---+" * cols


def make_computer_move(board, avail_cols):
    col = random.choice(avail_cols) 
    for row in range(len(board)-1, -1, -1):            # counts from bottom of board and up
        if board[row][col] == " ":                      # if there is a blank space, put a "O" and break
            print "The pairing is (%i,%i)" % (row,col)  #Print the coordinates
            board[row][col] = 'O'
            break

    if row == 0:      #arrives to the last row
        return col


def main():
    board = [[" ", " ", " ", " ", " "] for i in range(5)]
    avail_cols = range(len(board[0]))
    display_board(board)
    for counter in range(25):
        filled = make_computer_move(board, avail_cols)
        display_board(board)
        if filled is not None: avail_cols.remove(filled)


main()

Note:

  1. random import is now at the top.
  2. Code has been beautified a bit following PEP-8.
  3. I prepare the board with a list comprehension
  4. The two calls to display_board(board) . First one draw starting step, the secon one has been moved after make_computer_move to draw the last figure after the program is finish
  5. The use of % interpolations to simplify some lines

There are still some inefficiencies. For example you calculate len(board[0]) each time you call the function when this is not neccesary as the board stays always with the same size.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM