为什么Kotlin在使用Proxy时抛出IllegalArgumentException

这是使用InvocationHandler的Java代码的Kotlin等价物:

 override fun invoke(proxy: Any?, method: Method?, args: Array<out Any>?): Any { println("before httprequest--->" + args) val ret = method!!.invoke(obj, args) println("after httprequest--->") return ret } 

Java代码:

 public Object invoke(Object o, Method method, Object[] args) throws Throwable { System.out.println("jdk--------->http" + args); Object result=method.invoke(target, args); System.out.println("jdk--------->http"); return result; } 

在这两种情况下args都是null,但是如果我运行它,Kotlin代码会给Exception

 Exception in thread "main" java.lang.IllegalArgumentException: wrong number of arguments 

Kotlin使用标准Java类的原因是什么?

当你在kotlin中将args传入method!!.invoke(obj, args)时,它实际上是一个数组类型的单个参数,默认情况下它不会被分解为单独的参数。

要实现这种行为,请使用spread运算符 : *args

 val ret = method!!.invoke(obj, *args) 

使用这个语法, args将以与Java可变参数相同的方式传递。 例如,这些代码行是等价的:

 someVarargsFunction("a", "b", "c", "d", "e") someVarargsFunction("a", "b", *arrayOf("c", "d"), "e") 

注意:如果一个方法没有任何参数, args将是null ,并且将它传播到Kotlin将导致NullPointerException 。 作为一种解决方法,使用*(args ?: arrayOfNulls<Any>(0)) ,并在描述的角落案例中右边的部分被选中并扩展为零参数。


我的例子代理实现:

 interface SomeInterface { fun f(a: Int, b: Int): Int } val obj = object : SomeInterface { override fun f(a: Int, b: Int) = a + b } 

 val a = Proxy.newProxyInstance( SomeInterface::class.java.classLoader, arrayOf(SomeInterface::class.java)) { proxy, method, args -> println("Before; args: " + args?.contentToString()) val ret = method!!.invoke(obj, *(args ?: arrayOfNulls<Any>(0))) println("After; result: $ret") ret } as SomeInterface println(af(1, 2)) 

输出是:

 Before; args: [1, 2] After; result: 3 3 
Interesting Posts