Is it better to use class variables or pass parameters?
duncan.booth at invalid.invalid
Thu Mar 2 09:45:32 CET 2006
Derek Basch wrote:
> This one has always bugged me. Is it better to just slap a "self" in
> front of any variable that will be used by more than one class method
> or should I pass around variable between the methods?
Try to distinguish the state of the object from the parameters to methods.
An object should always have a consistent state. Say you call a method, and
that method calls a bunch of other methods. At almost any point during
those method calls execution can leak out to other bits of code (e.g. you
might think you are adding two values, but perhaps they have a user defined
addition operator) and that other code might just call methods on the same
object. This might not happen much in practice, but I think that if you
imagine all method calls as potentially happening in parallel it avoids a
lot of problems.
So, for example, if you had a method which returned a formatted
representation of something, and which took a precision as a parameter, you
shouldn't be saving the precision in the object: it isn't part of the
state, and if you save it as such one day you might find it changes under
your feet mid call.
A lot of objects benefit from being treated as immutable: i.e. initialise
them on creation, but never modify the attributes after creation. This has
the great benefit that you never need to worry about whether or not to copy
an object: you always just keep using the same object until an attribute
needs to change and then you just create a new one. Obviously this only
works for lightweight objects, but that should be most of them.
Passing one or two parameters around a host of methods is fine: if you are
passing more then it probably indicates you need to invent another object
to encapsulate the state associated with the method call. It is also likely
that it means you then want to move some of the code logic into the new
object. In other words, instead of:
obj.meth1(a, b, c, d) calls obj.meth2(a, b, c, d) calls obj.meth3, ...
(and perhaps meth2 only needs a, b and c so it can pass them on),
you want some helper object constructed with a, b, c & d and parts of the
original methods then get factored into methods on the help objects.
More information about the Python-list