gpt4 book ai didi

c# - IronPython 调用 TryGetMember 而不是 TryInvokeMember

转载 作者:行者123 更新时间:2023-11-30 12:30:07 24 4
gpt4 key购买 nike

我正在尝试将动态对象移交给 Ironpython,但 Ironpython 似乎并未调用 TryInvokeMember。相反,它会调用 TryGetMember 并给出无法调用结果的错误。

我已经用 IronPython 2.7 和 2.6.10920 试过了

示例代码:

动态对象:

class ExampleDynamicObject: DynamicObject {
public override bool TryGetMember(GetMemberBinder binder,
out object result) {
result = "TryGetMember";
return true;
}
public override bool TryInvokeMember(InvokeMemberBinder binder,
object[] args,
out object result) {
result = "TryInvokeMember";
return true;
}
}

调用 Mathode

static void Main(string[] args) {
dynamic example = new ExampleDynamicObject();
var program = @"test = example.Call2(2)";

var engine = Python.CreateEngine();
var scope = engine.CreateScope();
scope.SetVariable("example", example);
var source = engine.CreateScriptSourceFromString(program,
SourceCodeKind.Statements);
source.Execute(scope);
Console.ReadKey();
}

这会调用 TryGetMember 方法,然后引发 Microsoft.Scripting.ArgumentTypeException“str is not callable”

当您编写类似“test”(1) 的代码时抛出此错误

因此,Python 似乎没有意识到这是一个函数调用,而只是调用了一个属性。

但是当我尝试从 C# 调用它时

    Console.WriteLine(example.Call);
Console.WriteLine("----------------------------");
Console.WriteLine(example.Call(1));

这会起作用:

TryGetMember
-------------------
TryInvokeMember

有没有人建议如何解决这个问题?

解决方案:(编辑:calledMethodeName 必须是一个列表,否则嵌套方法将不起作用)

非常感谢 Jeff。

当我这样设计 Dynamic 时:

List<string> calledMethodeNames = new List<string>();

public override bool TryGetMember(GetMemberBinder binder,
out object result)
{
calledMethodeNames.Add(binder.Name);
result = this;
return true;
}
public override bool TryInvoke(InvokeBinder binder, object[] args, out object result)
{
//calledMethodeNames last Element has stored the Name of the called methode (remeber to remove it)
result = "TryInvoke";
return true;
}

一切正常。

线索是将对象本身作为成员返回,而不是对象是可调用的并且 python 调用 TryInvoke(不是 TryInvokeMember)

但是调用 TryInvoke 是因为在返回对象之后,调用了对象本身。所以 InvokeBinder 不知道被调用方法的名称。所以我将它存储到一个变量中。

最佳答案

这是预期的行为。 IronPython 使用 TryGetMember 后跟 TryInvoke,因为 Python 语言没有调用成员的概念:Python 方法调用始终是属性查找,然后是调用。

您遇到的错误是因为您将 result 设置为字符串(类型 str)并且字符串不可调用。您必须将 result 设置为另一个实现 TryInvoke 的动态对象或委托(delegate)。

关于c# - IronPython 调用 TryGetMember 而不是 TryInvokeMember,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17107417/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com