在 Haxe 中传递任意函数参数列表

Passing list of arbitrary function arguments in Haxe

在 ActionScript 中,我可以在函数声明中使用 ...,因此它可以接受任意参数:

function foo(... args):void { trace(args.length); }

然后我可以调用传递数组的函数:

foo.apply(this, argsArray);

我想用未知类型和数量的参数调用函数。这在 Haxe 中可行吗?

根据 Haxe 文档,您可以使用 Rest argument:

If the final argument of a macro is of type Array<Expr> the macro accepts an arbitrary number of extra arguments which are available from that array:

import haxe.macro.Expr;

class Main {
  static public function main() {
    myMacro("foo", a, b, c);
  }

  macro static function myMacro(e1:Expr, extra:Array<Expr>) {
    for (e in extra) {
      trace(e);
    }
    return macro null;
  }
}

您可以使用 Reflect.callMethod():

class Test {
    static function main() {
        var console = js.Browser.window.console;
        var fn = console.log;
        Reflect.callMethod(console, fn, [1, 2, "three", [4]]);
    }
}

补充一点,如果您正在为外部 JavaScript 库(或 Python、Lua 描述外部 ,或任何支持剩余参数的目标语言,例如...rest),有一个特定的Haxe类型haxe.extern.Rest来表达这一点。

这是一个示例,显示 JavaScript Math.max 函数处理可变参数:http://try.haxe.org/#4607C

class Test {
  static function main() {
    trace("JS Math.max takes varargs:");
    trace(MyMath.max(1,2,3,4)); // 4
    trace(MyMath.max(5,6));     // 6
  }
}

@:native("Math")
extern class MyMath {
  static function max(a:Float,
                      b:Float,
                      rest:haxe.extern.Rest<Float>):Float;
}

请注意,Haxe 标准库 而不是 Math.max 定义为 Rest,因为它的目标是跨平台兼容性。

Starting with Haxe 4.2,Haxe 将原生支持剩余参数:

function f(...args:Int) {
    for (arg in args) {
        trace(arg);
    }
}

f(1, 2, 3);

...args:Int 只是 rest:haxe.Rest<Int> 的语法糖。只有函数的最后一个参数可以是剩余参数。

您还可以使用 ... 在调用带有剩余参数的函数时“展开”数组:

final array = [1, 2, 3];
f(...array);