I have written some code that uses attributes of an object:
class Foo:
def __init__(self):
self.bar = "baz"
myFoo = Foo()
print (myFoo.bar)
Now I want to do some fancy calculation to return bar
. I could use @property
to make methods act as the attribute bar
, or I could refactor my code to use myFoo.bar()
.
Should I go back and add parens to all my bar
accesses or use @property
? Assume my code base is small now but due to entropy it will increase.
If it's logically a property/attribute of the object, I'd say keep it as a property. If it's likely to become parametrised, by which I mean you may want to invoke myFoo.bar(someArgs)
then bite the bullet now and make it a method.
Under most circumstances, performance is unlikely to be an issue.
Wondering about performance is needless when it's so easy to measure it:
$ python -mtimeit -s'class X(object):
> @property
> def y(self): return 23
> x=X()' 'x.y'
1000000 loops, best of 3: 0.685 usec per loop
$ python -mtimeit -s'class X(object):
def y(self): return 23
x=X()' 'x.y()'
1000000 loops, best of 3: 0.447 usec per loop
$
(on my slow laptop -- if you wonder why the 2nd case doesn't have secondary shell prompts, it's because I built it from the first with an up-arrow in bash, and that repeats the linebreak structure but not the prompts!-).
So unless you're in a case where you know 200+ nanoseconds or so will matter (a tight inner loop you're trying to optimize to the utmost), you can afford to use the property approach; if you do some computations to get the value, the 200+ nanoseconds will of course become a smaller fraction of the total time taken.
I do agree with other answers that if the computations become too heavy, or you may ever want parameters, etc, a method is preferable -- similarly, I'll add, if you ever need to stash the callable somewhere but only call it later, and other fancy functional programming tricks; but I wanted to make the performance point quantitatively, since timeit
makes such measurements so easy!-)
In cases like these, I find it much better to choose the option that makes the most sense. You won't get any noticeable performance loss with small differences like these. It's much more important that your code is easy to use and maintain.
As for choosing between using a method and a @property
, it's a matter of taste, but since properties disguise themselves as simple attributes, nothing elaborate should be going on. A method indicates that it might be an expensive operation, and developers using your code will consider caching the value rather than fetching it again and again.
So again, don't go on performance, always consider maintainability vs. performance. Computers get faster and faster as time goes by. The same does not stand for the readability of code.
In short, if you want to get a simple calculated value, @property
is an excellent choice; if you want an elaborate value calculated, a method indicates that better.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With