我应该在 urllib.urlopen() 之后调用 close() 吗?
题
我是 Python 新手,正在阅读别人的代码:
应该 urllib.urlopen()
紧随其后 urllib.close()
?否则,就会泄漏连接,对吗?
解决方案
在close
必须调用方法上的结果的urllib.urlopen
,请不可以的urllib
模块本身作为你正在考虑(你提到urllib.close
上 - 这没有按“T存在)。
最好的方法:代替x = urllib.urlopen(u)
等,使用:
import contextlib
with contextlib.closing(urllib.urlopen(u)) as x:
...use x at will here...
在with
语句和closing
上下文管理器,将确保甚至在异常的存在正确关闭。
其他提示
就像 @Peter 所说,超出范围的打开的 URL 将有资格进行垃圾收集。
不过,还要注意的是 urllib.py
定义:
def __del__(self):
self.close()
这意味着 当该实例的引用计数达到零时, , 它是 __del__
方法将被调用,因此它的 close
方法也会被调用。引用计数达到零的最“正常”方法是简单地让实例超出范围,但是没有什么严格阻止您显式 del x
早期(但是它不直接调用 __del__
但只是将引用计数减一)。
显式关闭资源当然是一种好方法——尤其是当您的应用程序面临使用过多资源的风险时——但是 Python 将要 如果您不做任何有趣的事情,例如维护(循环?)对您不再需要的实例的引用,它会自动为您清理。
严格地说,这是真实的。但在实践中,一次(如果)urllib
超出范围,则连接将被自动垃圾收集器关闭。
您基本的做的需要使用的 IronPython的:当明确关闭连接。在走出去的范围内自动关闭依赖于垃圾收集。我跑到那里的垃圾收集没有这么久的Windows跑出插座的运行情况。我是轮询以高频率(即高达IronPython和连接将允许〜7HZ)一个网络服务器。我可以看到(在使用即插座)中的“新建连接”上去了的性能监视器。解决的办法是每次调用gc.collect()
之后调用urlopen
。