Another newbie question

Mike Meyer mwm at mired.org
Wed Dec 7 23:58:02 EST 2005


"solaris_1234" <solaris_1234 at yahoo.com> writes:

> 1)  The stmt "board.Blist[10].DrawQueen(board.Blist[10].b1)" seems
> awkward. Is there another way (cleaner, more intuitive) to get the
> same thing done?

Yes. Reaching through objects to do things is usually a bad idea. Some
languages don't allow you to do that at all; they require you to
provide methods for manipulating the state of the object For instance,
you can extend your MyBoard class with an extra method:

   def DrawQueen(self, cell):
       square = self.Blist[cell]
       square.DrawQueen(square.b1)


And then those two lines become:

    board.DrawQueen(10)
    board.DrawQueen(22)

Except that's still ugly - you probably want something like
board.DrawQueen(1, 2).

Basically, Blist should be part of MyBoards implementation, not a
visible attribute. You should define methods for MyBoard that let
clients manipulate the board, without needing to know how it's
represented internally.

Along the same lines, why does MyBoard inherit from MyBox? It's not
using any of the features of MyBox. The code still works if you don't
do that. And why do you pass instances of Cavnas to the methods of
MyBox - it's got a canvas already! Do you really expect a MyBox to
draw onto Canvases other than it's own (if so, that's a bad design as
well).

Here's an updated version of your code. I've used the convention of an
_ prefix on attributes to indicate implementation details, and made
the classes inherit from object, as well as using "box" instead of
"b1", and changed the interface to MyBoard squares to use standard
2d-array indexing instead of forcing the clients to do array
index calculations. You may have a good reason for doing these things
that doesn't appear in your code fragment, but I consider these to be
improvements in the fragment.

Hmm. "b1" seems to indicate that you will eventually have more than
one canvas, which is why you passed in the canvas? In which case, the
distinguishing feature would be the number (or mabye the "b1"). In
that case, have your clients pass in the number (or name), and look up
the canvas in an internal structure.

    <mike

from Tkinter import *
import time
totalSolutionCount = 0
    
class MyBox(object):
   def __init__(self, myC, myrow, mycolumn, color):
      self._box = Canvas(myC, background=color, width=50, height=50)
      self._box.grid(row=myrow, column=mycolumn)
      self.occupied = False
        
   def ChangebgColor(self):
      self._box.config(bg="black")

   def DrawQueen(self):
      self._box.item = self._box.create_oval(4,4,50,50,fill="black")
      self.occupied = True
      self._box.update()

   def unDrawQueen(self):
      self._box.delete(self._box.item)
      self.occupied = False
      self._box.update()

class MyBoard(object) :
   def __init__(self, myC):
      self._blist = {}
      for i in range(8):
         for j in range(8):
             self._blist[i, j] = MyBox(myContainer, i, j,
                                        ("green", "red")[(i * 8 + j) % 2])
   def DrawQueen(self, i, j):
       square = self._blist[i, j]
       square.DrawQueen()

   def occupied(self, i, j):
       return self._blist[i, j].occupied


root=Tk()
myContainer = Frame(root)
myContainer.pack()

board=MyBoard(myContainer)

board.DrawQueen(1, 2)
board.DrawQueen(2, 6)

raw_input()  # A Hack debug statement

for i in range(8):
    for j in range(8):
        if board.occupied(i, j):
            print "%d, %d is occupied" % (i, j)

raw_input()  # A Hack debug statement
print "\n"*3




-- 
Mike Meyer <mwm at mired.org>			http://www.mired.org/home/mwm/
Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information.



More information about the Python-list mailing list