11

If a variable is assigned any new content, will the memory allocated for the "old content" be "properly" free'd? For example, in the following script, will the memory for variable "a" as an array of zeros be free'd after "a" is assigned some new stuff

import numpy
a = numpy.zeros(1000)
a = a+1

I would imaging Python is smart enough to do everything cleanly, using the so-called 'garbage collection', which I never really be able to read through. Any confirmation? I'd appreciate it.

Liang
  • 1,015
  • 1
  • 10
  • 13
  • [this](http://stackoverflow.com/questions/3427632/how-does-pythonic-garbage-collection-with-numpy-array-appends-and-deletes) question might help as well. – Joel Cornett Apr 04 '12 at 21:34

2 Answers2

10

Eventually, the old memory will be freed, though you cannot predict when this will happen. It is dependent on the Python implementation and many other factors.

That said, for the example you gave and the CPython implementation, the old array should be garbage collected during the assignment.

(Note that NumPy arrays are a particularly complex example for discussing garbage-collector behaviour.)

Sven Marnach
  • 574,206
  • 118
  • 941
  • 841
  • Thank you Sven. The problem for me is that sometimes I need to operate big matrices. In consideration of memory and speed, I always wrap things in functions, hoping that at least any extra memory allocated in a function will be free'd at end of THE function. Is that a good way to avoid bad things? BTW, I do use NumPy arrays mainly, is there a good alternative regarding both performance and convenience? – Liang Apr 04 '12 at 21:55
  • @Liang: There's no reasonable alternative to NumPy arrays. If you want to avoid excessive memory usage, try to use in-place operations wherever possible, and [follow the recommendations in this excellent answer](http://stackoverflow.com/questions/4370745/view-onto-a-numpy-array/4371049#4371049); be sure to also have a look at the `numexpr` module linked there. For the code in your question, this would mean to use `a += 1` to avoid any temporary arrays in the first place. – Sven Marnach Apr 04 '12 at 22:07
  • 1
    There's also a difference between when an object's memory can be reused by another Python object, and when the memory is released back to the OS. CPython uses some specialized structures for particular data types that keep this from happening entirely in some cases, and fragmentation may keep it from happening in other cases. – kindall Apr 04 '12 at 22:16
3

You can find the answer by playing with gc module (and probably finetuning). It provides the ability to disable the collector, tune the collection frequency, and set debugging options. It also provides access to unreachable objects that the collector found but cannot free. See http://docs.python.org/library/gc.html

Maksym Polshcha
  • 18,030
  • 8
  • 52
  • 77
  • Thank you Mark. I will try it out. It looks formidable for me, though. Actually I was wandering is there a "general" principle, like, "wrapping thing in functions". Thank you for the suggestion. – Liang Apr 04 '12 at 22:00