Message62227
Jeffrey:
Yay for measurements!
I was going to say that __add__ is inefficient because it makes so
many function calls, but it turns out that, as you say, the cost of
constructing a new Rational instance drowns everything else. On my
2.8GHz iMac, Rational(2,3) costs ~80 usec. This goes down to 50 usec
if I make it inherit from object -- the ABC machinery costs 30 usecs!
If I then also comment out all the typechecking of numerator and
denominator and go straight into the gcd(), the constructor costs go
down to 6 (six!) usecs. Beyond that it's slim pickings; replacing
super() with object or inlining gcd wins perhaps half an usec. But
once the constructor is down to 5-6 usec, the half usec for going
through the constructor (times 6 for 6 constructor calls in _add()!)
might be a significant gain to also try and inline the common case of
the binary operators.
In the mean time I have two recommendations if you want to make the
constructor faster without losing functionality: (a) remove the direct
inheritance from RationalAbc (using virtual inheritance instead); (b)
special-case the snot out of the common path in the constructor
(called with two ints).
An alternative might be to have a private class or static method to
construct a Rational from two ints that is used internally; it could
use object.__new__ instead of super() so as to save the ABC overhead.
But I'm not sure if this will always work.
Unrelated issue: I just realized for the first time that we have two
classes named 'Rational': the ABC and the concrete implementation.
That's going to be awfully confusing. Perhaps it's not too late to
rename rational.py/Rational to fractions.py/Fraction? |
|
Date |
User |
Action |
Args |
2008-02-09 16:37:30 | gvanrossum | set | spambayes_score: 0.00846061 -> 0.00846061 recipients:
+ gvanrossum, rhettinger, facundobatista, mark.dickinson, jyasskin |
2008-02-09 16:37:29 | gvanrossum | link | issue1682 messages |
2008-02-09 16:37:28 | gvanrossum | create | |
|