d={'a':1, 'b':2, ...}
if 'a' in d and 'b' in d and ...:
pass
is there a simple way to determine multiple keys at once?
something like:
if ['a', 'b'] in d:
You can do
if all(key in d for key in ['a', 'b', 'c', ...]):
This may be longer than writing them out separately if you're only testing a couple, but as the list of keys to be tested grows longer, this way will be quicker, since you only have to add the key to the list and not write an additional in d and.
d={'a':1, 'b':2, ...}
required_keys = set(('a', 'b', ...))
missing_keys = required_keys.difference(d.keys())
if missing_keys
print "You are missing some keys: ", missing_keys
else:
print "You have all of the required keys"
len(d.keys()) will let you know how many keys are in your dictionary
Related
This question already has answers here:
is it possible to reverse a dictionary in python using dictionary comprehension
(5 answers)
Closed 2 years ago.
While I've been improving my Python skills I have one question.
My code is below:
# def invertDictionary(dict):
# new_dict = {}
# for key, value in dict.items():
# if value in new_dict:
# new_dict[value].append(key)
# else:
# new_dict[value]=[key]
# return new_dict
def invertDictionary(dict):
new_dict = {value:([key] if value else [key]) for key, value in dict.items()}
return new_dict;
invertDictionary({'a':3, 'b':3, 'c':3})
I am trying to get output like {3:['a','b','c']}. I have achieved that using a normal for-loop; I just want to know how to get these results using a Dictionary Comprehension. I tried but in append it's getting an error. Please let me know how to achieve this.
Thanks in Advance!
You missed that you also need a list comprehension to build the list.
Iterate over the values in the dict, and build the needed list of keys for each one.
Note that this is a quadratic process, whereas the canonical (and more readable) for loop is linear.
d = {'a':3, 'b':3, 'c':3, 'e':4, 'f':4, 'g':0}
inv_dict = {v: [key for key, val in d.items() if val == v]
for v in set(d.values())}
result:
{0: ['g'],
3: ['a', 'b', 'c'],
4: ['e', 'f']
}
Will this do?
while your original version with a regular for loop is the best solution for this, here is a variation on #Prune answer that doesn't goes over the dict multiple times
>>> import itertools
>>> d = {'a':3, 'b':3, 'c':3, 'e':4, 'f':4, 'g':0}
>>> {group_key:[k for k,_ in dict_items]
for group_key,dict_items in itertools.groupby(
sorted(d.items(),key=lambda x:x[-1]),
key=lambda x:x[-1]
)
}
{0: ['g'], 3: ['a', 'b', 'c'], 4: ['e', 'f']}
>>>
first we sorted the items of the dict by value with a key function to sorted using a lambda function to extract the value part of the item tuple, then we use the groupby to group those with the same value together with the same key function and finally with a list comprehension extract just the key
--
as noted by Kelly, we can use the get method from the dict to get the value to make it shorter and use the fact that iteration over a dict give you its keys
>>> {k: list(g) for k, g in itertools.groupby(sorted(d, key=d.get), d.get)}
{0: ['g'], 3: ['a', 'b', 'c'], 4: ['e', 'f']}
>>>
You could use a defalutdict and the append method.
from collections import defaultdict
dict1 = {'a': 3, 'b': 3, 'c': 3}
dict2 = defaultdict(list)
{dict2[v].append(k) for k, v in dict1.items()}
dict2
>>> defaultdict(list, {3: ['a', 'b', 'c']})
I know this is a frequently asked question, however I do not have access to the Counter module as I'm using v2.6 of Python. I want to count the number of time a specific key appears in a list of dictionaries.
If my dictionary looks like this:
data = [{'a':1, 'b':1}, {'a':1, 'c':1}, {'b':1, 'c':1}, {'a':1, 'c':1}, {'a':1, 'd':1}]
How would I find out how many times "a" appears? I've tried using len, but that only returns the number of values for one key.
len(data['a'])
You can use list comprehension.
data = [{'a':1, 'b':1}, {'a':1, 'c':1}, {'b':1, 'c':1}, {'a':1, 'c':1}, {'a':1, 'd':1}]
sum([1 for d in data if 'a' in d])
Explanation:
First take the dictionary object from list data, check if key 'a' is present in the dictionary or not, if present, add 1 to the list. Then sum the new list.
You won't have access to collections.Counter, but collections.defaultdict was added in Python 2.5
keys and flatten list
data = [j for i in data for j in i.keys()]
# ['a', 'b', 'a', 'c', 'c', 'b', 'a', 'c', 'a', 'd']
collections.defaultdict
from collections import defaultdict
dct = defaultdict(int)
for key in data:
dct[key] += 1
# defaultdict(<type 'int'>, {'a': 4, 'c': 3, 'b': 2, 'd': 1})
If you only need the count for a, there are simpler ways to do this, but this will give you the counts of all keys in your list of dictionaries.
A one-line solution could be:
len([k for d in data for k in d.keys() if k == 'a'])
For this you could write the following function that would work for data in the structure you provided (a list of dicts):
def count_key(key,dict_list):
keys_list = []
for item in dict_list:
keys_list += item.keys()
return keys_list.count(key)
Then, you could invoke the function as follows:
data = [{'a':1, 'b':1}, {'a':1, 'c':1}, {'b':1, 'c':1}, {'a':1, 'c':1}, {'a':1, 'd':1}]
count_a = count_key('a',data)
In this case, count_a will be 4.
This question looks very much like a class assignment. Here is a simple bit of code that will do the job:
n=0
for d in data:
if 'a' in d:
n+=1
print(n)
Here n is a counter, the for loop iterates through the list of dictionaries.
The 'a' in d expression will return true if the key 'a' is in the dictionary d, in which case the counter n will be incremented. At the end the result is printed. I believe in Python 2.6 the brackets would be optional (I am using 3.6).
All the questions I've seen do the exact opposite of what I want to do:
Say I have a list:
lst = ['a','b','c']
I am looking to make a dictionary where the key is the element number (starting with 1 instead of 0) and the list element is the value. Like this:
{1:'a', 2:'b', 3:'c'}
But for a long list. I've read a little about enumerate() but everything I've seen has used the list element as the key instead.
I found this:
dict = {tuple(key): idx for idx, key in enumerate(lst)}
But that produces:
{'a':1, 'b':2, 'c':3}
... which is the opposite of what I want. And, also in a weird notation that is confusing to someone new to Python.
Advice is much appreciated! Thanks!
enumerate has a start keyword argument so you can count from whatever number you want. Then just pass that to dict
dict(enumerate(lst, start=1))
You could also write a dictionary comprehension
{index: x for index, x in enumerate(lst, start=1)}
By default enumerate start from 0 , but you can set by this value by second argument which is start , You can add +1 to every iterator if you want to start from 1 instead of zero :
print({index+1:value for index,value in enumerate(lst)})
output:
{1: 'a', 2: 'b', 3: 'c'}
Above dict comprehension is same as :
dict_1={}
for index,value in enumerate(lst):
dict_1[index+1]=value
print(dict_1)
Using Dict Comprehension and enumerate
print({x:y for x,y in enumerate(lst,1)})
{1: 'a', 2: 'b', 3: 'c'}
Using Dict Comprehension , zip and range-
print({x:y for x,y in zip(range(1,len(lst)+1),lst)})
{1: 'a', 2: 'b', 3: 'c'}
I think the below code should help.
my_list = ['A', 'B', 'C', 'D']
my_index = []
my_dict = {}
for i in range(len(my_list)):
my_index.append(i+1)
for key in my_index:
for value in my_list:
my_dict[key] = value
I want to merge two dictionaries like this:
old={'a':'1a','b':'1b','c':'1c'}
new={'1a':'c','1b':'d','1c':'e'}
I want output like this:
new_dict={'a':'c','b':'d','c':'e'}
Note: The length of both dictionaries is different.
How to do it in python?
With a dict-comprehension:
old = {'a': '1a','b': '1b','c': '1c'}
new = {'1a': 'c','1b': 'd','1c': 'e'}
res = {k: new[v] for k, v in old.items()} # if all values in `old` exist in `new` as keys.
res = {k: new.get(v, None) for k, v in old.items()} # if you cannot guarantee the above.
print(res) # {'b': 'd', 'a': 'c', 'c': 'e'}
*Note that the None parameter of the .get() method is the default one and as such, it can be omitted. I will leave it there though to remind you that you can specify anything you want depending on the specifics of your problem (e.g., '' (blank string) might be better in your case)
You can get the new dictionary using a dictionary comprehension where you get the values from the new dictionary based on the keys in the old dictionary. Be sure to use get which returns None by default if a value from the old dictionary is not present as a key in the new dictionary.
old = {'a': '1a', 'b': '1b' ,'c': '1c'}
new = {'1a': 'c', '1b': 'd', '1c': 'e'}
new_dict = {k: new.get(old[k]) for k in old}
>>> new_dict
{'a': 'c', 'b': 'd', 'c': 'e'}
You could use a dictionary comprehension that interprets the value of the first dictionary as the key of the second dictionary:
>>> {item: new[value] for item, value in old.items() if value in new}
{'a': 'c', 'b': 'd', 'c': 'e'}
In case you can garantuee that all values of old are in new you could omit the if value in new part.
I have a dictionary where the values are lists. I would like to look for a specific value in the lists (value field of dictionary) and return the key value:
dict={'a':['ab','cd','ef'], 'b':['gh', 'ij'], 'c':['kl', 'mn']}
So for 'ef' I would get 'a', for 'mn' I would get 'c'...
I have tryied
value_key=[a for a,b in dict if value in b]
Any ideas?
Assuming you want to do indexing this way more than once, you should build the reverse mapping, from values (sub-values really) to keys:
{ vsub:k for k, v in d.iteritems() for vsub in v }
This takes your original dict (called d here because dict is a builtin name in Python), and "inverts" it, with the tweak of mapping each sub-value (the elements within the lists).
Once you have this new dict, you can simply index into it by keys like 'ab' to get 'a':
{'ab': 'a', 'ef': 'a', 'mn': 'c', 'kl': 'c', 'ij': 'b', 'cd': 'a', 'gh': 'b'}
Iterate through the dictionary with for key in dict_object, and then use in operator to check if the value being searched is in the dictionary's value corresponding to the key. If it exists, then retain the key for the output.
my_dict,val={"a": ["ab", "cd", "ef"], "b": ["gh", "ij"], "c": ["kl", "mn"]}, "ef"
print [key for key in my_dict if val in my_dict[key]]
# ['a']
The advantage of this method is, it will work irrespective of the current popular Python versions, as we don't have to worry about items and iteritems methods.