I have a list of dictionaries, and some of them are subsets:
l = [
{'zero': 'zero', 'one': 'example', 'two': 'second'},
{'zero': 'zero', 'one': 'example', 'two': 'second', 'three': 'blabla'},
{'zero': 'zero'},
{'zero': 'non-zero', 'one': 'example'}, ...
]
And I want to create a new list of dictionaries that do not contain a subset of dictionaries.
res = [
{'zero': 'zero', 'one': 'example', 'two': 'second', 'three': 'blabla'},
{{'zero': 'non-zero', 'one': 'example'}, ...
]
This work around will create a new list that only contains dictionaries that are not subsets of any other dictionary in the list
res = [
d for d in l
if not any(set(d.items()).issubset(set(other.items()))
for other in l if other != d)
]
print(res)
Output:
[{'zero': 'zero', 'one': 'example', 'two': 'second', 'three': 'blabla'},
{'zero': 'non-zero', 'one': 'example'}]
Related
I need to create a dictionary of list of dictionaries or if there is any other way of achieving the below requirement:
i have a set of keys let say
keys = [1,2,3,4,5] (dont consider this as list but i am just showing i have let say 5 keys)
for each key i will have a set of key value pair so something lime below:
d = {
1:{
{'one': 'test', 'two': 'new', 'three': 'dummy'}
{'one': 'testtest', 'two': 'newnew', 'three': 'dummyextra'}
{'one': 'newvalue', 'two': 'newvalue2', 'three': 'newvalue4'}
}
2:{
{'one': 'test1', 'two': 'new1', 'three': 'dummy1'}
{'one': 'testtest2', 'two': 'newnew2', 'three': 'dummyextra2'}
{'one': 'newvalue3', 'two': 'newvalue23', 'three': 'newvalue43'}
}
1:{
{'one': 'test', 'two': 'new', 'three': 'dummy'}
{'one': 'testtest', 'two': 'newnew', 'three': 'dummyextra'}
{'one': 'newvalue', 'two': 'newvalue2', 'three': 'newvalue4'}
}
}
All the inner and outer dictionaries will be forming through loops.
If because of unique key the above is not possible than what will be the alternate solution to get the data in above format (list of dictionaries or dictionary of lists or anything else?).
With above my main agenda is i will have a unique tag that will be the key of outer dictionary and using that tag i will be creating one HTML header,
under that header i will b populating the data i.e. multiple links and that internal data has to come from inner dictionary from the example.
So in this example i have an html page with header title 1 and under this header i will have 3 links that wil come from inner dictionary.
Than i will have header 2 and again 3 links under it and so on.
Kindly help me to achieve this.
Thanks,
You just have to represent lists with [] not {} and don't forget the commas (,) to separate the elements:
d = {
1:[
{'one': 'test', 'two': 'new', 'three': 'dummy'},
{'one': 'testtest', 'two': 'newnew', 'three': 'dummyextra'},
{'one': 'newvalue', 'two': 'newvalue2', 'three': 'newvalue4'}
],
2:[
{'one': 'test1', 'two': 'new1', 'three': 'dummy1'},
{'one': 'testtest2', 'two': 'newnew2', 'three': 'dummyextra2'},
{'one': 'newvalue3', 'two': 'newvalue23', 'three': 'newvalue43'}
],
3:[
{'one': 'test', 'two': 'new', 'three': 'dummy'},
{'one': 'testtest', 'two': 'newnew', 'three': 'dummyextra'},
{'one': 'newvalue', 'two': 'newvalue2', 'three': 'newvalue4'}
]
}
Try to guess something similar to your input (dlist) just to how how to build a dict using a list as a default value and appending data:
dlist = [[2, {'two': 'two1'}], [1, {'one': 'one1'}], [1, {'one': 'one2'}], [2, {'two': 'two2'}] ]
res = {}
for item in dlist:
res.setdefault(item[0], list()).append(item[1])
print(res)
#=> {1: [{'one': 'one1'}, {'one': 'one2'}], 2: [{'two': 'two1'}, {'two': 'two2'}]}
Mapping two datastructures consisting of lists and dictionaries. The mapping from data should be recursively applied to the payload structure.
These are my inputs
data = {
'a': 'Apple',
'b': 'Ball',
'c': 'Cat',
'd': 'Dog',
'e': 'Egg',
'f': 'Fish',
'g': 'Goat',
'h': 'House',
'i': 'Ice-Cream',
'j': 'Jaguar',
'k': 'Key',
'l': 'Lock',
'm': 'Map'
}
and
payload = {
'PI': [
{
'one': 'a',
'two': 'b',
'three': 'c',
'four': {
'five': 'd',
'six': 'e',
'seven': 'f',
'eight': 'g'
}
}, {
'nine': 'h',
'ten': 'i',
'eleven': 'j',
'twelve': 'k'
}
]
}
Expected output:
payload = {
'PI': [
{
'one': 'Apple',
'two': 'Ball',
'three': 'Cat',
'four': {
'five': 'Dog',
'six': 'Egg',
'seven': 'Fish',
'eight': 'Goat'
}
}, {
'nine': 'House',
'ten': 'Ice-Cream',
'eleven': 'Jaguar',
'twelve': 'Key'
}
]
}
This my attempt at creating the mapping but it is not working
def mapping(payload):
for k,v in payload.items():
if(isinstance(v,dict)):
mapping(v)
elif(isinstance(v,list)):
for item in v:
mapping(item)
else:
try:
v = data[v]
except KeyError:
pass
return payload
I get this instead:
{
'PI': [
{
'four': {
'eight': 'g',
'five': 'd',
'seven': 'f',
'six': 'e'
},
'one': 'a',
'three': 'c',
'two': 'b'
},
{
'eleven': 'j',
'nine': 'h',
'ten': 'i',
'twelve': 'k'
}
]
}
Nothing has been replaced.
You can indeed use recursion; recurse for list values, and dictionary elements, and just map directly for everything else. Do not forget to return the result; the recursive function creates new dictionaries and lists:
def replace_strings(value, mapping):
if isinstance(value, list):
return [replace_strings(v, mapping) for v in value]
if isinstance(value, dict):
return {replace_strings(k, mapping): replace_strings(v, mapping)
for k, v in value.items()}
return mapping.get(value, value)
Demo:
>>> pprint(replace_strings(payload, data))
{'PI': [{'four': {'eight': 'Goat',
'five': 'Dog',
'seven': 'Fish',
'six': 'Egg'},
'one': 'Apple',
'three': 'Cat',
'two': 'Ball'},
{'eleven': 'Jaguar',
'nine': 'House',
'ten': 'Ice-Cream',
'twelve': 'Key'}]}
Your code had several issues:
You ignored the return value of any recursive call.
You returned the original input, unaltered.
Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.
Questions asking for code must demonstrate a minimal understanding of the problem being solved. Include attempted solutions, why they didn't work, and the expected results. See also: Stack Overflow question checklist
Closed 9 years ago.
Improve this question
Could somebody help me to transform this:
a = [{'one': 4, 'name': 'value1', 'two': 25}, {'one': 2, 'name': 'value1', 'two': 18}, {'one': 1, 'name': 'value1', 'two': 15}, {'one': 2, 'name': 'value2', 'two': 12}, {'one': 1, 'name': 'value2', 'two': 10}]
to something like this:
b = [{'value1': [(4, 25), (2, 18), (1, 15)]}, {'value2': [(2, 12), (1, 10)]}]
try this:
>>> di = {}
>>> for i in a:
... if di.get(i['name']):
... di[i['name']].append((i['one'], i['two']))
... else:
... di[i['name']] = []
... di[i['name']].append((i['one'], i['two']))
I reccomend to do like this:
#First create a small dictionary, wich is used to get the keys(name,two,one):
smalld = {'name': 'value1', 'two': 25, 'one': 4}
#Then create the big dict, the dict you are going to get the data
bigd = [{'one': 4, 'name': 'value1', 'two': 25},
{'one': 2, 'name': 'value1', 'two': 18},
{'one': 1, 'name': 'value1', 'two': 15},
{'one': 2, 'name': 'value2', 'two': 12},
{'one': 1, 'name': 'value2', 'two': 10}]
#Then create empty final dict where you
#will use the other dict to create this one
finald = {}
#and now the "magic" loop. k get keys value and run over the big dict to get data.
for k in smalld.iterkeys():
finald[k] = tuple(finald[k] for finald in bigd) #Edited, this line had a mistake
a = [{'one': 4, 'name': 'value1', 'two': 25},
{'one': 2, 'name': 'value1', 'two': 18},
{'one': 1, 'name': 'value1', 'two': 15},
{'one': 2, 'name': 'value2', 'two': 12},
{'one': 1, 'name': 'value2', 'two': 10}]
_d = {ele['name']:[] for ele in a}
for _dict in a:
_temp = {_dict['name']:(_dict['one'], _dict['two']) for ele in _dict}
_d[_temp.keys()[0]].append(_temp[_temp.keys()[0]])
print _d
Output:
{'value2': [(2, 12), (1, 10)], 'value1': [(4, 25), (2, 18), (1, 15)]}
I have the following data structure: {'one':['a','b','c'],'two':['q','w','e'],'three':['t','u','y'],...}. So, the dictionary has variant count of keys. Each array, picked by dict's key has similar length. How I can convert this structure to following: [{'one':'a','two':'q','three':'t'},{'one':'b','two':'w','three':'y'},...]?
I think I should use itertools.izip(), but how i can apply it with not predefined count of args? Maybe something like this: itertools.izip([data[l] for l in data.keys()])?
TIA!
Not terribly elegant, but does the trick:
In [9]: [{k:v[i] for (k,v) in d.items()} for i in range(len(d.values()[0]))]
Out[9]:
[{'one': 'a', 'three': 't', 'two': 'q'},
{'one': 'b', 'three': 'u', 'two': 'w'},
{'one': 'c', 'three': 'y', 'two': 'e'}]
I can't help thinking that there's got to be a better way to phrase the i loop, but nothing comes to mind right now.
Alternatively:
In [50]: map(dict, zip(*[[(k, v) for v in l] for k, l in d.items()]))
Out[50]:
[{'one': 'a', 'three': 't', 'two': 'q'},
{'one': 'b', 'three': 'u', 'two': 'w'},
{'one': 'c', 'three': 'y', 'two': 'e'}]
Not sure if this is much of an improvement on the readability front though.
Your assessment in using izip is correct but the way of using it is not quite right
You first need to
get the items as a list of tuples (key, value), (using iteritems() method if using Py2.x or items() if using Py3.x)
create a scalar product of key and value
flatten the list (using itertools.chain)
zip it (using itertools.izip)
and then create a dict of each element
Here is the sample code
>>> from pprint import PrettyPrinter
>>> pp = PrettyPrinter(indent = 4)
>>> pp.pprint(map(dict, izip(*chain((product([k], v) for k, v in data.items())))))
[ { 'one': 'a', 'three': 't', 'two': 'q'},
{ 'one': 'b', 'three': 'u', 'two': 'w'},
{ 'one': 'c', 'three': 'y', 'two': 'e'}]
>>>
lst = [1,2,3,4]
I have hard coded keys ['one','two','three','four','five']
and I want the dictionary like
{'one':1, 'two':2, 'three':3, 'four':4, 'five':None}
Keys are always more than the number of items in list.
import itertools
lst = [1,2,3,4]
lst2 = ['one','two','three','four','five']
print dict(itertools.izip_longest(lst2, lst, fillvalue=None))
# {'five': None, 'four': 4, 'one': 1, 'three': 3, 'two': 2}
Here are a couple of ways to do it
>>> K=['one','two','three','four','five']
>>> V=[1,2,3,4]
>>> dict(map(None, K, V))
{'four': 4, 'three': 3, 'five': None, 'two': 2, 'one': 1}
>>> D=dict.fromkeys(K)
>>> D.update(zip(K,V))
>>> D
{'four': 4, 'three': 3, 'five': None, 'two': 2, 'one': 1}
>>> dict(zip(keys, lst + [None]*(len(keys)-len(lst))))
{'four': 4, 'three': 3, 'five': None, 'two': 2, 'one': 1}