Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to avoid "RuntimeError: dictionary changed size during iteration" error?

I have checked all of the other questions with the same error yet found no helpful solution =/

I have a dictionary of lists:

d = {'a': [1], 'b': [1, 2], 'c': [], 'd':[]} 

in which some of the values are empty. At the end of creating these lists, I want to remove these empty lists before returning my dictionary. Current I am attempting to do this as follows:

for i in d:     if not d[i]:         d.pop(i) 

however, this is giving me the runtime error. I am aware that you cannot add/remove elements in a dictionary while iterating through it...what would be a way around this then?

like image 850
user1530318 Avatar asked Aug 13 '12 20:08

user1530318


People also ask

How do I fix the RuntimeError dictionary change size during iteration?

The Python "RuntimeError: dictionary changed size during iteration" occurs when we change the size of a dictionary when iterating over it. To solve the error, use the copy() method to create a shallow copy of the dictionary that you can iterate over, e.g. my_dict. copy() .

Is there a limit to dictionary size in Python?

It will not display the output because the computer ran out of memory before reaching 2^27. So there is no size limitation in the dictionary.

Can you iterate over dictionary keys?

Iterate keys in dictionary ( dict ): keys() As mentioned above, you can iterate keys by using the dictionary object directly, but you can also use keys() . The result is the same, but keys() may clarify the intent to the reader of the code. The keys() method returns dict_keys .

How do you check if a key is in a dictionary?

How do you check if a key exists or not in a dictionary? You can check if a key exists or not in a dictionary using if-in statement/in operator, get(), keys(), handling 'KeyError' exception, and in versions older than Python 3, using has_key(). 2.


2 Answers

In Python 3.x and 2.x you can use use list to force a copy of the keys to be made:

for i in list(d): 

In Python 2.x calling keys made a copy of the keys that you could iterate over while modifying the dict:

for i in d.keys(): 

But note that in Python 3.x this second method doesn't help with your error because keys returns an a view object instead of copynig the keys into a list.

like image 162
Mark Byers Avatar answered Sep 21 '22 03:09

Mark Byers


You only need to use "copy":

On that's way you iterate over the original dictionary fields and on the fly can change the desired dict (d dict). It's work on each python version, so it's more clear.

(BTW - Generally to iterate over copy of your data structure, instead of using ".copy" for "dict" or slicing "[:]" for "list", you can use import copy -> copy.copy (for shallow copy which equivalent to "copy" that supported by "dict" or slicing "[:]" that supported by "list") or copy.deepcopy on your data structure).

In [1]: d = {'a': [1], 'b': [1, 2], 'c': [], 'd':[]}  In [2]: for i in d.copy():    ...:     if not d[i]:    ...:         d.pop(i)    ...:           In [3]: d Out[3]: {'a': [1], 'b': [1, 2]} 
like image 35
Alon Elharar Avatar answered Sep 21 '22 03:09

Alon Elharar