python jedi:如何检索实例的方法?
python jedi: how to retrieve methods of instances?
我为屏幕阅读软件构建了具有一些辅助功能的简单文本编辑器。
我正在使用 Python for .NET (pythonnet) 来显示包含富文本框的表单。
当用户在一段时间后按 Tab 键时,它会弹出一个上下文菜单,其中包含所选元素的完成信息。
好的,它适用于 Python 个对象,但它不适用于 .net 活动对象,这个问题没有解决方案。
现在,我想构建一个包含我正在编辑的模块的所有名称和定义的 TreeView 对象。
因此,例如我输入:
import sys
import os
lst = list()
等...
如果我使用源的 jedi.names,我可以检索 os、sys 和 lst。
对于每个名称,我想检索子定义,例如 sys 和 os 模块的函数,以及 lst 的方法。
我找不到用绝地武士做到这一点的方法:
names = jedi.names(MySource)
names[0].defined_names() # works for sys
names[1].defined_names() # works for os
names[2].defined_names() # doesn't work for lst instance of list().
有什么建议吗?
我尝试使用越来越多的编辑器,但是可访问性支持非常非常糟糕...
这看起来像是一个错误,其中 jedi.evaluate.representation.Instance.__getattr__()
错误地阻止了 .names_dict
的计算。我在你的 jedi/evaluate/representation.py
副本中添加了一个 pull request to the jedi repository to fix this. In the mean time, you can either add 'names_dict' to the whitelist in Instance.__getattr__()
,或者使用下面的代码为当前会话自动修补此方法。
import jedi
def patch_jedi():
__old__getattr__ = jedi.evaluate.representation.Instance.__getattr__
def __patched__getattr__(self, name):
if name == 'names_dict':
# do a simplified version of __old__getattr__, bypassing the name check
return getattr(self.base, name)
else:
# use standard behavior
return __old__getattr__(self, name)
# test whether jedi has been updated to avoid the Instance.defined_names() bug
try:
jedi.names("lst = list()")[0].defined_names()
except AttributeError as e:
if e.args[0].startswith("Instance ") and e.args[0].endswith("Don't touch this (names_dict)!"):
# patch jedi to avoid this error
print "patching jedi"
jedi.evaluate.representation.Instance.__getattr__ = __patched__getattr__
else:
# something else strange is going on
raise
patch_jedi()
print jedi.names("lst = list()")[0].defined_names()
# or: print jedi.Script("lst = list()").goto_definitions()[0].defined_names()
请注意,我不熟悉 jedi
,所以我不知道 defined_names()
是否适用于创建实例的定义。上面的代码不会修复像 jedi.names("lst = []")[0].defined_names()
这样的引用,并且没有明显的补丁可以做到这一点。所以可能有更深层次的事情我不知道。希望开发人员能够帮助解决这个问题,以响应该拉取请求。
我为屏幕阅读软件构建了具有一些辅助功能的简单文本编辑器。 我正在使用 Python for .NET (pythonnet) 来显示包含富文本框的表单。 当用户在一段时间后按 Tab 键时,它会弹出一个上下文菜单,其中包含所选元素的完成信息。 好的,它适用于 Python 个对象,但它不适用于 .net 活动对象,这个问题没有解决方案。 现在,我想构建一个包含我正在编辑的模块的所有名称和定义的 TreeView 对象。
因此,例如我输入:
import sys
import os
lst = list()
等... 如果我使用源的 jedi.names,我可以检索 os、sys 和 lst。 对于每个名称,我想检索子定义,例如 sys 和 os 模块的函数,以及 lst 的方法。 我找不到用绝地武士做到这一点的方法:
names = jedi.names(MySource)
names[0].defined_names() # works for sys
names[1].defined_names() # works for os
names[2].defined_names() # doesn't work for lst instance of list().
有什么建议吗? 我尝试使用越来越多的编辑器,但是可访问性支持非常非常糟糕...
这看起来像是一个错误,其中 jedi.evaluate.representation.Instance.__getattr__()
错误地阻止了 .names_dict
的计算。我在你的 jedi/evaluate/representation.py
副本中添加了一个 pull request to the jedi repository to fix this. In the mean time, you can either add 'names_dict' to the whitelist in Instance.__getattr__()
,或者使用下面的代码为当前会话自动修补此方法。
import jedi
def patch_jedi():
__old__getattr__ = jedi.evaluate.representation.Instance.__getattr__
def __patched__getattr__(self, name):
if name == 'names_dict':
# do a simplified version of __old__getattr__, bypassing the name check
return getattr(self.base, name)
else:
# use standard behavior
return __old__getattr__(self, name)
# test whether jedi has been updated to avoid the Instance.defined_names() bug
try:
jedi.names("lst = list()")[0].defined_names()
except AttributeError as e:
if e.args[0].startswith("Instance ") and e.args[0].endswith("Don't touch this (names_dict)!"):
# patch jedi to avoid this error
print "patching jedi"
jedi.evaluate.representation.Instance.__getattr__ = __patched__getattr__
else:
# something else strange is going on
raise
patch_jedi()
print jedi.names("lst = list()")[0].defined_names()
# or: print jedi.Script("lst = list()").goto_definitions()[0].defined_names()
请注意,我不熟悉 jedi
,所以我不知道 defined_names()
是否适用于创建实例的定义。上面的代码不会修复像 jedi.names("lst = []")[0].defined_names()
这样的引用,并且没有明显的补丁可以做到这一点。所以可能有更深层次的事情我不知道。希望开发人员能够帮助解决这个问题,以响应该拉取请求。