Home > database >  Correct way to json.dump() nested dictionary AND read back into python w/ json.load()?
Correct way to json.dump() nested dictionary AND read back into python w/ json.load()?

Time:02-19

I have nested dictionaries in "letters" in python. I want to write out all objects to a file so that when the program reruns each dictionary can be imported into the top dictionary "letters" and then appended with additional user inputs/dictionaries.

I think my issue is in not correctly using json.dumps() for each nested dictionary. *I know my dictionary names need to be unique, working on that.

 import json
letter_dict = {}
print('letters dict:', letter_dict)

for number in range(1, 6):
    print('what letter is in position ', number, '?:')
    letter = input()
    if letter == '':
        print('no additional inputs')
        break
    else:
        code = input('what code?:')
        #position = input('what position?:')
    letter_dict['letter'] = letter
    letter_dict['code'] = code
    letter_dict['position'] = number

    print(letter)
    print(code)
    #print(position)
    print(number)
    print(letter_dict)

    with open('letters.txt', 'a') as file:
        dictname = "'dict"   str(number)   "': "
        file.write(dictname)
        file.write(json.dumps(letter_dict))
        file.write(',\n')

letters.txt =

'dict1': {"letter": "a", "code": "y", "position": 1},
'dict2': {"letter": "p", "code": "y", "position": 2},
'dict1': {"letter": "a", "code": "y", "position": 1},

import function:

import json

with open('letters.txt', 'r') as file:
    print(json.load(file))

errors:

  File "/usr/lib/python3.9/json/__init__.py", line 293, in load
    return loads(fp.read(),
  File "/usr/lib/python3.9/json/__init__.py", line 346, in loads
    return _default_decoder.decode(s)
  File "/usr/lib/python3.9/json/decoder.py", line 337, in decode
    obj, end = self.raw_decode(s, idx=_w(s, 0).end())
  File "/usr/lib/python3.9/json/decoder.py", line 355, in raw_decode
    raise JSONDecodeError("Expecting value", s, err.value) from None
json.decoder.JSONDecodeError: Expecting value: line 1 column 1 (char 0)

CodePudding user response:

I don't know if it's the problem but your file is not a valid JSON,

  • You must use double quotes instead of simple
  • The final comma is not supposed to be there
  • You must put your dict into curly brackets
  • Do not duplicate dict keys.

Valid file will be:

{
"dict1": {"letter": "a", "code": "y", "position": 1},
"dict2": {"letter": "p", "code": "y", "position": 2},
"dict3": {"letter": "a", "code": "y", "position": 1}
}

CodePudding user response:

Rather than trying to write yourself a valid json just let the json.dump do the heavy-lifting for you. With a main_dict variable to collect the subdicts, you can just dump it to your file:

import json
main_dict = {}

for number in range(1, 6):
    letter_dict = {}
    letter = input(f'what letter is in position {number}? ')
    if letter:
        code = input('what code?:')
    else:
        print('no additional inputs')
        break
      
    letter_dict['letter'] = letter
    letter_dict['code'] = code
    letter_dict['position'] = number

    main_dict[f'dict{number}'] = letter_dict

with open('letters.json', 'w') as file:
    json.dump(main_dict, file)

Note that I don't open the file letters.txt in append mode because a second run of your program would append another dictionary after the first one, thereby making the json invalid. If you want to append, load the json file in main_dict, add a key-value pair to main_dict and dump again.

  • Related