• Java 及 Kotlin 中的可变参数 vararg


    本文地址


    目录

    Java 及 Kotlin 中的可变参数 vararg

    Java 中可变参数的规则

    • 可变参数只能出现在参数列表的最后
    • ... 代表可变参数,... 位于变量类型和变量名之间
    • 在方法体中以数组的形式访问可变参数

    Kotlin 中的规则类似

    可变参数的本质是数组

    Java 中对应数组 T[]

    public static void hello(String[] array, String... args) {
        Class<?> stringArrayClass = Array.newInstance(String.class, 0).getClass(); // 获取数组的 Class
    
        System.out.println(array.getClass() == args.getClass()); // true
        System.out.println(array.getClass() == stringArrayClass); // true
        System.out.println(args.getClass().getName()); // [Ljava.lang.String;
    }
    

    上面代码中的 stringArrayClass 代表的就是 String 数组的 Class 对象,参考

    Kotlin 中可能对应 Array

    fun hello(array: Array<String>, vararg args: String) {
        val stringArrayClass: Class<*> = java.lang.reflect.Array.newInstance(String::class.java, 0).javaClass
    
        println(array.javaClass == args.javaClass) // true
        println(array.javaClass == stringArrayClass) // true
        println(args.javaClass.name) // [Ljava.lang.String;
    }
    

    或 IntArray 等衍生数组

    fun hello(array: IntArray, vararg args: Int) {
        val intPrimitiveType: Class<Int>? = Int::class.javaPrimitiveType
        val intArrayClass: Class<*> = java.lang.reflect.Array.newInstance(intPrimitiveType, 0).javaClass
    
        println(array.javaClass == args.javaClass) // true
        println(array.javaClass == intArrayClass) // true
        println(args.javaClass.name) // [I
    }
    

    可变参数的应用

    可变参数的声明

    public static void javaTest(String name, int... args) {
        System.out.println(name + " -- " + args.length);
    }
    
    fun kotlinTest(name: String, vararg args: Int) = println("$name - ${args.size}")
    

    可变参数是否可为空

    • Java 中可变参数可为空,所以在调用前必须判空
    • Kotlin 中可变参数不可为空,所以在调用前不需要判空
      • 如果判空了,IDE 会提示你:Condition 'args==null' is always 'false'
      • 在 Java 中调用 Kotlin 的可变参数时,虽然传 null 可以编译通过,但运行时会直接崩溃
    javaTest("bqt");                // bqt - 0
    javaTest("bqt", null);          // 编译通过,运行时崩溃
    MainKt.kotlinTest("bqt", null); // 编译通过,运行时会直接崩溃
    
    kotlinTest("bqt")       // bqt - 0
    kotlinTest("bqt", null) // 编译不通过,Null can not be a value of a non-null type Int
    javaTest("bqt", null)   // 编译不通过,Null can not be a value of a non-null type Int
    

    可变参数的调用

    在 Kotlin 中,如果想将数组传入到可变参数,需要在引用前面加上 *

    public static void javaTest(String name, int... args) {
        MainKt.kotlinTest(name, 1, 2); // 这里的 MainKt 是自动生成的一个类,用于封装 Kotlin 中的顶层函数
        MainKt.kotlinTest(name, args);
        MainKt.kotlinTest(name, new int[]{1, 2, 3});
    }
    

    Java 中调用 Kotlin 中定义的顶层函数时,需要以静态方法的语法去调用,类名是 Kotlin 文件名 + 后缀 Kt

    fun kotlinTest(name: String, vararg args: Int) {
        Test.javaTest(name, 1, 2, 3)
        Test.javaTest(name, *args)
        Test.javaTest(name, *IntArray(3)) // 这里的 3 代表的其实是 size
    }
    

    Kotlin 类型转换

    fun main() {
        intTest("IntArray", *intArrayOf(1, 2, 3)) // Remove redundant spread operator
        intTest("Array<Int>", *arrayOf(1, 2, 3).toIntArray())
        intTest("List<Int>", *listOf(1, 2, 3).toIntArray())
    
        val stringArray = com.sun.xml.internal.fastinfoset.util.StringArray().also { it.add("1") }
        stringTest("StringArray", *stringArray.array)
        stringTest("Array<String>", *arrayOf("2")) // Remove redundant spread operator
        stringTest("List<String>", *listOf("3").toTypedArray())
    }
    
    fun intTest(name: String, vararg args: Int) = println("$name - ${args.toList()}")
    fun stringTest(name: String, vararg args: String) = println("$name - ${args.toList()}")
    

    StringArray 并不是 Kotlin 中定义的类,而是一个 Java 类。继承自 ValueArray(继承自 Object)
    StringArray.array 其实是调用了 public String[] getArray() 方法

    2022-5-2

  • 相关阅读:
    Legacy(点对线段有路走,线段向点有路走,线段树走dij)
    G. Death DBMS(查询每个主串和n个模板串匹配后val最大值,支持单点更新)
    2020 CCPC Wannafly Winter Camp Day5 J Xor on Figures(矩阵转01串,统计01串异或种类)
    zoj3988(自己集合和自己集合匹配)
    2020 CCPC Wannafly Winter Camp Day7 A(求任何子序列中相邻范围内数的个数的总和)
    hdu6241(给定树中向上向下限制求最小可能个数)
    hdu6230(求限制条件的回文个数,利用manacher+BIT求解)
    NOIP 2020 游记
    分散层叠算法学习笔记
    代理模式
  • 原文地址:https://www.cnblogs.com/baiqiantao/p/16216523.html
Copyright © 2020-2023  润新知