[PEP draft 2] Adding new math operators
Rainer Deyke
root at rainerdeyke.com
Wed Aug 9 00:52:04 EDT 2000
"Huaiyu Zhu" <hzhu at localhost.localdomain> wrote in message
news:slrn8p1e12.1ob.hzhu at rocket.knowledgetrack.com...
> Well, conceptually, two sets of operators are equally fundamental: the
> arithmetic type operators + - * / and the lattice type operators (and)
(or)
> (not) (xor), etc. Both of them have two versions, objectwise and
> elementwise. The bitwise operators are elementwise lattice operators when
> each bit in an integer is regarded as an element.
I've mentioned this before: your division between objectwise and elementwise
operators does not hold because it is not clear whether elementwise
operators are "deep" or "shallow". For example ([[0, 1], [2, 3]]
(elementwise+) [[4, 5], [6, 7]]) could evaluate to either [[4, 6], [8, 10]]
or [[0, 1, 4, 5], [2, 3, 6, 7]].
The only truly flexible approach would be to allow users to specify an
arbitrary depth for elementwise operators. In the proposed ~* notation,
that would mean that for every binary operator X there is an operator ~X
which goes one level deeper than X - even if X itself is ~~+. (This makes
the proposed notation useless unless someone figures out how support an
infinite number of operators.)
Another problem with naive elementwise operators is that they require a
ridiculous number of __magic__ functions, all of which are essentially
identical. For example:
class Pair:
def __init__(self, first, second):
self.first = first
self.second = second
def __elementwise_add__(self, other):
return Pair(self.first + other.first, self.second + other.second)
def __elementwise_multiply__(self, other):
return Pair(self.first * other.first, self.second * other.second)
def __elementwise_subtract__(self, other):
return Pair(self.first - other.first, self.second - other.second)
def __elementwise_divide__(self, other):
return Pair(self.first / other.first, self.second / other.second)
def __elementwise_fnord__(self, other):
return Pair(fnord(self.first,other.first),
fnord(self.second,other.second)
def __elementwise_call__(self, other):
return Pair(self.first(other.first), self.second(other.second))
def __elementwise_elementwise_add__(self, other):
return Pair(self.first ~+ other.first, self.second ~+ other.second)
...
A better solution would be to have a method for "elementwise" operations:
class Pair:
def __init__(self, first, second):
self.first = first
self.second = second
def elementwise(self, operation):
return Pair(operation(self.first), operation(self.second))
Alternately, you could add another argument to other __magic__ functions:
class Pair:
def __init__(self, first, second):
self.first = first
self.second = second
def __add__(self, rhs, depth):
if (depth == 0):
return objectwise_add(self, rhs)
else:
return Pair(add(self.first, rhs.first, depth - 1),\
add(self.second, rhs.second, depth - 1)
# Substitute proper infix syntax for add.
--
Rainer Deyke (root at rainerdeyke.com)
Shareware action/role-playing games - http://rainerdeyke.com
"In ihren Reihen zu stehen heisst unter Feinden zu kaempfen" - Abigor
More information about the Python-list
mailing list