繁体   English   中英

Jython装饰器:无法将第一个arg强制转换为org.python.core.PyFunction

[英]Jython Decorators: 1st arg can't be coerced to org.python.core.PyFunction

我正在构建一种使用Python编写CraftBukkit(Minecraft修改后的服务器软件)的脚本的方法。

我通过使用Jython加载Python脚本,然后为事件等添加装饰器来实现此目的。

我目前正在实现事件装饰器,但是我有一个问题:没有参数的装饰器可以正常工作,但是一旦添加了参数,它就会开始抱怨没有足够的参数。

这有效:

@script.event
def test(event):
    print "hi" # Works

public void event(PyFunction func) {
    return func;
}

这不是:

@script.event("player.PlayerMoveEvent", "normal")
def test(event):
    print "player moved!" # TypeError: event(): 1st arg can't be coerced to org.python.core.PyFunction

public void event(PyFunction func, PyString eventType, PyString priority) {
    // Do all kinds of crap
    return func;
}

这是我的Java代码: http : //pastebin.com/GsULYdJr

这与Jython无关。 等效的纯Python代码显示了实际的问题(为简单起见,我省略了类或名称空间script ):

def event(func, event_type, priority):
    # ...
    return func

@event("player.PlayerMoveEvent", "normal")
def test(event):
    print "player moved"

错误是

Traceback (most recent call last):
  ...
TypeError: event() missing 1 required positional argument: priority

这是由于装饰者的误解造成的。 您希望装饰后的函数定义像这样执行

def test(event):
    print "player moved"

test = event(test, "player.PlayerMoveEvent", "normal")

但是它是这样执行的:

__decorator = event("player.PlayerMoveEvent", "normal")

def test(event):
    print "player moved"

test = __decorator(test)

在后面的部分@孤立被评估,并且该结果被称为与test功能作为参数。 Python中通常的解决方法是使用闭包,但是在Java中这可能很麻烦。 用Python编写装饰器的一部分并保留当前的Java代码可能是最简单的:

def script(event_type, priority):
    def decorate(func):
        return script.event(func, event_type, priority)
    return decorate

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM