Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Class cross referencing?

I come from a C++ background and I am a bit lost without the whole pointer concept in python. Or at least it's unclear. For instance, I want to create a game of tick tack toe using OOP in Python. I have a couple classes like so:

class Game(object):
    def __init__(self, player1, player2):
        self.board = [['','',''],
                      ['','',''],
                      ['','','']]
        self.players = [player1, player2]

class Player(object):
    def __init__(self, game, marking):
        self.game = game
        self.marking = marking  # either 'X' or 'O'

It seems obvious that the game needs to have a reference to the two players and that a player is also part of a game, and should, therefore, have a reference to the game. However, the above code doesn't work because there is no way I can create a player without a creating a game first. But to create a game I need two players. I could add in these references afterwards by doing something like: player.game = some_game_reference but this seems unpythonic and tedious to keep up with.

What is the best and most pythonic way of accomplishing this?

like image 913
Max Smith Avatar asked Oct 18 '22 10:10

Max Smith


1 Answers

You can just have one class or the other updates its arguments. For example, create the players first, then have the game update the players with itself:

class Game(object):
    def __init__(self, player1, player2):
        self.board = [['','',''],
                      ['','',''],
                      ['','','']]
        self.players = [player1, player2]
        player1.game = self
        player2.game = self
        player1.marking = 'X'
        player2.marking = 'O'  

# Neither game nor marking make sense to set initially, until
# the players are added to a game.
class Player(object):
    def __init__(self):
        pass

p1 = Player()
p2 = Player()

g = Game(p1, p2)

(Whether you need this kind of coupling is, as others have pointed out, a separate design issue.)

Just to show the other direction is just as feasible:

class Player(object):
    def __init__(self, game, marking):
        self.game = game
        self.marking = marking
        game.players.append(self)

class Game(object):
    def __init__(self):
        self.board = [['','',''],
                      ['','',''],
                      ['','','']]

g = Game()
p1 = Player(g, 'X')
p2 = Player(g, 'O')

Hopefully, though, you'll agree that it makes more sense for the game to assign each player a marking. Here, you might try to add more than 2 players to a game, or add two X or two O players.

like image 136
chepner Avatar answered Oct 22 '22 10:10

chepner