This is my list:
volume = [['1.986', '3000'], ['1.987', '2000'], ['1.986', '700'],['1.987', '4000']]
How can I get the sum of volume[1] when volume[0] is the same price?
results = [['1.986', '3700'], ['1.987', '6000']]
Dictionaries would be a good data structure to use here. The default dict holds unique strings as the keys and assumes empty values are 0 because I set it to be based off of int.
from collections import defaultdict
d = defaultdict(int)
for v in volume:
d[v[0]] += int(v[1])
print d
If you need a list afterwards you can use a list comprehension:
list_version = [[key, value] for key,value in d]
Related
In Python, how can we assign multiple dictionary keys the same value.
I tried something below but it's not working.
server = {'server1','server2': 'abc#xyz.com', 'server3','server4':'pqr#xyz.com'}
For example:
s = "the_value" # the value you want for the keys below
l = ["name", "age", "address"] # keys
d = {} # initiating an empty dictionary
for item in l:
d[item] = s
This should print
{'name': 'the_value', 'age': 'the_value', 'address': 'the_value'}
If you order your inputs as list of tuples, where each tuple is the value and a list of servers, you can use a nested list comprehension to create your dictionary:
from pprint import pprint
# arange your inputdata as tuples of ("value" to be set, list of servers)
# data = [ (f"login_{v}",[f"server_{v}{10+w}" for w in range(3)]) for v in range(5)]
data = [ ('login_0', ['server_010', 'server_011', 'server_012']),
('login_1', ['server_110', 'server_111', 'server_112']),
('login_2', ['server_210', 'server_211', 'server_212']),
('login_3', ['server_310', 'server_311', 'server_312']),
('login_4', ['server_410', 'server_411', 'server_412']) ]
# create the dict using a nested list comprehension
d = {k:v for v,keys in data for k in keys}
pprint(d)
Output:
# of the created dict using a nested list comprehension
{'server_010': 'login_0',
'server_011': 'login_0',
'server_012': 'login_0',
'server_110': 'login_1',
'server_111': 'login_1',
'server_112': 'login_1',
'server_210': 'login_2',
'server_211': 'login_2',
'server_212': 'login_2',
'server_310': 'login_3',
'server_311': 'login_3',
'server_312': 'login_3',
'server_410': 'login_4',
'server_411': 'login_4',
'server_412': 'login_4'}
See Explanation of how nested list comprehension works? if you do not know about those.
You could use tuples as keys but then it is difficult to find the dictionary entry corresponding to a single value
server = {('server1','server2','serverX'): 'abc#xyz.com', \
('server3','server4'):'pqr#xyz.com'}
Note: you can do that because tuples are hashable.
This makes only sense if you want to query the dictionary by exactly such tuples, for instance:
server[('server3', 'server4')]
# Out: 'pqr#xyz.com'
I have a list of pairs.The list contains items of [x,y].I would like to make list or dictionary making the left item the key and right the value.The list maybe contains multiple times the same key. I want to sum the values and keep one time the key.
E.x
pairs[0]=['3106124650', 2.86]
pairs[1]=['3106124650', 8.86]
pairs[2]=['5216154610', 23.77]
I want to keep '3106124650' one time and sum the values.So my new list or dictionary will contain one time this key with value 11.72.
'3106124650',11.72
Here's a way. For large datasets, numpy will probably be faster though.
import collections
result = collections.defaultdict(lambda : 0)
for k,v in pairs:
result[k]+=v
sumdict = dict()
for i, v in pairs:
sumdict[i] = v + sumdict.get(i, 0)
li=[['a',1],['a',2],['b',3],['c',4]]
d={}
for w in li:
d[w[0]]=w[1]+d.get(w[0],0)
Output:{'a': 3, 'b': 3, 'c': 4}
you can try this:
d={}
for entry in pairs:
if entry[0] in d:
d[entry[0]]+=entry[1]
else:
d[entry[0]]=entry[1]
I have one list which contain a few dictionaries.
[{u'TEXT242.txt': u'work'},{u'TEXT242.txt': u'go to work'},{u'TEXT1007.txt': u'report'},{u'TEXT797.txt': u'study'}]
how to combine the dictionary when it has the same key. for example:
u'work', u'go to work'are under one key:'TEXT242.txt', so that i can remove the duplicated key.
[{u'TEXT242.txt': [u'work', u'go to work']},{u'TEXT1007.txt': u'report'},{u'TEXT797.txt': u'study'}]
The setdefault method of dictionaries is handy here... it can create an empty list when a dictionary key doesn't exist, so that you can always append the value.
dictlist = [{u'TEXT242.txt': u'work'},{u'TEXT242.txt': u'go to work'},{u'TEXT1007.txt': u'report'},{u'TEXT797.txt': u'study'}]
newdict = {}
for d in dictlist:
for k in d:
newdict.setdefault(k, []).append(d[k])
from collections import defaultdict
before = [{u'TEXT242.txt': u'work'},{u'TEXT242.txt': u'go to work'},{u'TEXT1007.txt': u'report'},{u'TEXT797.txt': u'study'}]
after = defaultdict(list)
for i in before:
for k, v in i.items():
after[k].append(v)
out:
defaultdict(list,
{'TEXT1007.txt': ['report'],
'TEXT242.txt': ['work', 'go to work'],
'TEXT797.txt': ['study']})
This technique is simpler and faster
than an equivalent technique using dict.setdefault()
I have two dictionaries:
a = {u'Anthracite': [u'3/optimized/8593793_fpx.tif'],
u'Black': [u'6/optimized/8593796_fpx.tif'],
u'Cobalt': [u'9/optimized/8593799_fpx.tif'],
u'Fire': [u'2/optimized/8593802_fpx.tif'],
u'Fuschia': [u'5/optimized/8593805_fpx.tif'],
u'Iris': [u'8/optimized/8593808_fpx.tif'],
u'Midnight': [u'1/optimized/8593811_fpx.tif']}
b = {u'Anthracite': [u'5/optimized/8593795_fpx.tif'],
u'Black': [u'8/optimized/8593798_fpx.tif'],
u'Cobalt': [u'1/optimized/8593801_fpx.tif'],
u'Fire': [u'4/optimized/8593804_fpx.tif'],
u'Fuschia': [u'7/optimized/8593807_fpx.tif'],
u'Iris': [u'0/optimized/8593810_fpx.tif'],
u'Midnight': [u'3/optimized/8593813_fpx.tif']}
I need to produce such dict:
c = {u'Anthracite': [u'3/optimized/8593793_fpx.tif', u'5/optimized/8593795_fpx.tif'],
u'Black': [u'6/optimized/8593796_fpx.tif', u'8/optimized/8593798_fpx.tif'],
....
}
So I need to collect all items from lists with same keys, but I need to save first order.
Dictionaries always have same keys
I have try to do this with zip but I`m getting total mess
Why not just iterating over the dictionaries and copy them to a new dictionary? A defaultdict is used in the following code for simplicity :
from collections import defaultdict
c = defaultdict(list)
a = {"foo": ["bar"]}
b = {"foo": ["baz"], "bah": ["foo"]}
for k, v in a.items() + b.items():
c[k].extend(v)
If the keys are the same, you can copy the first dictionary and update its content :
d = a.copy()
for k, v in b.iteritems():
d[k].extend(v)
Note that the latter creates a shallow copy and therefore the dictionary a is also modified during the process.
If you want alphabetical order, use an OrderedDict and sort the keys:
from collections import OrderedDict
srt_keys = sorted(a.keys())
d = OrderedDict()
for k in srt_keys:
d[k] = a[k]
d[k] += b[k]
print d
OrderedDict([(u'Anthracite', [u'3/optimized/8593793_fpx.tif', u'5/optimized/8593795_fpx.tif']), (u'Black', [u'6/optimized/8593796_fpx.tif', u'8/optimized/8593798_fpx.tif']), (u'Cobalt', [u'9/optimized/8593799_fpx.tif', u'1/optimized/8593801_fpx.tif']), (u'Fire', [u'2/optimized/8593802_fpx.tif', u'4/optimized/8593804_fpx.tif']), (u'Fuschia', [u'5/optimized/8593805_fpx.tif', u'7/optimized/8593807_fpx.tif']), (u'Iris', [u'8/optimized/8593808_fpx.tif', u'0/optimized/8593810_fpx.tif']), (u'Midnight', [u'1/optimized/8593811_fpx.tif', u'3/optimized/8593813_fpx.tif'])])
How about using OrderedDict with a tuple list to set initial order. and then simply maintaining it.
Check my answer here for nicer dict syntax: Override the {...} notation so i get an OrderedDict() instead of a dict()?
from collections import OrderedDict
#Use an ordered dict, with a tuple list init to maintain initial order
a = OrderedDict([
(u'Anthracite', [u'3/optimized/8593793_fpx.tif']),
(u'Black', [u'6/optimized/8593796_fpx.tif']),
(u'Cobalt', [u'9/optimized/8593799_fpx.tif']),
(u'Fire', [u'2/optimized/8593802_fpx.tif']),
(u'Fuschia', [u'5/optimized/8593805_fpx.tif']),
(u'Iris', [u'8/optimized/8593808_fpx.tif']),
(u'Midnight', [u'1/optimized/8593811_fpx.tif'])
])
#We don't care about b's order
b = {u'Anthracite': [u'5/optimized/8593795_fpx.tif'],
u'Black': [u'8/optimized/8593798_fpx.tif'],
u'Cobalt': [u'1/optimized/8593801_fpx.tif'],
u'Fire': [u'4/optimized/8593804_fpx.tif'],
u'Fuschia': [u'7/optimized/8593807_fpx.tif'],
u'Iris': [u'0/optimized/8593810_fpx.tif'],
u'Midnight': [u'3/optimized/8593813_fpx.tif']}
merge = OrderedDict()
#Since b has the same keys as a(we don't need to care for diffrent keys), but we want a's order
for key in a:
#We insert by order to an OrderedDict so the same order will be maintained
merge[key] = a[key] + b[key]
Say I have a list of list like this: (suppose you have no idea how many lists in this list)
list=[['food','fish'],['food','meat'],['food','veg'],['sports','football']..]
how can I merge the items in the list like the following:
list=[['food','fish','meat','veg'],['sports','football','basketball']....]
i.e, merge all the nested lists into the same list if they contain one of the same items.
Use defaultdict to make a dictionary that maps a type to values and then get the items:
>>> from collections import defaultdict
>>> d = defaultdict(list)
>>> items = [['food','fish'],['food','meat'],['food','veg'],['sports','football']]
>>> for key, value in items:
... d[key].append(value)
...
>>> [[key] + values for key, values in d.items()]
[['food', 'fish', 'meat', 'veg'], ['sports', 'football']]
The "compulsory" alternative to defaultdict which can work better for data that's already in order of the key and if you don't want to build data structures on it (ie, just work on groups)...
data = [['food','fish'],['food','meat'],['food','veg'],['sports','football']]
from itertools import groupby
print [[k] + [i[1] for i in v] for k, v in groupby(data, lambda L: L[0])]
But defaultdict is more flexible and easier to understand - so go with #Blender's answer.