Can you do ... with the dictionary? (14)


#1

Can you delete a value, without having to check in which key it is?

What I mean is that if you can delete 'dagger' in the key 'backpack' like this:

inventory['backpack'].remove('dagger')

But i ask if i can remove 'dagger' without having to check backpack


#2

Yes and no, you need to destroy the key or set the key to an empty string.

If you don't know what the key is, but do know what the value is, you can something like this:

for key, value in inventory.iteritems():
    if type(value) is not int:
        if "dagger" in value:
            inventory[key].remove('dagger')

#3

for key, value in inventory.items():
    if isinstance(value, list):
        inventory[key] = [x for x in value if x != 'dagger']

Would be faster (removing is expensive, iterators are slower, only save memory) and more robust (what if a string is added), but it's still a bad idea to compare lots of values until you find a match, it's better to use a data structure that supports constant time lookups and removals like set or dict (could be nested dicts where the key is the item type and the value is the amount)

If the list should not be replaced then this could be used instead:

value[:] = [x for x in value if x != 'dagger']
which changes the already existing list instead of replacing it.


#4

I see python3 syntax.

Anyway, i never claimed this was a fast, good robust way, but the question was how remove dagger if the key was unknown. So i did. Give me a second to run your code

Your method seems better indeed.


#5

That's valid for both Python2 and Python3!


#6

I have much to learn :slightly_smiling:


#7

What this does: inventory['backpack'] is to retrieve the value that the key 'backpack' corresponds to. That value is not a key, the key was used to retrieve the value. In this case, that value is a list.
Inventory looks something like this:
inventory = {'backpack' : ['dagger', 'toothpick', 'a purple fish']}
It's a dictionary, it has a key ('backpack') and the corresponding value is a list from which you want to remove the dagger.

In order to remove something from that list, you have to get a reference to that list. So there's no way to remove from that list without having access to the list. We can, as @stetim94 says, search for all lists contained by inventory, but the result of that would still be that we found the backpack.

You might for example have both a wagon and a backpack in your inventory (your possessions), and you might want to get a dagger out of either of them. So then you would loop through all your containers (the wagon and the backpack) and see if there's a dagger there. And then you might either continue, removing all daggers, or stop this loop if you only wanted to remove one.