Python calling method in class

classmethodspython

I'm punching way above my weight here, but please bear with this Python amateur. I'm a PHP developer by trade and I've hardly touched this language before.

What I'm trying to do is call a method in a class…sounds simple enough? I'm utterly baffled about what 'self' refers to, and what is the correct procedure to call such a method inside a class and outside a class.

Could someone explain to me, how to call the move method with the variable RIGHT. I've tried researching this on several 'learn python' sites and searches on StackOverflow, but to no avail. Any help will be appreciated.

The following class works in Scott's Python script which is accessed by a terminal GUI (urwid).

The function I'm working with is a Scott Weston's missile launcher Python script, which I'm trying to hook into a PHP web-server.

class MissileDevice:
  INITA     = (85, 83, 66, 67,  0,  0,  4,  0)
  INITB     = (85, 83, 66, 67,  0, 64,  2,  0)
  CMDFILL   = ( 8,  8,
                0,  0,  0,  0,  0,  0,  0,  0,
                0,  0,  0,  0,  0,  0,  0,  0,
                0,  0,  0,  0,  0,  0,  0,  0,
                0,  0,  0,  0,  0,  0,  0,  0,
                0,  0,  0,  0,  0,  0,  0,  0,
                0,  0,  0,  0,  0,  0,  0,  0,
                0,  0,  0,  0,  0,  0,  0,  0)
  STOP      = ( 0,  0,  0,  0,  0,  0)
  LEFT      = ( 0,  1,  0,  0,  0,  0)
  RIGHT     = ( 0,  0,  1,  0,  0,  0)
  UP        = ( 0,  0,  0,  1,  0,  0)
  DOWN      = ( 0,  0,  0,  0,  1,  0)
  LEFTUP    = ( 0,  1,  0,  1,  0,  0)
  RIGHTUP   = ( 0,  0,  1,  1,  0,  0)
  LEFTDOWN  = ( 0,  1,  0,  0,  1,  0)
  RIGHTDOWN = ( 0,  0,  1,  0,  1,  0)
  FIRE      = ( 0,  0,  0,  0,  0,  1)

  def __init__(self, battery):
    try:
      self.dev=UsbDevice(0x1130, 0x0202, battery)
      self.dev.open()
      self.dev.handle.reset()
    except NoMissilesError, e:
      raise NoMissilesError()

  def move(self, direction):
    self.dev.handle.controlMsg(0x21, 0x09, self.INITA, 0x02, 0x01)
    self.dev.handle.controlMsg(0x21, 0x09, self.INITB, 0x02, 0x01)
    self.dev.handle.controlMsg(0x21, 0x09, direction+self.CMDFILL, 0x02, 0x01)

Best Solution

The first argument of all methods is usually called self. It refers to the instance for which the method is being called.

Let's say you have:

class A(object):
    def foo(self):
        print 'Foo'

    def bar(self, an_argument):
        print 'Bar', an_argument

Then, doing:

a = A()
a.foo() #prints 'Foo'
a.bar('Arg!') #prints 'Bar Arg!'

There's nothing special about this being called self, you could do the following:

class B(object):
    def foo(self):
        print 'Foo'

    def bar(this_object):
        this_object.foo()

Then, doing:

b = B()
b.bar() # prints 'Foo'

In your specific case:

dangerous_device = MissileDevice(some_battery)
dangerous_device.move(dangerous_device.RIGHT) 

(As suggested in comments MissileDevice.RIGHT could be more appropriate here!)

You could declare all your constants at module level though, so you could do:

dangerous_device.move(RIGHT)

This, however, is going to depend on how you want your code to be organized!