json1-3 Exercise 1: What Survives dumps -> loads? ================================================== Run with Python 3.14.0: py ex1.py (ASCII-only output on purpose: it uses ascii() so a Windows console can show it) --- ex1.py --- # Exercise 1: which Python values survive dumps -> loads? import json, math, datetime as dt from decimal import Decimal samples = { 'dict, str keys': {'a': 1, 'b': [True, None, 2.5]}, 'tuple': (1, 2), 'dict, int keys': {1: 'a', 2: 'b'}, 'dict, float key': {2.5: 'x'}, 'dict, bool/None key': {True: 'x', None: 'y'}, 'int 10**20': 10**20, 'float 1.0': 1.0, 'float -0.0': -0.0, 'nan': float('nan'), 'inf': float('inf'), 'str with unicode': 'Zo' + chr(235) + ' ' + chr(0x1F600), 'date': dt.date(2026, 10, 12), 'Decimal': Decimal('19.99'), 'set': {1, 2}, 'bytes': b'x', 'key collision': {1: 'int', '1': 'str'}, } print('value'.ljust(22) + 'dumps'.ljust(46) + 'loads(dumps) == original ?') for label, v in samples.items(): try: text = json.dumps(v) except Exception as e: print(label.ljust(22) + ('ERROR ' + type(e).__name__).ljust(46) + '-'); continue back = json.loads(text) same = (back == v) if v == v else ('nan != nan, so test with math.isnan: ' + str(math.isnan(back))) print(label.ljust(22) + ascii(text)[:44].ljust(46) + str(same) + ' -> ' + ascii(back)[:40]) Output: value dumps loads(dumps) == original ? dict, str keys '{"a": 1, "b": [true, null, 2.5]}' True -> {'a': 1, 'b': [True, None, 2.5]} tuple '[1, 2]' False -> [1, 2] dict, int keys '{"1": "a", "2": "b"}' False -> {'1': 'a', '2': 'b'} dict, float key '{"2.5": "x"}' False -> {'2.5': 'x'} dict, bool/None key '{"true": "x", "null": "y"}' False -> {'true': 'x', 'null': 'y'} int 10**20 '100000000000000000000' True -> 100000000000000000000 float 1.0 '1.0' True -> 1.0 float -0.0 '-0.0' True -> -0.0 nan 'NaN' nan != nan, so test with math.isnan: True -> nan inf 'Infinity' True -> inf str with unicode '"Zo\\u00eb \\ud83d\\ude00"' True -> 'Zo\xeb \U0001f600' date ERROR TypeError - Decimal ERROR TypeError - set ERROR TypeError - bytes ERROR TypeError - key collision '{"1": "int", "1": "str"}' False -> {'1': 'str'} WHY THIS WORKS AS AN ANSWER --------------------------- The script prints the JSON text itself, not only a yes/no, so each loss can be seen: the tuple comes back as a list, int/float/bool/None keys come back as the strings "1", "2.5", "true", "null", and the collision case writes a duplicate key and reads back only the last value, with no error at all. The values with no JSON form (date, Decimal, set, bytes) raise TypeError and are marked ERROR instead of being skipped, so nothing is hidden. NaN is the one value that is not equal to itself, so a plain == would call it a failure; math.isnan is used for it (a check on the check). The True rows (str-keyed dict, int, -0.0, inf, the unicode string) are the controls that show the comparison can say True. Not tested: other Python versions, and the third-party libraries, which may differ on every row.