Iterating over A dict to access a specific key value - python

I have a list of dicts ('sortings') that I am trying to iterate through to access a values in one specific key of each dict. My code keeps saying that there is a key error for the desired value in the dict. If I print inside the for loop, it prints with the values entered but once I exit the for loop it says there is a key error.
for i in range(sort_len):
sentence = sortings[i]['content']
containing_messages.append(sentence)
print(containing_messages)

This is an answer for my understanding of the question. I would require the given input and expected output to provide a better answer.
list_of_dicts = [{'keya':'value1_1','keyb':'value2_1','keyc':'value3_1'},
{'keya':'value1_2','keyb':'value2_2','keyc':'value3_2'},
{'keya':'value1_3','keyb':'value2_3','keyc':'value3_3'}]
list_of_key_values = [my_dict['keyb'] for my_dict in list_of_dicts]
print list_of_key_values

Related

How can I search for a specific key in a dictionary in Python?

So I got this dictionary from a csv file and I would like to look for a specific key inside this dictionary (actually the og idea was to search for said key in the csv file and then make a dictionary from that key down) but I don't really know how to do it.
So far I got:
df = pd.read_csv('data.csv')
dict = df.to_dict(orient='dict')
for index, line in enumerate(dict):
if "Wavelength [nm]" in line:
print(index)
The idea is to know the index of "Wavelength".
If you want the value of a key without knowing whether it's in the dict, often the most natural way is
value = dict.get( key, defaultvalue)
defaultvalue is what you would set value to in your code once you had established that the key is not present. Often, None, or an empty list or tuple.
If you just waht to check whether the key is present without accessing the value, use
if key in dict:
# do stuff
you can use:
if key in dict:
print(key,dict[key])

How can I get the key value pair to create a dictionary from a nested dictionary?

I have a dictionary which looks as shown below. Now I need to get the key its corresponding path together so as to use it further to identify its slot number based on the key. How can I achieve that?
I tried an approach but it is giving me key error.
What you need can easily be implemented as:
>>> {key: value["mpath"] for key, value in multipath.items()}
{'/dev/sdh': '/dev/mapper/mpathk', '/dev/sdi': '/dev/mapper/mpathk',
'/dev/sdg': '/dev/mapper/mpathj', '/dev/sdf': '/dev/mapper/mpathj',
'/dev/sdd': '/dev/mapper/mpathi', '/dev/sde': '/dev/mapper/mpathi',
'/dev/sdb': '/dev/mapper/mpathh', '/dev/sdc': '/dev/mapper/mpathh',
'/dev/sdj': '/dev/mapper/mpathg', '/dev/sdk': '/dev/mapper/mpathg'}
Great one line answer by #Selcuk using dictionary comprehension.
An elaborated one along the same line would be:
mpath_dict = {}
for sd, mpath in multipath.items():
mpath_dict[sd] = mpath['mpath']
print(mpath_dict)
Since every value item of "mpath" dictionary is a dictionary itself, you can retrieve values from it as you would do it in a dictionary.

Why does the default dictionary in my code keep expanding?

I have a default dictionary and I run it through a couple of loops to look for certain strings in the dictionary. The loops don't really append anything to the dictionary yet as it turns out, during the loop, new items keep getting appended to the dictionary and the final dictionary ends up bigger than the original one before the loop.
I've been trying to pinpoint the error forever but now it's late and I have no idea what's causing this!
from collections import defaultdict
dummydict = defaultdict(list)
dummydict['Alex'].append('Naomi and I love hotcakes')
dummydict['Benjamin'].append('Hayley and I hate hotcakes')
part = ['Alex', 'Benjamin', 'Hayley', 'Naomi']
emp = []
for var in dummydict:
if 'I' in dummydict[var]:
emp.append(var)
for car in part:
for key in range(len(dummydict)):
print('new len', len(dummydict))
print(key, dummydict)
if car in dummydict[key]:
emp.append(car)
print(emp)
print('why are there new values in the dictionary?!', len(dummydict), dummydict)
I expect the dictionary to remain unchanged.
if car in dummydict[key]:
key being an integer, and your dict being initially filled with only string as keys, this will create a new value in dummydict for each key.
Accessing missing keys as in dummydict[key] will add those keys to the defaultdict. Note that key is an int, not the value at that position, as for key in range(len(dummydict)) iterates indexes, not the dict or its keys.
See the docs:
When each key is encountered for the first time, it is not already in the mapping; so an entry is automatically created using the default_factory function which returns an empty list.
For example, this code will show a dummydict with a value in it, because simply accessing dummydict[key] will add the key to the dict if that key is not already there.
from collections import defaultdict
dummydict = defaultdict(list)
dummydict[1]
print (dummydict)
outputs:
defaultdict(<class 'list'>, {1: []})
Your issue is that in your loop, you do things like dummydict[key] and dummydict[var], which adds those keys.

Python Max function - Finding highest value in a dictionary

