Correct handling of zeropad and fill_char options
This commit is contained in:
@@ -1397,8 +1397,8 @@ _FLOAT_FORMAT_SPECIFICATION_MATCHER = re.compile(r"""
|
||||
(?P<sign>[-+ ]?)
|
||||
(?P<no_neg_0>z)?
|
||||
(?P<alternate>\#)?
|
||||
(?P<zeropad>0)?
|
||||
(?P<width>0|[1-9][0-9]*)?
|
||||
(?P<zeropad>0(?=0*[1-9]))?
|
||||
(?P<width>[0-9]+)?
|
||||
(?P<thousands_separators>[,_])?
|
||||
(?:\.(?P<precision>[0-9]+))?
|
||||
(?P<rounding>[UDYZN])?
|
||||
@@ -1470,13 +1470,11 @@ def read_format_spec(format_spec):
|
||||
if rounding_char is not None:
|
||||
format_dict['rounding'] = _GMPY_ROUND_CHAR_DICT[rounding_char]
|
||||
|
||||
if match['zeropad'] and match['fill_char']:
|
||||
raise ValueError('Cannot specify both 0-padding and a fill '
|
||||
'character')
|
||||
|
||||
if match['zeropad']:
|
||||
format_dict['align'] = '='
|
||||
format_dict['fill_char'] = '0'
|
||||
if not match['align']:
|
||||
format_dict['align'] = '='
|
||||
if not match['fill_char']:
|
||||
format_dict['fill_char'] = '0'
|
||||
|
||||
if format_dict['precision'] < 0 and format_dict['type'].lower() not in ['', 'a', 'b']:
|
||||
format_dict['precision'] = 6
|
||||
|
||||
@@ -54,7 +54,9 @@ def fmt_str(draw, types='fFeE', for_complex=False):
|
||||
skip_thousand_separators = True
|
||||
|
||||
# Width
|
||||
res += draw(st.sampled_from(['']*7 + list(map(str, range(1, 40)))))
|
||||
res += draw(st.sampled_from(['']*7 + list(map(str, range(1, 40)))
|
||||
+ ([] if for_complex else ['0' + str(_)
|
||||
for _ in range(40)])))
|
||||
|
||||
# grouping character (thousand_separators)
|
||||
gchar = draw(st.sampled_from([''] + list(',_')))
|
||||
@@ -470,6 +472,7 @@ def test_mpf_fmt_cpython():
|
||||
allow_subnormal=True))
|
||||
@example(fmt='.0g', x=9.995074823339339e-05) # issue 880
|
||||
@example(fmt='.016f', x=0.1) # issue 915
|
||||
@example(fmt='0030f', x=0.3)
|
||||
def test_mpf_floats_bulk(fmt, x):
|
||||
'''
|
||||
These are additional random tests that check that mp.mpf and fp.mpf yield
|
||||
@@ -479,6 +482,9 @@ def test_mpf_floats_bulk(fmt, x):
|
||||
if not x and math.copysign(1, x) == -1:
|
||||
return # skip negative zero
|
||||
spec = read_format_spec(fmt)
|
||||
if (spec['width'] > 0 and spec['fill_char'] == '0'
|
||||
and spec['thousands_separators']):
|
||||
return # issue 917
|
||||
if not spec['type'] and spec['precision'] < 0 and math.isfinite(x):
|
||||
# The mpmath could choose a different decimal
|
||||
# representative (wrt CPython) for same binary
|
||||
@@ -799,11 +805,6 @@ def test_errors():
|
||||
with pytest.raises(ValueError, match="Invalid format specifier '12.3 E '"):
|
||||
f"{mp.mpf('4'):12.3 E }"
|
||||
|
||||
with pytest.raises(ValueError, match="Cannot specify both 0-padding "
|
||||
"and a fill character"):
|
||||
f"{mp.mpf('4'):q<03f}"
|
||||
|
||||
|
||||
|
||||
@settings(max_examples=10000)
|
||||
@given(st.floats(allow_nan=True, allow_infinity=True,
|
||||
|
||||
Reference in New Issue
Block a user