4

I have a following data set that I read in from a text file:

all_examples=   ['A,1,1', 'B,2,1', 'C,4,4', 'D,4,5']

I need to create a list of dictionary as follows:

lst = [ 
{"A":1, "B":2, "C":4, "D":4 },
{"A":1, "B":1, "C":4, "D":5 } 
]

I tried using an generator function but it was hard to create a list as such.

attributes = 'A,B,C'
def get_examples():

    for value in examples:
        yield dict(zip(attributes, value.strip().replace(" ", "").split(',')))
4
  • Your desired output dictionary is not correct. Please edit your post. Commented Mar 9, 2016 at 5:19
  • 2
    Why not have a single key point to a list containing the mapped values, instead? Commented Mar 9, 2016 at 5:19
  • 2
    You can have a list that contains dictionaries. But you can't have a dictionary , that just contains lists. You need key:value pairs in a dictionary. Also your input is strictly a list of strings. So look up using split to turn that into a list of lists first. Commented Mar 9, 2016 at 5:21
  • I think you have []'s mixed up with {}'s. learnpythonthehardway.org/book/ex39.html Commented Mar 9, 2016 at 5:24

4 Answers 4

7

A one liner, just for fun:

all_examples = ['A,1,1', 'B,2,1', 'C,4,4', 'D,4,5']

map(dict, zip(*[[(s[0], int(x)) for x in s.split(',')[1:]] for s in all_examples]))

Produces:

[{'A': 1, 'C': 4, 'B': 2, 'D': 4}, 
 {'A': 1, 'C': 4, 'B': 1, 'D': 5}]

As a bonus, this will work for longer sequences too:

all_examples = ['A,1,1,1', 'B,2,1,2', 'C,4,4,3', 'D,4,5,6']

Output:

[{'A': 1, 'C': 4, 'B': 2, 'D': 4},
 {'A': 1, 'C': 4, 'B': 1, 'D': 5},
 {'A': 1, 'C': 3, 'B': 2, 'D': 6}]

Explanation:

map(dict, zip(*[[(s[0], int(x)) for x in s.split(',')[1:]] for s in all_examples]))
  • [... for s in all_examples] For each element in your list:
  • s.split(',')[1:] Split it by commas, then take each element after the first
  • (...) for x in and turn it into a list of tuples
  • s[0], int(x) of the first letter, with that element converted to integer
  • zip(*[...]) now transpose your lists of tuples
  • map(dict, ...) and turn each one into a dictionary!
Sign up to request clarification or add additional context in comments.

2 Comments

great solution, but is there anyway to create an ordered dictionary? The result here is unordered.
Regular dictionaries in python are always unordered; if you want an ordered one just add from collections import OrderedDict and use that instead of dict.
3

Also just for fun, but with a focus on understandability:

all_examples = ['A,1,1', 'B,2,1', 'C,4,4', 'D,4,5']
ll = [ x.split(",") for x in all_examples ]
ld = list()
for col in range(1, len(ll[0])):
    ld.append({ l[0] : int(l[col]) for l in ll })
print ld

will print

[{'A': 1, 'C': 4, 'B': 2, 'D': 4}, {'A': 1, 'C': 4, 'B': 1, 'D': 5}]

Works as long as the input is csv with integers and lines are same length.

Dissection: I will use the teminology "thing" for A, B and C and "measurement" for the "columns" in the data, i.e. those values in the same "csv-column" of the inut data.

Get the string input data into a list for each line: A,1,1 -> ["A","1","1"]

ll = [ x.split(",") for x in all_examples ]

The result is supposed to be a list of dicts, so let's initialize one:

ld = list()

For each measurement (assuming that all lines have the same number of columns):

for col in range(1, len(ll[0])):

Take the thing l[0], e.g. "A", from the line and assign the numeric value int(), e.g. 1, of the measurement in the respective column l[col], e.g. "1", to the thing. Then use a dictionary comprehension to combine it into the next line of the desired result. Finally append() the dict to the result list ld.

    ld.append({ l[0] : int(l[col]) for l in ll })

View unfoamtted. Use print json.dumps(ld, indent=4) for more convenient display:

print ld

Hope this helps. Find more on dict comprehensions e.g. here (Python3 version of this great book).

1 Comment

can you explain a bit on this one?
1

You actually have a list of strings, and you'd like to have a list of paired dictionaries generated from the same key in the tuple triplets of each string.

To keep this relatively simple, I'll use a for loop instead of a complicated dictionary comprehension structure.

my_dictionary_list = list()
d1 = dict()
d2 = dict()
for triplet_str in all_examples:
    key, val1, val2 = triplet_str.split(',')
    d1[key] = val1
    d2[key] = val2
my_dictionary_list.append(d1)
my_dictionary_list.append(d2)

>>> my_dictionary_list
my_dictionary_list
[{'A': '1', 'B': '2', 'C': '4', 'D': '4'},
 {'A': '1', 'B': '1', 'C': '4', 'D': '5'}]

Comments

1

Your question should be "How to crate list of dictionaries?". Here's something you would like to consider.

>>> dict={}
>>> dict2={}
>>> new_list = []
>>> all_examples=['A,1,1', 'B,2,1', 'C,4,4', 'D,4,5']
>>> for k in all_examples:
...     ele=k.split(",")
...     dict[str(ele[0])]=ele[1]
...     dict[str(ele[0])]=ele[2]
...     new_list.append(dict)
...     new_list.append(dict2)
>>> dict
{'A': '1', 'C': '4', 'B': '2', 'D': '4'}
>>> dict2
{'A': '1', 'C': '4', 'B': '1', 'D': '5'}

Comments

Your Answer

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

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.