diff options
| author | Antony Lee <anntzer.lee@gmail.com> | 2021-08-05 12:20:12 +0200 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2021-08-05 13:20:12 +0300 |
| commit | d97e31e891e868457d710d53b8ddadb0d473ec8a (patch) | |
| tree | 3515f22bb31a111ae029a9c5a5384b379f46ffca /numpy | |
| parent | b3e3567544dc2b41e1bcc89157b977cf12ef2efb (diff) | |
| download | numpy-d97e31e891e868457d710d53b8ddadb0d473ec8a.tar.gz | |
PERF: Speed-up common case of loadtxt()ing non-hex floats. (#19598)
* PERF: Speed-up common case of loadtxt()ing non-hex floats.
`python runtests.py --bench bench_io` reports a ~5-10% perf gain.
* TST: Add tests to check fromhex not called unintentionally.
Adds regression tests to check that the logic surrounding when
the default floatconv applies the fromhex conversion does not
change.
Co-authored-by: Ross Barnowski <rossbar@berkeley.edu>
Diffstat (limited to 'numpy')
| -rw-r--r-- | numpy/lib/npyio.py | 13 | ||||
| -rw-r--r-- | numpy/lib/tests/test_io.py | 22 |
2 files changed, 31 insertions, 4 deletions
diff --git a/numpy/lib/npyio.py b/numpy/lib/npyio.py index 9ae5d0b59..3b6a1c563 100644 --- a/numpy/lib/npyio.py +++ b/numpy/lib/npyio.py @@ -732,10 +732,15 @@ def _getconv(dtype): """ Find the correct dtype converter. Adapted from matplotlib """ def floatconv(x): - x.lower() - if '0x' in x: - return float.fromhex(x) - return float(x) + try: + return float(x) # The fastest path. + except ValueError: + if '0x' in x: # Don't accidentally convert "a" ("0xa") to 10. + try: + return float.fromhex(x) + except ValueError: + pass + raise # Raise the original exception, which makes more sense. typ = dtype.type if issubclass(typ, np.bool_): diff --git a/numpy/lib/tests/test_io.py b/numpy/lib/tests/test_io.py index 534ab683c..d97ad76df 100644 --- a/numpy/lib/tests/test_io.py +++ b/numpy/lib/tests/test_io.py @@ -984,6 +984,28 @@ class TestLoadTxt(LoadTxtBase): res = np.loadtxt(c, dtype=dt) assert_equal(res, tgt, err_msg="%s" % dt) + def test_default_float_converter_no_default_hex_conversion(self): + """ + Ensure that fromhex is only used for values with the correct prefix and + is not called by default. Regression test related to gh-19598. + """ + c = TextIO("a b c") + with pytest.raises( + ValueError, match="could not convert string to float" + ): + np.loadtxt(c) + + def test_default_float_converter_exception(self): + """ + Ensure that the exception message raised during failed floating point + conversion is correct. Regression test related to gh-19598. + """ + c = TextIO("qrs tuv") # Invalid values for default float converter + with pytest.raises( + ValueError, match="could not convert string to float" + ): + np.loadtxt(c) + def test_from_complex(self): tgt = (complex(1, 1), complex(1, -1)) c = TextIO() |
