Let's say i have a lot of functions in alotoffunc.py that is used by more than 1 type of object.
Let's say ObjectI and ObjectII and ObjectXI all uses some functions in alotoffunc.py. And each of the Object were using different set of functions but all the objects have the variable object.table.
alotoffunc.py:
def abc(obj, x):
return obj.table(x) * 2
def efg(obj, x):
return obj.table(x) * obj.table(x)
def hij(obj, x, y):
return obj.table(x) * obj.table(y)
def klm(obj, x, y):
return obj.table(x) *2 - obj.table(y)
And then i import the functions and overload them:
import alotoffunc
class ObjectI:
def abc(self, x):
return alotoffunc.abc(self, x)
def efg(self, x):
return alotoffunc.efg(self, x)
class ObjectII:
def efg(self, x):
return alotoffunc.efg(self, x)
def klm(self, x, y):
return alotoffunc.klm(self, x, y)
class ObjectXI:
def abc(self, x):
return alotoffunc.abc(self, x)
def klm(self, x, y):
return alotoffunc.klm(self, x, y)
It looks a like a big mess now, how should I go about building my object class and arrange my alotoffunc.py?
A pretty useful technique for simulating multiple constructors in a Python class is to provide . __init__() with optional arguments using default argument values. This way, you can call the class constructor in different ways and get a different behavior each time.
a) Methods should not have more than an average of 30 code lines (not counting line spaces and comments). b) A class should contain an average of less than 30 methods, resulting in up to 900 lines of code.
Classes provide a way to merge together some data and related operations. If you have only one operation on the data then using a function and passing the data as argument you will obtain an equivalent behaviour, with less complex code.
An object is simply a collection of data (variables) and methods (functions) that act on those data. Similarly, a class is a blueprint for that object. We can think of a class as a sketch (prototype) of a house.
(1) You can have a base class that implements all the methods then override the unnecessary ones to raise a NotImplementedError in the subclasses.
(2) You can have mixins to reduce repetition:
import alotoffunc
class MixinAbc:
def abc(self, x):
return alotoffunc.abc(self, x)
class MixinEfg:
def efg(self, x):
return alotoffunc.efg(self, x)
class MixinKlm:
def klm(self, x, y):
return alotoffunc.klm(self, x, y)
class ObjectI(MixinAbc, MixinEfg):
pass
class ObjectII(MixinEfg, MixinKlm):
pass
class ObjectXI(MixinAbc, MixinKlm):
pass
You can also combine this method with that of @cpburnz.
The simplest way is to bind the desired functions directly as instance methods to a class in its definition. Note that each function will receive self as the first argument.
import alotoffunc
class ObjectI:
abc = alotoffunc.abc
efg = alotoffunc.efg
class ObjectII:
efg = alotoffunc.efg
klm = alotoffunc.klm
class ObjectXI:
abc = alotoffunc.abc
klm = alotoffunc.klm
This can be a simpler approach to defining mix-in classes if there isn't a clear, logical grouping for the various functions. The grouping does depend on your use case though so the mix-in approach can be better depending on the situation.
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