IronPython 奇怪的行为

IronPython strange behaviour

我有文件 A.py:

...
from System.IO import Directory
...
execfile('B.py')

和文件 B.py:

...
result = ['a','b'].Contains('a')

这样的组合效果很好。 但是如果我在 A.py 评论这个特定的导入行然后 B.py 抱怨:

AttributeError: 'list' object has no attribute 'Contains'

我觉得很奇怪,尤其是 B.py 一个人运行良好。

模块 System.IO 中是否有一些 'list' 覆盖?有没有办法确定导入过程中发生了什么变化?或者避免这种奇怪的行为?

B.py 本身(在 IPy 2.7.4 上)也会导致您提供的错误。它应该是因为没有内置方法可以绑定该调用。您也可以尝试在标准 python 上重现此内容以确保。

将 "include" B.py 转换为 A.py 的方式存在固有的风险和问题,至少是因为缺少对 B 中代码执行范围的控制。如果您将代码包装在适当的 module/classes 中,您可以确定不会出现此类问题。

这可能(简化后,只是一个函数,没有 类 等)看起来像:

from B import getResult
getResult()
from System.IO import Directory
getResult()

def getResult():
    from System.IO import Directory
    result = ['a','b'].Contains('a')
    return result

如您所见,函数 getResult 可以确保所有导入和其他范围属性都是正确的,并且无论调用站点是否具有给定的导入,它都会起作用。

至于导入 System.IO.Directory 导致绑定到 IronPython.dll!IronPython.Runtime.List.Contains(object value) 的原因尚不清楚,需要仔细查看 IronPython 的内部实现。

如果您介意对 System.IO.Directory 的实际导入,但不想重构代码,您可以使用 LINQ for IronPython/ImportExtensions,因为它也会提供 Contains 方法。这不会减少,但实际上会增加您的导入样板,但更重要。

import clr
clr.AddReference("System.Core")
import System
clr.ImportExtensions(System.Linq)

result = ['a','b'].Contains('a')