I want to replace dictionary's value - python

I want to replace dictionary's value.I have a dictionary whose variable's name is dct like
dct={'A': {'a1': [[10.0, 5.0], [7.0, 7.0], [1.0, 5.0], [20.0, 30.0]],
'a2': [[50.0, 50.0], [55.0, 60.0]],
'a3': [[40.0, 100.0], [100.0, 200.0], [100.0, 140.0], [200.0, 190.0]],
'a4': [[50.0, 70.0], [140.0, 130.0], [160.0, 150.0], [200.0, 180.0]],
'a5': [[100.0, 110.0], [180.0, 210.0], [60.0, 50.0], [200.0, 190.0]] }}
If dictionary's child value like [[10.0, 5.0], [7.0, 7.0], [1.0, 5.0], [20.0, 30.0]] or [[50.0, 50.0], [55.0, 60.0]] can be divided 4,I want to replace 5 instead of the child value.If dictionary's child value can be divided 2,I want to replace 4 instead of the child value.
So, I wrote the codes,
for ky, vl in dct.items():
for k,v in vl.items():
if len(v) %4 == 0:
element[ky] = 5
elif len(v) %2 == 0:
element[ky] = 4
else:
continue
print(element)
But print(element) shows {‘A’: {‘a5’: 5}} so it has only last value.I really cannot understand why such a thing happens.How can I fix this?What is wrong in my codes?

Actually your code is incorrect to perform that given task, here's the correct code to solve your query like whatever you wanted to implement.
Check this below code it works fine and replaces child values by 5 when each child value is divisible by 4 and replaces values by 4 when each child value is divisible by 2
dct = {'A': {'a1': [[10.0, 5.0], [7.0, 7.0], [1.0, 5.0], [20.0, 30.0]],
'a2': [[50.0, 50.0], [55.0, 60.0]],
'a3': [[40.0, 100.0], [100.0, 200.0], [100.0, 140.0], [200.0, 190.0]],
'a4': [[50.0, 70.0], [140.0, 130.0], [160.0, 150.0], [200.0, 180.0]],
'a5': [[100.0, 110.0], [180.0, 210.0], [60.0, 50.0], [200.0, 190.0]] }}
print (dct)
for k,v in dct.items():
for ky,vl in v.items():
for each_elem in (range(0,len(vl))):
if vl[each_elem][0] % 4 == 0:
vl[each_elem][0] = 5
else:
if vl[each_elem][0] % 2 == 0:
vl[each_elem][0] = 4
if vl[each_elem][1] % 4 == 0:
vl[each_elem][1] = 5
else:
if vl[each_elem][1] % 2 == 0:
vl[each_elem][1] = 4
print ("\n")
print (dct)
that gives this output below
{'A': {'a1': [[10.0, 5.0], [7.0, 7.0], [1.0, 5.0], [20.0, 30.0]], 'a3': [[40.0, 100.0], [100.0, 200.0], [100.0, 140.0], [200.0, 190.0]], 'a2': [[50.0, 50.0], [55.0, 60.0]], 'a5': [[100.0, 110.0], [180.0, 210.0], [60.0, 50.0], [200.0, 190.0]], 'a4': [[50.0, 70.0], [140.0, 130.0], [160.0, 150.0], [200.0, 180.0]]}}
{'A': {'a1': [[4, 5.0], [7.0, 7.0], [1.0, 5.0], [5, 4]], 'a3': [[5, 5], [5, 5], [5, 5], [5, 4]], 'a2': [[4, 4], [55.0, 5]], 'a5': [[5, 4], [5, 4], [5, 4], [5, 4]], 'a4': [[4, 4], [5, 4], [5, 4], [5, 5]]}}
Hope this answer work great for you. Have a good time ahead :)

