3

I am trying to create a nested dictionary from a mysql query but I am getting a key error

result = {}

for i, q in enumerate(query):

    result['data'][i]['firstName'] = q.first_name
    result['data'][i]['lastName'] = q.last_name
    result['data'][i]['email'] = q.email

error

KeyError: 'data'

desired result

result = {
    'data': {
        0: {'firstName': ''...}
        1: {'firstName': ''...}
        2: {'firstName': ''...}
    }
}
Rudie
  • 52,220
  • 42
  • 131
  • 173
user3071933
  • 187
  • 1
  • 3
  • 10
  • you want the keys to be the integers from 0 to `len(result)`? why not use a list? – jpwagner Dec 05 '13 at 20:32
  • Why do you use `'data'` if you don't want to have it in `result`? – Lev Levitsky Dec 05 '13 at 20:32
  • 1
    You should look up dictionaries in the docs – keyser Dec 05 '13 at 20:32
  • @KEYSER Be easy with OP, this is a typical assumption error for any beginner to assume flat dict assignment would create nested dict. If everyone needs to learn from docs (which we didnt refer), then why SOF ;) – user2390183 Dec 05 '13 at 21:37
  • possible duplicate of [What's the best way to initialize a dict of dicts in Python?](http://stackoverflow.com/questions/651794/whats-the-best-way-to-initialize-a-dict-of-dicts-in-python) – timfeirg Oct 10 '14 at 08:43

4 Answers4

10

You wanted to create a nested dictionary

result = {} will create an assignment for a flat dictionary, whose items can have any values like "string", "int", "list" or "dict"

For this flat assignment

python knows what to do for result["first"]

If you want "first" also to be another dictionary you need to tell Python by an assingment result['first'] = {}.

otherwise, Python raises "KeyError"

I think you are looking for this :)

>>> from collections import defaultdict
>>> mydict = lambda: defaultdict(mydict)
>>> result = mydict()
>>> result['Python']['rules']['the world'] = "Yes I Agree"
>>> result['Python']['rules']['the world']
'Yes I Agree'
Eyal.D
  • 550
  • 3
  • 18
user2390183
  • 975
  • 8
  • 17
1
result = {}
result['data'] = {}

for i, q in enumerate(query):
    result['data']['i'] = {}
    result['data'][i]['firstName'] = q.first_name
    result['data'][i]['lastName'] = q.last_name
    result['data'][i]['email'] = q.email

Alternatively, you can use you own class which adds the extra dicts automatically

class AutoDict(dict):
    def __missing__(self, k):
        self[k] = AutoDict()
        return self[k]

result = AutoDict()

for i, q in enumerate(query):
    result['data'][i]['firstName'] = q.first_name
    result['data'][i]['lastName'] = q.last_name
    result['data'][i]['email'] = q.email
John La Rooy
  • 295,403
  • 53
  • 369
  • 502
0

result['data'] does exist. So you cannot add data to it.

Try this out at the start:

result = {'data': []};
qwertynl
  • 3,912
  • 1
  • 21
  • 43
0

You have to create the key data first:

result = {}
result['data'] = {}

for i, q in enumerate(query):
    result['data'][i] = {}
    result['data'][i]['firstName'] = q.first_name
    result['data'][i]['lastName'] = q.last_name
    result['data'][i]['email'] = q.email
Hyperboreus
  • 31,997
  • 9
  • 47
  • 87