Reputation: 2742
I know I should have come up with a better title, but anyway...
Say I make a class inherited from int
in python:
class Foo(int):
def is_even(self):
return self%2 == 0
and do something like this
a = Foo(3)
b = Foo(5)
print(type(a+b)) #=> <class 'int'>
I understand this behaviour is not surprising at all, as __add___
called here is defined to return int
instances. But I would like to create a class so that a+b
returns Foo(8)
. In other words, I'd like the result a+b
to have the is_even
method.
Is there any way I can achieve this conveniently? Or do I have to overwrite __add__
and everything?
Background information: I'm trying to write an interpreter for an esoteric programming language called Grass . In that attempt, I want to have a class that behaves like 'callable-int
' (actually, numpy.uint8
), whose __call__
would be like
def __call__(self, other):
if self == other:
return lambda x: lambda y: x
else:
return lambda x: lambda y: y
.
Upvotes: 2
Views: 105
Reputation: 3413
There are tricks that you could do with metaclasses (__metaclass__
class variable) or the __getattribute__
special method. But the documentation states:
Bypassing the getattribute() machinery in this fashion provides significant scope for speed optimisations within the interpreter, at the cost of some flexibility in the handling of special methods (the special method must be set on the class object itself in order to be consistently invoked by the interpreter)
Which means that if you want to make sure that the parent class is never handled directly, you need to intercept everything. And for int, that is described as emulating numeric types (i.e.: implementing all those methods).
That said, I believe you could implement all those methods in your class quite easily by creating a lambda or generic method that takes two parameters and just calls super on them. And then assign that method to all the specific methods that you need to implement. So you implement once and reuse it.
Upvotes: 1