The problem is you are inserting main dict key's into new dict , But in origional dict there are two dict , so you have to maintain a sub or nested dict and then at last you can insert that nested dict to main dict:
Try this code :
dct={'A': {'a1': [[10.0, 5.0], [7.0, 7.0], [1.0, 5.0], [20.0, 30.0]], 'a2': [[50.0, 50.0], [55.0, 60.0]], 'a3': [[40.0, 100.0], [100.0, 200.0], [100.0, 140.0], [200.0, 190.0]], 'a4': [[50.0, 70.0], [140.0, 130.0], [160.0, 150.0], [200.0, 180.0]], 'a5': [[100.0, 110.0], [180.0, 210.0], [60.0, 50.0], [200.0, 190.0]] }}
element={}
for ky, vl in dct.items():
sub_dict={}
for k, v in vl.items():
if len(v) % 4 == 0:
sub_dict[k] = 5
elif len(v) % 2 == 0:
sub_dict[k] = 4
else:
continue
element[ky]=sub_dict
print(element)
output:
{'A': {'a1': 5, 'a2': 4, 'a3': 5, 'a5': 5, 'a4': 5}}

Related

Fill a python dictionary with values from a pandas dataFrame

This is my dictionary, called "reviews":
reviews= {1: {'like', 'the', 'acting'},
2: {'hate', 'plot', 'story'}}
And this is my "lexicon" dataFrame:
import pandas as pd
lexicon = {'word': ['like', 'movie', 'hate'],
'neg': [0.0005, 0.0014, 0.0029],
'pos': [0.0025, 0.0019, 0.0002]
}
lexicon = pd.DataFrame(lexicon, columns = ['word', 'neg','pos'])
print (lexicon)
I need to fill my "reviews" dictionary with the neg and pos values from the "lexicon" dataFrame.
If there is no value in the lexicon, then I want to put 0.5
To finally get this outcome:
reviews= {1: {'like': [0.0005, 0.0025], 'the': [0.5, 0.5], 'acting': [0.5, 0.5]},
2: {'plot': [0.5, 0.5], 'hate': [0.0029, 0.0002], 'story': [0.5, 0.5]}}
You can use df.reindex here.
df_ = lexicon.set_index("word").agg(list, axis=1)
out = {k: df_.reindex(v, fill_value=[0.5, 0.5]).to_dict() for k, v in reviews.items()}
# {1: {'the': [0.5, 0.5], 'like': [0.0005, 0.0025], 'acting': [0.5, 0.5]},
# 2: {'story': [0.5, 0.5], 'hate': [0.0029, 0.0002], 'plot': [0.5, 0.5]}}
Create dictionary from lexicon and then in double dictionary comprehension mapping by dict.get for possible add default value if no match:
d = lexicon.set_index('word').agg(list, axis=1).to_dict()
print (d)
{'like': [0.0005, 0.0025], 'movie': [0.0014, 0.0019], 'hate': [0.0029, 0.0002]}
out = {k: {x: d.get(x, [0.5,0.5]) for x in v} for k, v in reviews.items()}
print (out)
{1: {'like': [0.0005, 0.0025], 'the': [0.5, 0.5], 'acting': [0.5, 0.5]},
2: {'story': [0.5, 0.5], 'hate': [0.0029, 0.0002], 'plot': [0.5, 0.5]}}

Add nested dictionaries on matching keys

I have a nested dictionary, such as:
{'A1': {'T1': [1, 3.0, 3, 4.0], 'T2': [2, 2.0]}, 'A2': {'T1': [1, 0.0, 3, 5.0], 'T2': [2, 3.0]}}
What I want to do is sum each sub dictionary, to obtain this:
A1 A2 A1 A2
T1+T1 T2+T2 (ignore the first entry of the list)
[3.0, 5.0, 9.0] <<<< output
1 2 3
res 3.0 + 0.0 = 3.0 and 2.0 + 3.0 = 5.0 and 5.0 + 4.0 = 9.0
How can I do this? I've tried a for, but I've created a big mess
One way is to use collections.Counter in a list comprehension, and sum the resulting Counter objects:
from collections import Counter
d = {'A1': {'T1': 3.0, 'T2': 2.0}, 'A2': {'T1': 0.0, 'T2': 3.0}}
l = (Counter(i) for i in d.values())
sum(l, Counter())
# Counter({'T1': 3.0, 'T2': 5.0})
For sum to work here, I've defined an empty Counter() as the start argument, so sum expects other Counter objects.
To get only the values, you can do:
sum(l, Counter()).values()
# dict_values([3.0, 5.0])
you could use a list comprehension with zip:
d = {'A1': {'T1': 3.0, 'T2': 2.0}, 'A2': {'T1': 0.0, 'T2': 3.0}}
[sum(e) for e in zip(*(e.values() for e in d.values()))]
output:
[3.0, 5.0]
this will work if your python version is >= 3.6
also, you can use 2 for loops:
r = {}
for dv in d.values():
for k, v in dv.items():
r.setdefault(k, []).append(v)
result = [sum(v) for v in r.values()]
print(result)
output:
[3.0, 5.0]
after your edit
you could use:
from itertools import zip_longest
sum_t1, sum_t2 = list(list(map(sum, zip(*t))) for t in zip(*[e.values() for e in d.values()]))
[i for t in zip_longest(sum_t1[1:], sum_t2[1:]) for i in t if i is not None]
output:
[3.0, 5.0, 6, 9.0]

