Quinten C
Quinten C

Reputation: 771

Re-use argument or use self

When defining a class and you need to use an argument twice is it better to keep using the argument or use the self version as soon as it is made?

class Example:
    def __init__(self, name):
        self.name = name
        self.name_upper = name.upper()

or

class Example:
    def __init__(self, name):
        self.name = name
        self.name_upper = self.name.upper()

And what about with list?

class Example:
    def __init__(self, name):
        self.name = name
        self.name_list = [name,name,name]
class Example:
    def __init__(self, name):
        self.name = name
        self.name_list = [self.name,self.name,self.name]

Upvotes: 0

Views: 40

Answers (2)

ShadowRanger
ShadowRanger

Reputation: 155734

TL;DR: In the specific cases you're describing, it doesn't matter. It's a very small trade-off between speed and safety against future changes, but there's no right answer.

If there is no massaging of the argument before it's stored in the attribute, then it doesn't really matter. Using the unqualified name will be slightly faster (self.name on CPython involves a cheap LOAD_FAST and a significantly more expensive, if still cheap in absolute terms, LOAD_ATTR; plain name for an argument is just a LOAD_FAST), so if you're 100% sure you're never going to massage the argument before storage (e.g. no self.name = int(name)), avoiding self when you can will speed initialization a bit.

That said, it's rare to be that sure, so using self.name is safer. You can always split the difference though even when massaging arguments, by doing something like:

self.name = name = int(name)

which stores back to both the attribute and the local (via DUP_TOP and STORE_FAST, two of the cheapest op codes in CPython), so you get the same massaged value by either means, and the cheap loads from the unqualified name.

Upvotes: 3

bashBedlam
bashBedlam

Reputation: 1500

It's a question of scope. In the example below, the variable 'name' is only visible with in the method '__init__' whereas the variable 'self.name_list' can be used in any method within the class.

class Example :
    def __init__ (self, name) :
        self.name_list = [name] * 3

    def show_variables (self) :
        print (self.name_list)
        print (name)      # gives 'name' is not defined error

this = Example ('This example')
this.show_variables ()

Upvotes: -2

Related Questions