简体   繁体   中英

Connect Four Python printing problems

I have made an initialized board for the game connect four and I want to now keep track of the position and play of each tur n such that if i do:

b = ConnectFour()
b.play_turn(1, 3)
b.play_turn(1, 3)
b.play_turn(1, 4)
b.print_board()   

The board should print out:

-----------------------------
| 0 | 1 | 2 | 3 | 4 | 5 | 6 |
-----------------------------
|   |   |   |   |   |   |   |
|   |   |   |   |   |   |   |
|   |   |   |   |   |   |   |
|   |   |   |   |   |   |   |
|   |   |   | x |   |   |   |
|   |   |   | x | x |   |   |
-----------------------------

UPDATE:

#initializes board

class ConnectFour(object):
        def __init__(self):
            self.board = [[0 for i in range(7)] for j in range(8)]



def get_position(self, row, column):
  """ Returns either None or an integer 1 or 2 depending 
  on which player is occupying the given row or column.  
  Row is an integer between 0 and 5 and column is an integer between 0 and 6. """
assert row >= 0 and row < 6 and column >= 0 and column < 7
return self.board[row][column]


def play_turn(self, player, column):
    """ Updates the board so that player plays in the given column.

    player: either 1 or 2
    column: an integer between 0 and 6
    """
    assert player == 1 or player == 2
    assert column >= 0 and column < 7

    for row in range(6):
        if self.board[row][column] == None:
            self.board[row][column] = player
            return



def print_board(self):
    print "-" * 29
    print "| 0 | 1 | 2 | 3 | 4 | 5 | 6 |"
    print "-" * 29
    for row in range(5,-1,-1):
        s = "|"
        for col in range(7):
            p = self.get_position(row, col)
            if p == None:
                s += "   |"
            elif p == 1:
                s += " x |"
            elif p == 2:
                s += " o |"
            else:                     
                s += " ! |"
        print s
print "-" * 29

Resolved:

This is Current OUTPUT:

-----------------------------
| 0 | 1 | 2 | 3 | 4 | 5 | 6 |
-----------------------------
|   |   |   |   |   |   |   |
|   |   |   |   |   |   |   |
|   |   |   |   |   |   |   |
|   |   |   |   |   |   |   |
|   |   |   | x |   |   |   |
|   |   |   | x | x |   |   |
-----------------------------

The problem I see is that your self.get_position does not do what you want it to do.

def get_position(self, row, column):
    assert row >= 0 and row < 6 and column >= 0 and column < 7
    if self.get_position == 1: # the type of self.get_position is a function, and it will never be equal to 1, or 2, so it always goes to None
            return 1
        elif self.get_position == 2:
            return 2
        else:
            return None

Another problem is that you never used board, and you never store your data at any place.
If I were you, I would first consider how I would store the data.
An obvious option is a two-dimension array.

self.board = [[0 for i in range(6)] for j in range(7)]

When you call play_turn, try to update the column, eg you already have [0,0,0,0,2,1] on column 3, you would try to get the index of the first element that is not 0. Then put the new player index on the element before it, so it goes to [0,0,0,1,2,1] (if the piece belongs to player 1).

Then, actually with a column number and a row number, you want to check what is on the board. Whether it is 0 or 1 or 2.
you'd better call it get_player_num or something like that. You do not get position but the player number of the piece at that position.

An example. If I have a 2 * 2 array in a class:

class CF(object):
    def __init__(self):
        board = [[0, 0], [0, 0]]

This represents a 2 * 2 field, now they are all empty.
0 0
0 0

I could design an update method:

def update(self, col, row, newVal):
    self.board[col - 1][row - 1] = newVal

If a do:

game = CF()
game.update(1, 2, 1) 

Then the board becomes
0 0
1 0

While reading the board, I know at column 1, row 2 is a piece of player 1.

Your code for get_position is not correct. You need to be inspecting self.board , rather than looking at self.get_position (which is the method itself, not any value).

Since you're not currently using self.board anywhere, I'm not sure exactly what format you intend it to have (is it intended to be a single list, or a list of lists?).

Here's what I think you need to add:

  1. Better initialization of the board in to __init__ . I suggest making self.board a list that has 0 or None (whatever you want to represent "empty"), repeated 7*6 times. Or alternatively you could make it a list of lists (probably six lists of seven values each).

  2. Check the board for values in get_position . If you're doing a single list, you should check self.board[row*7+column] .

  3. The play_turn method needs to inspect the board to find out what row a piece falls to when it is put in a specified column. The piece will go in the lowest row that is empty for that column, so a loop is needed. Once you find the precise position, you can set the value in self.board .

Your print_board function should work just fine, once get_position is fixed.

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