Replace dictionary keys from values of another dictionary

I have three dictionaries:
packed_items = {0: [0, 3],
2: [1],
1: [2]}
trucks_dict = {0: [9.5, 5.5, 5.5],
1: [13.0, 5.5, 7.0],
2: [16.0, 6.0, 7.0]}
items_dict = {0: [4.6, 4.3, 4.3],
1: [4.6, 4.3, 4.3],
2: [6.0, 5.6, 9.0],
3: [8.75, 5.6, 6.6]}
packed_items consists of trucks as keys and values as list of items. I want to change my packed_dict such that it gives me output in this format
packed_dict = {[9.5, 5.5, 5.5]:[[4.6, 4.3, 4.3],[8.75, 5.6, 6.6]]
[16.0, 6.0, 7.0]:[[4.6, 4.3, 4.3]]
[13.0, 5.5, 7.0]:[[6.0, 5.6, 9.0]]}
Basically I want to replace my keys in packed_items with the values in trucks_dict, and values in packed_items with values in items_dict.
By converting your list keys to tuples, you can do that with something like:
Code:
result = {}
for k, v in packed_items.items():
for i in v:
result.setdefault(tuple(trucks_dict[k]), []).append(items_dict[i])
Test Code:
packed_items = {0: [0, 3],
2: [1],
1: [2]}
trucks_dict = {0: [9.5, 5.5, 5.5],
1: [13.0, 5.5, 7.0],
2: [16.0, 6.0, 7.0]}
items_dict = {0: [4.6, 4.3, 4.3],
1: [4.6, 4.3, 4.3],
2: [6.0, 5.6, 9.0],
3: [8.75, 5.6, 6.6]}
result = {}
for k, v in packed_items.items():
for i in v:
result.setdefault(tuple(trucks_dict[k]), []).append(items_dict[i])
print(result)
Results:
{(9.5, 5.5, 5.5): [[4.6, 4.3, 4.3], [8.75, 5.6, 6.6]],
(16.0, 6.0, 7.0): [[4.6, 4.3, 4.3]],
(13.0, 5.5, 7.0): [[6.0, 5.6, 9.0]]
}
You cannot have lists as dictionary keys because they are unhashable.
Because you asked for string keys, you can do:
from collections import defaultdict
packed_items = {0: [0, 3],
2: [1],
1: [2]}
trucks_dict = {0: [9.5, 5.5, 5.5],
1: [13.0, 5.5, 7.0],
2: [16.0, 6.0, 7.0]}
items_dict = {0: [4.6, 4.3, 4.3],
1: [4.6, 4.3, 4.3],
2: [6.0, 5.6, 9.0],
3: [8.75, 5.6, 6.6]}
d = defaultdict(list)
for k1, v1 in trucks_dict.items():
for k2, v2 in items_dict.items():
if k1 == k2 % 3:
d[str(v1)].append(v2)
print(d)
# {'[9.5, 5.5, 5.5]': [[4.6, 4.3, 4.3], [8.75, 5.6, 6.6]], '[16.0, 6.0, 7.0]': [[4.6, 4.3, 4.3]], '[13.0, 5.5, 7.0]': [[6.0, 5.6, 9.0]]}
You can use a dict comprehension to map the lists in trucks_dict to items in items_dict. The lists have to be converted to tuples so that they can be hashable as keys:
{tuple(trucks_dict[k]): [items_dict[i] for i in l] for k, l in packed_items.items()}
This returns:
{(9.5, 5.5, 5.5): [[4.6, 4.3, 4.3], [8.75, 5.6, 6.6]],
(13.0, 5.5, 7.0): [[6.0, 5.6, 9.0]],
(16.0, 6.0, 7.0): [[4.6, 4.3, 4.3]]}

