导入函数内部:在函数退出时回收内存?

时间:2017-10-18 15:23:32

标签: python micropython

相关问题:

如果函数内部有一个import语句,一旦函数退出,它所占用的内存是否会被回收?如果是,那么回收的时间是否确定(或者甚至 -ish )?

def func():
    import os
    ...
    # function about to exit; will memory occupied by `os` be freed?

如果有人了解micropython关于此主题的行为,可以获得奖励积分。

2 个答案:

答案 0 :(得分:3)

第一次导入执行模块中的代码。它创建模块对象的属性。每个后续导入仅引用第一次导入创建的模块对象。

Python中的模块对象实际上是单例。为了实现这一点,Python实现必须在第一次导入后保留唯一的模块实例,而不管模块绑定的名称如何。如果它被绑定到一个名称,因为还有from some_module import some_name形式的导入。

所以不,内存没有被回收。

不知道Micropython,但如果它在这里彻底改变语义,我会感到惊讶。你可以自己测试一下:

some_module.py:

value = 0

some_other_module.py:

def f():
    import some_module
    some_module.value += 1
    print(some_module.value)

f()
f()

这应该打印数字1和2.

答案 1 :(得分:0)

要了解@BlackJack所写的内容,根据Python语义,“import”语句会将模块引用添加到sys.modules,这样就可以防止模块对象被垃圾回收。

您可以尝试执行del sys.modules["some_module"],但无法保证模块占用的所有内存都将被回收。 (之前出现过这个问题,但我不记得它的当前状态,例如,如果字节码对象可以被垃圾收集)。

  

如果是,那么回收的时间是否确定(或甚至是-ish)?

在MicroPython中,“回收时间”肯定是不确定的,因为它使用纯粹的垃圾收集方案,没有引用计数。这意味着应该显式关闭任何耗费资源的对象(文件,套接字)。

否则,函数级导入在Python中是有效且有用的习惯用法,在MicroPython中尤其有用。它只允许在命中特定代码路径时导入某些模块。例如。如果用户从不调用某个函数,则不会导入模块,为用户在此特定应用程序/调用中需要的任务节省更多内存。