2

I'm not quite sure why the following doesn't work. I tried to send a dictionary object to a function, test a few things and make the dict null if certain criteria was met. I don't know why.

A simple version of what I tried to do:

def destroy_bad_variables(a):
    # test if a is a bad variable, nullify if true
    #del a # doesn't work.
    a = None
    print a # this says its null

def change(a):
    a['car'] = 9


b = {'bar':3, 'foo':8}
print b

change(b)
print "change(b):", b

destroy_bad_variables(b)
print "destroy_bad_variables(b):", b

It produces the following output:

{'foo': 8, 'bar': 3}
change(b): {'car': 9, 'foo': 8, 'bar': 3}
None
destroy_bad_variables(b): {'car': 9, 'foo': 8, 'bar': 3}

The dict can be modified by a function as is expected, but for some reason it can't be set to None. Why is this? Is there some good reason for this seemingly inconsistent behaviour? Forgive my ignorance, none of the books I've read on python explain this. As I understand it dicts are "mutable", the function should null the dict object and not some copy of it.

I know I can work around it by setting b = destroy(b) and returning None from destroy(), but I don't understand why the above doesn't work.

3
  • 1
    You're not destroying anything, you're just changing a's reference to None in destroy's local scope. Commented Dec 14, 2014 at 14:54
  • I don't understand "references". I found pointers very confusing. Is there somewhere that explains references in python in a clear way for those unfamiliar with pointers/references? Commented Dec 14, 2014 at 14:57
  • 2
    @shley: you might find Facts and myths about Python names and values helpful. Commented Dec 14, 2014 at 14:59

3 Answers 3

4

When you say

a = None

you are making a refer to None, which was earlier pointing to the dictionary object. But when you do

a['car'] = 9

a is still a reference to the dictionary object and so, you are actually adding a new key car to the dictionary object only. That is why it works.

So, the correct way to clear the dictionary is to use dict.clear method, like this

a.clear()
Sign up to request clarification or add additional context in comments.

Comments

0

the thing why its not working:

>>> a=[1,2,3,4]
>>> def destroy(a):
...     del a          # here a is local to destroy only
... 
>>> destroy(a)
>>> a
[1, 2, 3, 4]

Comments

0

You're not destroying anything, you're just changing a's value to None in destroy's local scope.

Why are you not simply using:

some_dictionary = None

To remove reference to some_dictionary? The garbage collector will do the destruction when no one references some_dictionary anymore.

In your code:

b = None # replaced: destroy(b)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.