[Tutor] Issue with classes

Peter Otten __peter__ at web.de
Tue Jun 12 11:02:11 CEST 2012


Bod Soutar wrote:

> Hi,
> 
> I am having some difficulty calling a class method from a different class.
> When I run the attached script like this "python cheatsheet.py --list"
> 
> C:\>python cheatsheet.py --list
> done
> here?
> Traceback (most recent call last):
>   File "cheatsheet.py", line 167, in <module>
>     main()
>   File "cheatsheet.py", line 165, in main
>     ca.parseArgs()
>   File "cheatsheet.py", line 39, in parseArgs
>     self.argList()
>   File "cheatsheet.py", line 96, in argList
>     handle = cf.load()
> NameError: global name 'cf' is not defined
> 
> 
> So the traceback points to the issue being on line 96, specifically the
> call to cf.load(). cf.load() (line 147) is part of the cheatFile class
> (line 125), and is instantiated with cf = cheatFile() (line 161)
> 
> I confess I don't know anything about classes really so I'm probably doing
> something stupid, but can anyone point me in the right direction?
> 
> Thanks,
> Bodsda

Your problem has nothing to do with classes, you are trying to use a 
variable outsite its scope. For example the same error will be triggered by

def print_message():
    print(message)

def main():
    message = "hello"
    print_message()

main()

The tempting newbie fix is to make message a global variable

def main():
    global message
    message = "hello"
    print_message()

but this makes for brittle code and you and up with lots of implicit 
dependencies. Instead you should pass an argument explicitly:

def print_message(message):
    print(message)

def main():
    message = "hello"
    print_message(message)


If you are dealing with a class you can either pass the argument to the 
relevant method, or, if you need it in a lot of places make it an attribute


class Message:
    def __init__(self, message):
        self.message = message
    def print_it(self):
        print(self.message)


def main():
    m = Message("hello")
    m.print_it()


Can you apply that idea to your code? Your main() function will become 
something like

def main():
    cf = cheatFile()
    print "done"
    ca = cliArgs(cf)
    ca.parseArgs()

Come back here if you run into problems.

By the way, Python's standard library offers an excellent way to deal with 
commandline arguments, see

http://docs.python.org/library/argparse.html

which you should prefer over you self-made cliArgs.



More information about the Tutor mailing list