7

I want to dump a dictionary to file, like in Dump Python dictionary to JSON file. But I faced with a problem with encoding: When I simply do

print(data) 

I get something like this in terminal:

{'legend': '\n\r\n\t\tНа прямой расположены стойла, в которые необходимо расставить коров так, чтобы минимальное расcтояние между коровами было как можно больше.\r\n    \n', 'input_specification': '\n\r\n     Входные данные\r\n    \n\r\n\t\tВ первой строке вводятся числа N\xa0 (2 < N  < 10001) – количество стойл и K\xa0 (1 < K < N ) – количество коров. Во второй строке\xa0задаются N натуральных чисел в порядке возрастания – координаты стойл (координаты не превосходят 109)\r\n    \n', 'output_specification': '\n\r\n     Выходные данные\r\n    \n\r\n\t\tВыведите одно число – наибольшее возможное допустимое расстояние.\r\n    \n'}

So it is normal, human-readable text. But when I dump the same dictionary to some json file this way:

with open('Data\{0}.json'.format(i), 'w') as file:
        json.dump(data, file) 

There is strange mess of special characters in the file:

{"legend": "\n\r\n\t\t\u041d\u0430 \u043f\u0440\u044f\u043c\u043e\u0439 \u0440\u0430\u0441\u043f\u043e\u043b\u043e\u0436\u0435\u043d\u044b \u0441\u0442\u043e\u0439\u043b\u0430, \u0432 \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e \u0440\u0430\u0441\u0441\u0442\u0430\u0432\u0438\u0442\u044c \u043a\u043e\u0440\u043e\u0432 \u0442\u0430\u043a, \u0447\u0442\u043e\u0431\u044b \u043c\u0438\u043d\u0438\u043c\u0430\u043b\u044c\u043d\u043e\u0435 \u0440\u0430\u0441c\u0442\u043e\u044f\u043d\u0438\u0435 \u043c\u0435\u0436\u0434\u0443 \u043a\u043e\u0440\u043e\u0432\u0430\u043c\u0438 \u0431\u044b\u043b\u043e \u043a\u0430\u043a \u043c\u043e\u0436\u043d\u043e \u0431\u043e\u043b\u044c\u0448\u0435.\r\n    \n", "input_specification": "\n\r\n     \u0412\u0445\u043e\u0434\u043d\u044b\u0435 \u0434\u0430\u043d\u043d\u044b\u0435\r\n    \n\r\n\t\t\u0412 \u043f\u0435\u0440\u0432\u043e\u0439 \u0441\u0442\u0440\u043e\u043a\u0435 \u0432\u0432\u043e\u0434\u044f\u0442\u0441\u044f \u0447\u0438\u0441\u043b\u0430 N\u00a0 (2 < N  < 10001) \u2013 \u043a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e \u0441\u0442\u043e\u0439\u043b \u0438 K\u00a0 (1 < K < N ) \u2013 \u043a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e \u043a\u043e\u0440\u043e\u0432. \u0412\u043e \u0432\u0442\u043e\u0440\u043e\u0439 \u0441\u0442\u0440\u043e\u043a\u0435\u00a0\u0437\u0430\u0434\u0430\u044e\u0442\u0441\u044f N \u043d\u0430\u0442\u0443\u0440\u0430\u043b\u044c\u043d\u044b\u0445 \u0447\u0438\u0441\u0435\u043b \u0432 \u043f\u043e\u0440\u044f\u0434\u043a\u0435 \u0432\u043e\u0437\u0440\u0430\u0441\u0442\u0430\u043d\u0438\u044f \u2013 \u043a\u043e\u043e\u0440\u0434\u0438\u043d\u0430\u0442\u044b \u0441\u0442\u043e\u0439\u043b (\u043a\u043e\u043e\u0440\u0434\u0438\u043d\u0430\u0442\u044b \u043d\u0435 \u043f\u0440\u0435\u0432\u043e\u0441\u0445\u043e\u0434\u044f\u0442 109)\r\n    \n", "output_specification": "\n\r\n     \u0412\u044b\u0445\u043e\u0434\u043d\u044b\u0435 \u0434\u0430\u043d\u043d\u044b\u0435\r\n    \n\r\n\t\t\u0412\u044b\u0432\u0435\u0434\u0438\u0442\u0435 \u043e\u0434\u043d\u043e \u0447\u0438\u0441\u043b\u043e \u2013 \u043d\u0430\u0438\u0431\u043e\u043b\u044c\u0448\u0435\u0435 \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e\u0435 \u0434\u043e\u043f\u0443\u0441\u0442\u0438\u043c\u043e\u0435 \u0440\u0430\u0441\u0441\u0442\u043e\u044f\u043d\u0438\u0435.\r\n    \n"}

I tried to specify ensure_ascii=False like here: Python Saving JSON Files as UTF-8, but it throws UnicodeEncodeError:

UnicodeEncodeError: 'charmap' codec can't encode characters in position 11-12: character maps to <undefined>

All in all, how can I dump dictionary to JSON file without messing up with encoding?

4
  • What version of Python do you use?
    – handras
    Feb 24, 2019 at 7:38
  • @handras 3.7.2 32bit
    – keddad
    Feb 24, 2019 at 7:41
  • How are u using ensure_ascii = False ?
    – skaul05
    Feb 24, 2019 at 7:50
  • 1
    The "mess" is valid JSON using Unicode escape codes. It's just not as readable. When you read it back in it will be correct. Feb 24, 2019 at 8:17

1 Answer 1

12

You need to open the file specifying the file encoding.

with open('Data{0}.json'.format(1), 'w', encoding='utf-8') as file:
    json.dump(data, file, ensure_ascii=False)

This way I have dumped your example data sucessfully.

2
  • encoding = 'utf-8' is not necessary because the file reading and writing is all done as utf8 by default in Python 3 open() @handras
    – skaul05
    Feb 24, 2019 at 8:00
  • 2
    @skaul05 No, open uses locale.getpreferredencoding(False), which depends on the OS and terminal configuration. It's better to be explicit and specify the encoding. Not all Linux are correctly configured for UTF-8, and the Windows terminal doesn't use it, although some Python IDEs do. Feb 24, 2019 at 8:13

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.