With MPL 0.62.4, the following script is yielding a few
> badly formatted y-axis labels:
> import matplotlib from matplotlib.matlab import *
> a=array([2,4,6,8,10,12,14,16,18,20])*1e5 plot(a) show()
> I tried adding a "print s,m" statement after line 272: m =
> self._zerorgx.match(s), where s is the original text. Here
> is the output:
> 2.0e+005 <_sre.SRE_Match object at 0x01249608> 4.0e+005
> <_sre.SRE_Match object at 0x01249608> 6.0e+005
> <_sre.SRE_Match object at 0x01249608> 8.0e+005
> <_sre.SRE_Match object at 0x01249608> 1.0e+006
> <_sre.SRE_Match object at 0x01249608> 1.2e+006 None
> 1.4e+006 None 1.6e+006 None 1.8e+006 None 2.0e+006
> <_sre.SRE_Match object at 0x01249608>
> _zerorgx = re.compile('^(.*?)\.?0+(e[+-]\d+)?$'), which is
> greek to me (and I dont have a good reference on
> regexp's).
There's a reason Jamie Zawinski said
Some people, when confronted with a problem, think "I know, I'll use
regular expressions." Now they have two problems.
Here's a re-implementation using string methods. See if it passes all
your tests. More importantly, do you agree that removing the zeros
etc which aren't necessary to visually parse the number is a good
idea?
class ScalarFormatter(Formatter):
"""
Tick location is a plain old number. If viewInterval is set, the
formatter will use %d, %1.#f or %1.ef as appropriate. If it is
not set, the formatter will do str conversion
"""
def __call__(self, x, pos):
'Return the format for tick val x at position pos'
self.verify_intervals()
d = abs(self.viewInterval.span())
return self.pprint_val(x,d)
def pprint_val(self, x, d):
#if the number is not too big and it's an int, format it as an
#int
if abs(x)<1e4 and x==int(x): return '%d' % x
if d < 1e-2: fmt = '%1.3e'
elif d < 1e-1: fmt = '%1.3f'
elif d > 1e5: fmt = '%1.1e'
elif d > 10 : fmt = '%1.1f'
elif d > 1 : fmt = '%1.2f'
else: fmt = '%1.3f'
s = fmt % x
tup = s.split('e')
if len(tup)==2:
mantissa = tup[0].rstrip('0').rstrip('.')
exponent = tup[1].replace('+', '').lstrip('0')
s = '%se%s' %(mantissa, exponent)
return s
JDH