My question is about finding highest value in a dictionary using max function.
I have a created dictionary that looks like this:
cc_GDP = {'af': 1243738953, 'as': 343435646, etc}
I would like to be able to simply find and print the highest GDP value for each country.
My best attempt having read through similar questions is as follows (I'm currently working through the Python crash course book at which the base of this code has been taken, note the get_country_code function is simply providing 2 letter abbreviations for the countries in the GDP_data json file):
#Load the data into a list
filename = 'gdp_data.json'
with open(filename) as f:
gdp_data = json.load(f)
cc_GDP` = {}
for gdp_dict in gdp_data:
if gdp_dict['Year'] == 2016:
country_name = gdp_dict['Country Name']
GDP_total = int(gdp_dict['Value'])
code = get_country_code(country_name)
if code:
cc_GDP[code] = int(GDP_total)
print(max(cc_GDP, key=lambda key: cc_GDP[key][1]))
This provides the following error 'TypeError: 'int' object is not subscriptable'
Note if leaving out the [1] in the print function, this does provide the highest key which relates to the highest value, but does not return the highest value itself which is what I wish to achieve.
Any help would be appreciated.
So you currently extract the key of the country that has the highest value with this line:
country_w_highest_val = max(cc_GDP, key=lambda key: cc_GDP[key]))
You can of course just look that up in the dictionary again:
highest_val = cc_GDP[contry_w_highest_val]
But simpler, disregard the keys completely, and just find the highest value of all values in the dictionary:
highest_val = max(cc_GDP.values())
How about something like this:
print max(cc_GDP.values())
That will give you the highest value but not the key.
The error is being cause because you need to look at the entire dictionary, not just one item. remove the [1] and then use the following line:
print(cc_GDP[max(cc_GDP, key=lambda key: cc_GDP[key])])
Your code currently just returns the dictionary key. You need to plug this key back into the dictionary to get the GDP.
You could deploy .items() method of dict to get key-value pairs (tuples) and process it following way:
cc_GDP = {'af': 1243738953, 'as': 343435646}
m = max(list(cc_GDP.items()), key=lambda x:x[1])
print(m) #prints ('af', 1243738953)
Output m in this case is 2-tuple, you might access key 'af' via m[0] and value 1243738953 via m[1].

Modify multiple keys of dictionary by a mapping dictionary

I have 2 dict, one original and one for mapping the original one's key to another value simultaneously,for instance:
original dict:
built_dict={'China':{'deportivo-cuenca-u20':{'danny':'test1'}},
'Germany':{'ajax-amsterdam-youth':{'lance':'test2'}}}
mapping dict:
club_team_dict={'deportivo-cuenca-u20':'deportivo','ajax-amsterdam-youth':'ajax'}
It works well if I use the following code to change the key of the nested dict of original dict,like
def club2team(built_dict,club_team_dict):
for row in built_dict:
# print test_dict[row]
for sub_row in built_dict[row]:
for key in club_team_dict:
# the key of club_team_dict must be a subset of test_dict,or you have to check it and then replace it
if sub_row==key:
built_dict[row][club_team_dict[sub_row]] = built_dict[row].pop(sub_row)
return built_dict
and the result:
{'Germany': {'ajax': {'lance': 'test2'}}, 'China': {'deportivo': {'danny': 'test1'}}}
so far so good, however if I have a dict with multiple key mapping to the same key,for example,my original dict is like
built_dict={'China':{'deportivo-cuenca-u20':{'danny':'test1'}},
'Germany':{'ajax-amsterdam-youth':{'lance':'test2'},
'ajax-amsterdam':{'tony':'test3'}}}
and the mapping dict with more then 1 key mapping to the same value,like:
club_team_dict={'deportivo-cuenca-u20':'deportivo',
'ajax-amsterdam-youth':'ajax',
'ajax-amsterdam':'ajax'}
as you can see, both 'ajax-amsterdam-youth'and 'ajax-amsterdam-youth' are mapping to 'ajax',and the trouble is when I use the same code to execute it, the original dict's size has been changed during the iteration
RuntimeError: dictionary changed size during iteration
I want to get a result with nested list for the same key like this
{'Germany': {'ajax':[{'lance': 'test2'},
{'tony' : 'test3'}]}},
'China': {'deportivo': [{'danny': 'test1'}]}}
Well I have found a solution for this,the code:
def club2team(built_dict,club_team_dict):
for row in built_dict:
# print test_dict[row]
for sub_row in built_dict[row].keys():
for key in club_team_dict:
# the key of club_team_dict must be a subset of test_dict,or you have to check it and then replace it
if sub_row==key:
# built_dict[row][club_team_dict[sub_row]] = built_dict[row].pop(sub_row)
built_dict[row].setdefault(club_team_dict[sub_row],[]).append(built_dict[row].pop(sub_row))
return built_dict
pay attention to the for sub_row in built_dict[row].keys(): and setdefault() method, I used to believe that in python 2.7, the default iteration for dict is just iterate the keys(), however, this time it proves it's a little different, maybe you have better solution, please show me and it will be appreciate,thank you

Categories