Converting dataframe into sub-list or dictionaries

I have the data in tabular format (rows and columns) which I read into a dataframe (Data1) :
Name D Score
0 Angelica D1 3.5
1 Angelica D2 2.0
2 Bill D1 2.0
3 Chan D3 1.0
......
I am able to convert it into a list using:
Data2 = Data1.values.tolist()
and get the below output:
[
['Angelica', 'D1', 3.5], ['Angelica', 'D2', 2.0],
['Bill', 'D1', 2.0], ['Bill', 'D2', 3.5],
['Chan', 'D8', 1.0], ['Chan', 'D3', 3.0], ['Chan', 'D4', 5.0],
['Dan', 'D4', 3.0], ['Dan', 'D5', 4.5], ['Dan', 'D6', 4.0]
]
What I want is, the output to be like this:
{
'Angelica': {'D1': 3.5, 'D2': 2.0} ,
'Bill': {'D1': 2.0, 'D2': 3.5}
'Chan': {'D8': 1.0, 'D3': 3.0, 'D4': 5.0 }
'Dan': {'D4': 3.0, 'D5': 4.5, 'D6': 4.0}
}
How can I achieve this in Python?
You can use a dictionary comprehension after grouping the df by the Name column:
>>> df = pd.DataFrame([{'Name': 'Angela', 'Score': 3.5, 'D': 'D1'}, {'Name': 'Angela', 'Score': 2.0, 'D': 'D2'}, {'Name': 'Bill', 'Score': 2.0, 'D': 'D1'}, {'Name': 'Chan', 'Score': 1.0, 'D': 'D3'}])
>>> df
D Name Score
0 D1 Angela 3.5
1 D2 Angela 2.0
2 D1 Bill 2.0
3 D3 Chan 1.0
>>> data2 = {name: {df.ix[v].D: df.ix[v].Score for v in val} for name, val in df.groupby('Name').groups.items()}
>>> data2
{'Chan': {'D3': 1.0}, 'Angela': {'D1': 3.5, 'D2': 2.0}, 'Bill': {'D1': 2.0}}
You can zip up the values from each group after grouping by Name:
In [4]: l = [
...: ['Angelica', 'D1', 3.5], ['Angelica', 'D2', 2.0],
...: ['Bill', 'D1', 2.0], ['Bill', 'D2', 3.5],
...: ['Chan', 'D8', 1.0], ['Chan', 'D3', 3.0], ['Chan', 'D4', 5.0],
...: ['Dan', 'D4', 3.0], ['Dan', 'D5', 4.5], ['Dan', 'D6', 4.0]
...: ]
...: columns=["Name", "D", "Score"]
...: df = pd.DataFrame(l, columns=columns)
...:
In [5]: {name: dict(zip(v["D"], v["Score"])) for name, v in df.groupby("Name")}
In [6]: data
Out[6]:
{'Angelica': {'D1': 3.5, 'D2': 2.0},
'Bill': {'D1': 2.0, 'D2': 3.5},
'Chan': {'D3': 3.0, 'D4': 5.0, 'D8': 1.0},
'Dan': {'D4': 3.0, 'D5': 4.5, 'D6': 4.0}}
from collections import defaultdict
result = defaultdict(dict)
for item in Data2:
result[item[0]].update(dict([item[1:]]))

Unique value in list of lists in Python

