我正在研究一些使用socket.fromfd()
函数的Python套接字代码。
但是,此方法并非在所有平台上都可用,因此在未定义方法的情况下,我正在编写一些回退代码。
确定方法是否在运行时定义的最佳方法是什么?以下内容是否足够或是否有更好的习惯用法?
if 'fromfd' in dir(socket):
sock = socket.fromfd(...)
else:
sock = socket.socket(...)
我有点担心dir()
的文档似乎不鼓励使用它。 getattr()
会是更好的选择,例如:
if getattr(socket, 'fromfd', None) is not None:
sock = socket.fromfd(...)
else:
sock = socket.socket(...)
思想?
编辑正如Paolo所指出的,这个问题是nearly a duplicate关于确定属性存在的问题。但是,由于使用的术语是不相交的(lk的“对象具有属性” vs my “模块具有函数”),因此保留此问题以进行搜索可能会有所帮助,除非两者可以合并。
答案 0 :(得分:37)
hasattr()
是最佳选择。去吧。 :)
if hasattr(socket, 'fromfd'):
pass
else:
pass
编辑:实际上,根据文档,所有hasattr正在做的是调用getattr并捕获异常。因此,如果你想要削减中间人,你应该选择marcog的答案。
编辑:我也刚刚意识到这个问题实际上是duplicate。其中一个答案讨论了你所拥有的两个选项的优点:捕获异常(“更容易请求宽恕而不是许可”)或者只是简单地检查(“在你跳跃之前看”)。老实说,我更多的是后者,但似乎Python社区倾向于前学派。
答案 1 :(得分:24)
或者只是使用try..except块:
try:
sock = socket.fromfd(...)
except AttributeError:
sock = socket.socket(...)
答案 2 :(得分:3)
hasattr(obj,'attributename')可能是更好的一个。 hasattr将尝试访问该属性,如果它不存在,它将返回false。
在python中可以使用动态方法,即在您尝试访问它们时创建的方法。他们不会在dir(...)。但是hasattr会检查它。
>>> class C(object):
... def __init__(self):
... pass
... def mymethod1(self):
... print "In #1"
... def __getattr__(self, name):
... if name == 'mymethod2':
... def func():
... print "In my super meta #2"
... return func
... else:
... raise AttributeError
...
>>> c = C()
>>> 'mymethod1' in dir(c)
True
>>> hasattr(c, 'mymethod1')
True
>>> c.mymethod1()
In #1
>>> 'mymethod2' in dir(c)
False
>>> hasattr(c, 'mymethod2')
True
>>> c.mymethod2()
In my super meta #2