Android面试题之Kotlin和Java之间互操作

本文首发于公众号"AntDream",欢迎微信搜索"AntDream"或扫描文章底部二维码关注,和我一起每天进步一点点

互操作性和可空性

  • 要注意Java中所有类型都是可空的
  • String!表示平台数据类型
kotlin 复制代码
public class JavaTest {
        public String generateName() {
            return "name";
        }

        //可以用注解标注可空
        @Nullable
        public String generateNullString() {
            return null;
        }
    }



    fun main() {
        val result = JavaTest()
        //要用安全操作符来操作
        println(result?.generateName())
    }

类型映射

  • kotlin代码运行时,所有的映射类型都会重新映射回对应得Java类型

属性访问

  • 不需要调用相关setter和getter方法,可以用赋值语法来设置一个Java字段值
kotlin 复制代码
fun main() {
    val result = JavaTest()
    println(result.generateNullString())
    //对应的Java类中属性要实现get和set方法
    println(result.points)
}

@JvmName

  • 用来注解指定编译类的名字,方便Java调用

    //System.out.printf(HeroKt.sayHello()); //用JvmName改了名字后 System.out.printf(Hero.sayHello());

@JvmField

用@JvmField修饰后,Java中可以直接调用属性,不用getter方法

java 复制代码
class SpellBook {
    @JvmField
    val spells = "hello world"
}

public class JHaa {
    public static void main(String[] args) {
        SpellBook spellBook = new SpellBook();
        //没有@JvmField修饰时的调用方法
//        spellBook.getSpells();
        System.out.printf(spellBook.spells);
    }
}

@JvmOverloads

  • 协助产生kotlin函数的重载版本,设计一个可能会暴露给Java用户使用的API,记得使用 @JvmOverloads注解
kotlin 复制代码
class SpellBook {
        @JvmField
        val spells = "hello world"

        @JvmOverloads
        fun handleWithDefault(left:String = "left", right:String = "right"){
            println("you handle with $left and $right")
        }
    }

    public class JHaa {
        public static void main(String[] args) {
            SpellBook spellBook = new SpellBook();
    //        spellBook.getSpells();
            System.out.printf(spellBook.spells);
            //没有JvmOverloads注解时会报错,因为没有这个无参的重载函数版本
            spellBook.handleWithDefault();
        }
    }

@JvmStatic

  • @JvmField注解还能用来以静态方式提供伴生对象里定义的值
  • @JvmStatic注解的作用类似于@JvmField,允许你直接调用伴生对象的函数
less 复制代码
//互操作
    class SpellBook {
        @JvmField
        val spells = "hello world"

        @JvmOverloads
        fun handleWithDefault(left:String = "left", right:String = "right"){
            println("you handle with $left and $right")
        }

        companion object{
            @JvmField
            val MAX_SPELL_COUNT = 10
            @JvmStatic
            fun getSpell() = println("i am groot!")
        }
    }

    public class JHaa {
        public static void main(String[] args) {
            SpellBook spellBook = new SpellBook();
            //伴生对象属性的调用方式
    //        spellBook.Companion.getMAX_SPELL_COUNT();
            //伴生对象的属性加了@JvmField修饰以后
            int result = spellBook.MAX_SPELL_COUNT;

            spellBook.Companion.getSpell();
            //加了@JvmStatic修饰以后
            spellBook.getSpell();
        }
    }

@Throws

  • 抛出一个需要检查的指定异常,Java和kotlin有关的异常检查的差异让@Throws注解解决了,在编写供Java开发者调用的Kotlin API时,要考虑使用@Throws注解。这样用户就指定怎么正确处理任何异常了
  • kotlin中抛出的异常会被转换成Throwable,Java中会catch不了。加上@Throws注解就可以在Java中正常catch
kotlin 复制代码
class SpellBook {

        @Throws(IOException::class)
        fun funWithException() {
            throw IOException()
        }
    }

    public class JHaa {
        public static void main(String[] args) {
            SpellBook spellBook = new SpellBook();

            try {
                spellBook.funWithException();
                //没有Throws时,这里只能是Throwable,编译器也不会提示
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

函数类型操作

  • kotlin函数类型和匿名函数的简洁高效的语法因->操作符而实现,但Java8之前的JDK版本不支持lambda表达式。
  • 在Java里,kotlin函数类型使用FuctionN这样的名字的接口来表示,N代表值参的数目,这样的Function接口由23个,每一个都包含一个invoke函数,专门用于调用函数类型函数
typescript 复制代码
class SpellBook {
     
    val translator = { origin:String ->
        println(origin.lowercase().capitalize())
    }
}

public class JHaa {
    public static void main(String[] args) {
        SpellBook spellBook = new SpellBook();

        Function1<String, Unit> translator = spellBook.getTranslator();
        translator.invoke("TRACE");
}

欢迎关注我的公众号查看更多精彩文章!

相关推荐
lxysbly5 小时前
n64模拟器安卓版带金手指2026
android
Serene_Dream7 小时前
JVM 并发 GC - 三色标记
jvm·面试
游戏开发爱好者88 小时前
日常开发与测试的 App 测试方法、查看设备状态、实时日志、应用数据
android·ios·小程序·https·uni-app·iphone·webview
王码码20358 小时前
Flutter for OpenHarmony 实战之基础组件:第三十一篇 Chip 系列组件 — 灵活的标签化交互
android·flutter·交互·harmonyos
黑码哥8 小时前
ViewHolder设计模式深度剖析:iOS开发者掌握Android列表性能优化的实战指南
android·ios·性能优化·跨平台开发·viewholder
亓才孓8 小时前
[JDBC]元数据
android
独行soc8 小时前
2026年渗透测试面试题总结-17(题目+回答)
android·网络·安全·web安全·渗透测试·安全狮
金融RPA机器人丨实在智能9 小时前
Android Studio开发App项目进入AI深水区:实在智能Agent引领无代码交互革命
android·人工智能·ai·android studio
科技块儿9 小时前
利用IP查询在智慧城市交通信号系统中的应用探索
android·tcp/ip·智慧城市
独行soc9 小时前
2026年渗透测试面试题总结-18(题目+回答)
android·网络·安全·web安全·渗透测试·安全狮