I have following list of lists in python :
[
u'aaaaa',
[1, 6, u'testing', 20.0, 18.0, 2.0, 'In time'],
u'zzzzzz',
[1, 6, u'testing', 20.0, 18.0, 2.0, 'In time'],
[1, 1, u'xyz ', 30.0, 25.0, 5.0, 'On Going'],
[2, 1, u'abcd', 10.0, 8.0, 2.0, 'In time'],
u'bbbbb',
[1, 6, u'testing', 20.0, 18.0, 2.0, 'In time'],
[1, 1, u'xyz ', 30.0, 25.0, 5.0, 'On Going'],
[2, 1, u'abcd', 10.0, 8.0, 2.0, 'In time'],
[1, 7, u'develop', 20.0, 15.0, 5.0, 'On Going']
]
I want following output in python :
[
[u'aaaaa', [1, 6, u'testing', 20.0, 18.0, 2.0, 'In time']],
[u'zzzzzz', [1, 1, u'xyz ', 30.0, 25.0, 5.0, 'On Going'], [2, 1, u'abcd', 10.0, 8.0, 2.0, 'In time']],
[u'bbbbb', [1, 7, u'develop', 20.0, 15.0, 5.0, 'On Going']]
]
Please suggest me how can it possible with manage order in python.
The following should give you the desired output. It uses a dictionary to spot duplicate entries.
entries = [
u'aaaaa', [1, 6, u'testing', 20.0, 18.0, 2.0, 'In time'],
u'zzzzzz', [1, 6, u'testing', 20.0, 18.0, 2.0, 'In time'],
[1, 1, u'xyz ', 30.0, 25.0, 5.0, 'On Going'],
[2, 1, u'abcd', 10.0, 8.0, 2.0, 'In time'],
u'bbbbb',
[1, 6, u'testing', 20.0, 18.0, 2.0, 'In time'],
[1, 1, u'xyz ', 30.0, 25.0, 5.0, 'On Going'],
[2, 1, u'abcd', 10.0, 8.0, 2.0, 'In time'],
[1, 7, u'develop', 20.0, 15.0, 5.0, 'On Going']]
d = {}
output = []
entry = []
for item in entries:
if type(item) == type([]):
t = tuple(item)
if t not in d:
d[t] = 0
entry.append(item)
else:
if len(entry):
output.append(entry)
entry = [item]
output.append(entry)
print output
This gives the following output:
[[u'aaaaa', [1, 6, u'testing', 20.0, 18.0, 2.0, 'In time']], [u'zzzzzz', [1, 1, u'xyz ', 30.0, 25.0, 5.0, 'On Going'], [2, 1, u'abcd', 10.0, 8.0, 2.0, 'In time']], [u'bbbbb', [1, 7, u'develop', 20.0, 15.0, 5.0, 'On Going']]]
Tested using Python 2.7
Update: If a list of lists format is needed, simply add [] to item in the above script as follows::
entry.append([item])
This would give the following output:
[[u'aaaaa', [[1, 6, u'testing', 20.0, 18.0, 2.0, 'In time']]], [u'zzzzzz', [[1, 1, u'xyz ', 30.0, 25.0, 5.0, 'On Going']], [[2, 1, u'abcd', 10.0, 8.0, 2.0, 'In time']]], [u'bbbbb', [[1, 7, u'develop', 20.0, 15.0, 5.0, 'On Going']]]]
If you want all unique values from a list:
mylist = [u'nowplaying', u'PBS', u'PBS', u'nowplaying', u'job', u'debate', u'thenandnow']
mylist = [list(x) for x in set(tuple(x) for x in testdata)]
print myset # This is now a set containing all unique values.
# This will not maintain the order of the items
1) I really think you should check out Python dictionaries. They would make much more sense, looking at the kind of output you want.
2) In this case, if I understand you correctly, you want to convert a list with elements that are either strings or lists into a list of lists. This list of lists should have a starting element as a string, and the remaining elements as the following list items within the main list, till you hit the next string. (At least that's what it looks like from your example).
output_list = []
for elem in main_list:
if isinstance(elem,basestring):
output_list.append([elem])
else:
output_list[-1].append(elem)

Categories