6

I am trying to make my JSON encoder dump floats with only 2 decimal precision. So '2.241' becomes '2.24'

I've read in this answer by Alex Martelli that you can overwrite the default FLOAT_REPR of json.encoder. I have tried the following:

>>> import json
>>> json.encoder.FLOAT_REPR = lambda o: format(o, '.2f')

But I dont get the same results:

>>> json.dumps(2.241)
'2.241'

And I can even verify the FLOAT_REPR is changed:

>>> print json.encoder.FLOAT_REPR
<function <lambda> at 0xb....>

And works as expected:

>>> json.encoder.FLOAT_REPR(2.241)
2.24

Why is the built-in JSON module not using the FLOAT_REPR when I can see that it has been overwritten and the solution should be working according to Alex Martelli?

I have tested this on two different computers, both running Python 2.7.6 on Ubuntu 14.0.4.

TylerH
  • 20,799
  • 66
  • 75
  • 101
  • 1
    I found a comment in the mentioned question stating that "onkey patching json.encoder.FLOAT_REPR does not work if your Python runtime uses a C version of the JSON module" this can explain why it does not work. – Johannes valbjørn Sep 13 '15 at 16:46

1 Answers1

3

The problem occurs beause of the CPython speedups done by the c_make_encoder in json.encoder.

If you set it to None then the json.encoder.FLOAT_REPR trick works as explained in this answer on the same question:

The monkey-patch trick does not seem to work with the original simplejson module if the C speedups are installed:

My implementation can be seen in the jsonplustypes repository.

Note: This solution doesn't work on python 3.6+

roschach
  • 8,390
  • 14
  • 74
  • 124