Performance of accessing class variables in Python

global-variables, python, scope

Solution

Accessing it via `ClassName` rather than via `self` will be slightly faster, since if you access it via `self` it must first check the instance namespace. But I don't expect the difference to be at all significant, unless you have profiling information to suggest that it is.

So I would recommend using whichever one you think is easier to read/understand as a human.

Semantically, they will be different only if the `class_variable_dict` variable gets shadowed somewhere -- in particular, if (a) `self` defines a variable of the same name; or (b) `self` is an instance of a subclass of `ClassName`, and that subclass (or one of its bases that's still a subclass of `ClassName`) defines a variable of the same name. If neither of those is true, then they should be semantically identical.

Edit:

delnam has a good point: there are factors that might make either faster. I stand by my assertion that the difference will be trivial unless it's in a very very tight loop. To test it, I created the tightest loop I could think of, and timed it with `timeit`. Here are the results:

- access via class var: 20.226 seconds

- access via inst var: 23.121 seconds

Based on several runs, it looks like the error bars are about 1sec -- i.e., this is a statistically significant difference, but probably not worth worrying about. Here's my test code:

import timeit

setup='''
class A:
    var = {}
    def f1(self):
        x = A.var
    def f2(self):
        x = self.var

a = A()
'''
print 'access via class var: %.3f' % timeit.timeit('a.f1()', setup=setup, number=100000000)
print 'access via inst var: %.3f' % timeit.timeit('a.f2()', setup=setup, number=100000000)

Problem

I wonder if there is any difference in performance when accessing a class variable (a dict) inside a method of the same class using: ``` self.class_variable_dict.add(some_key, some_value) ``` and ``` ClassName.class_variable_dict.add(some_key, some_value) ``` obviously, both will work as long as there is no instance variable with the same name, but is there any reason/use case for which we should prefer one over the other?

Original source

Related problems