为什么一些可调用属性在dir()函数中没有列出?

8

为什么Python中的dir()函数不能显示所有可调用属性?

import win32com.client

iTunes = win32com.client.gencache.EnsureDispatch("iTunes.Application")
currentTrack = win32com.client.CastTo(iTunes.CurrentTrack,"IITFileOrCDTrack")

print dir(currentTrack)

结果:

['AddArtworkFromFile', 'CLSID', 'Delete', 'GetITObjectIDs', 'Play', 'Reveal', 'UpdateInfoFromFile', 'UpdatePodcastFeed', '_ApplyTypes_', '__doc__', '__eq__', '__getattr__', '__init__', '__module__', '__ne__', '__repr__', '__setattr__', '_get_good_object_', '_get_good_single_object_', '_oleobj_', '_prop_map_get_', '_prop_map_put_', 'coclass_clsid']

print currentTrack.Location

Location是可调用的,返回文件路径,但它未列在第一个结果中。它也不会出现在代码补全工具中。这是因为它通过getter方法获取吗?我在_prop_map_get_和_prop_map_put_下看到了它的列表。

另外,为什么currentTrack.Location返回文件路径,而currentTrack._prop_map_get_['Location']返回"(1610874880, 2, (8, 0), (), 'Location', None)"?它从哪里获取文件路径字符串?

2个回答

8
在Python中,一个对象可以有一个__getattr__方法。对于任何不存在的属性访问,它都会被调用。看起来这个对象在实现__getattr__时使用了_prop_map_get_
由于__getattr__可以进行任意计算以满足属性请求,并且可以为它无法处理的名称引发AttributeError,因此从外部无法列出所有可用属性。

+1 当我真正理解这一点时,对于Python(以及动态语言总体来说),就像灯泡在我脑海中亮了起来。 - bgporter
我很好奇PythonWin如何为使用COMObject实例的属性提供正确的完成列表,以及是否可以在Python代码中执行相同的操作,或者它是否执行了win32com包没有公开的操作。 - Wooble

4

不错。 Dir() 函数的功能是正确的,其行为是可以解释的。

Location 是 currentTrack 的属性,但只能通过 currentTrack._prop_map_get_ 访问。可调用的 _prop_map_get_ 列在 dir(currentTrack) 中。请参见 getattr,它与 currentTrack._prop_map_get_ 以某种方式映射。

在包装器 win32com 中会找到各种这样的情况。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接