我是 Python 的新手,正在阅读别人的代码:
urllib.urlopen()
后面是否应该跟着 urllib.close()
?否则会造成连接泄漏,对吗?
close
方法必须在urllib.urlopen
的结果对象上调用,而不是在你想象中的urllib
模块本身上进行调用(正如你提到的urllib.close
- 这并不存在)。
最好的做法是:不要使用x = urllib.urlopen(u)
等方式,而要使用:
import contextlib
with contextlib.closing(urllib.urlopen(u)) as x:
...use x at will here...
with
语句和closing
上下文管理器可以确保在异常情况下也能正确关闭。
就像 @Peter 所说的那样,超出范围的打开的URL将会成为垃圾回收的候选对象。
但是,还要注意在CPython中URLopener
定义了 :
def __del__(self):
self.close()
这意味着当该实例的引用计数归零时,它的 __del__
方法将被调用,从而也会调用其 close
方法。最常见的使引用计数归零的方式是让实例超出作用域,但没有什么严格的限制阻止你提前显式地使用 del x
(但直接减少一次引用计数,而不是直接调用 __del__
)。
显式关闭资源通常是一个好的做法,特别是当应用程序可能使用过多的资源时,但如果你不保留对不再需要的实例的(循环?)引用等诡异操作,Python 也会自动为您进行清理。
gc.collect()
或者 close()
可以清理掉这些句柄]。 - Charles Duffy严格来说,这是正确的。但实际上,一旦(如果)urllib
超出范围,连接将被自动垃圾回收器关闭。
gc.disable
可以禁用GC。 - gsneddersurlopen
后调用gc.collect()
。Connection:close
头部。这是官方文档中的内容,您可以在 此处 进行查看。
data = urllib2.urlopen('url').read()
? - Facundo Cascowith
语句。以下是示例代码:with urllib.urlopen(u) as x: ...
- merwokcontextlib.closing
? - user66081urllib.urlopen
根本不存在。 - Eric