真实的国产乱ⅩXXX66竹夫人,五月香六月婷婷激情综合,亚洲日本VA一区二区三区,亚洲精品一区二区三区麻豆

成都創(chuàng)新互聯(lián)網(wǎng)站制作重慶分公司

Java與Kotlin之間怎樣進(jìn)行互操作

這篇文章主要介紹了Java與Kotlin之間怎樣進(jìn)行互操作,具有一定借鑒價(jià)值,感興趣的朋友可以參考下,希望大家閱讀完這篇文章之后大有收獲,下面讓小編帶著大家一起了解一下。

創(chuàng)新互聯(lián)專(zhuān)注于雨湖網(wǎng)站建設(shè)服務(wù)及定制,我們擁有豐富的企業(yè)做網(wǎng)站經(jīng)驗(yàn)。 熱誠(chéng)為您提供雨湖營(yíng)銷(xiāo)型網(wǎng)站建設(shè),雨湖網(wǎng)站制作、雨湖網(wǎng)頁(yè)設(shè)計(jì)、雨湖網(wǎng)站官網(wǎng)定制、小程序設(shè)計(jì)服務(wù),打造雨湖網(wǎng)絡(luò)公司原創(chuàng)品牌,更為您提供雨湖網(wǎng)站排名全網(wǎng)營(yíng)銷(xiāo)落地服務(wù)。

前言

目前kotlin是谷歌首推的開(kāi)發(fā)Android的語(yǔ)言,但由于歷史原因,我們絕大部分項(xiàng)目依舊還是以Java為主的,也就是說(shuō)存在Java和Kotlin兩種語(yǔ)言同時(shí)開(kāi)發(fā)的情況。

有人會(huì)說(shuō)把老項(xiàng)目全部翻譯成Kotlin,的確可以怎么做,但是成本還是挺大的。我們只能一點(diǎn)一點(diǎn)慢慢的向kotlin語(yǔ)言遷移。

那么在遷移的過(guò)程中就避免不了Java和Kotlin相互調(diào)用的情況。即Kotlin調(diào)用Java或者Java調(diào)用Kotlin。下面我們就來(lái)具體看下兩者之間相互操作的一些解決方案。

kotlin調(diào)用java

可空性(Nullability)

Java默認(rèn)有數(shù)值可空性而kotlin沒(méi)有,所以在調(diào)用Java的方法的時(shí)候不知道會(huì)不會(huì)收到空值。
所以我們?cè)贙otlin中調(diào)用Java的時(shí)候需要添加 ?或者 !來(lái)告訴Kotlin有可能出現(xiàn)空值。

比如這里有一個(gè)Java方法,接受一組字符串后返回一組做字符串:

public Set toSet(Collection elements){
 //TODO
}

那么Kotlin在調(diào)用的時(shí)候是不能確定輸入和輸出是否可為空的。就需要使用?或者 !來(lái)輔助判斷。

為了方便Kotlin調(diào)用,我們通常使用 @NotNull 注解來(lái)標(biāo)識(shí)Java代碼的非原始參數(shù)、字段、返回值。

@NotNull
Set<@NotNull String> toSet(@NotNull Collection<@NotNull String> elements){
 //TODO
}

這個(gè)Kotlin在調(diào)用的時(shí)候就明確知道不能為空,這里我們使用的是jetBrain的 @NotNull注解,當(dāng)然還有其他選擇,如下圖:

Java與Kotlin之間怎樣進(jìn)行互操作

這里還是推薦使用JetBrain或者Android的注解。

前綴屬性:(getter、setter)

如果是使用Java bean,那么我們?cè)贙otlin中調(diào)用就沒(méi)有什么問(wèn)題。

如果你的空參數(shù)方法是以get開(kāi)頭的,那么Kotlin就知道這是getter,就可以通過(guò)屬性名來(lái)訪問(wèn)它。

相同的如果是由set開(kāi)頭的單一參數(shù)方法,那么Kotlin就知道這是setter,就通過(guò)屬性名直接賦值。

當(dāng)然is的工作原理也是和它們類(lèi)似的。

我們定義一個(gè)Java bean:

class User {
 
 private String name;
 private int age;

 public String getName() {
  return name;
 }

 public void setName(String name) {
  this.name = name;
 }

 public int getAge() {
  return age;
 }

 public void setAge(int age) {
  this.age = age;
 }
}

Kotlin中訪問(wèn)

val user = User()
user.name = "四爺" //賦值
val age = user.age //獲取age字段值

關(guān)鍵字(keywords)

kotlin中有很多系統(tǒng)定義的關(guān)鍵字如 fun is in objects、typeof、val、var、when、typealias等。

這些關(guān)鍵字在java是可以被使用的,但是在kotlin卻是不行的。

函數(shù)或者參數(shù)使用了這些關(guān)鍵字,那么kotlin在調(diào)用的時(shí)候會(huì)出現(xiàn)一些問(wèn)題,比如Java中定義了一個(gè)方法名叫 is 的方法。那么在Kotlin中直接調(diào)用就會(huì)報(bào)錯(cuò)。

那么最簡(jiǎn)單的方法就是重命名Java方法,但如果調(diào)用的是三方庫(kù)的方法,就很難去重命名了。
所以我們另一種解決方式是在Kotlin調(diào)用java方法的時(shí)候加上 `` 反引號(hào)來(lái)使用。

Utils.`is`()

但是我們?nèi)绻苤孛€是重命名,以防止代碼出現(xiàn)太多的符號(hào)。

避免在任何擴(kuò)展方法和擴(kuò)展屬性上使用Any

Java與Kotlin之間怎樣進(jìn)行互操作

運(yùn)算符重載(operator Overloading)

在Java不存在運(yùn)算符重載,而kotlin有。比如:

a+b => a.plus(b)

在kotlin中將運(yùn)算符 + 翻譯為了方法 plus。

如果在Java中使用了同樣的方法名稱(chēng),比如 加(plus)、 減(minus)或者其他運(yùn)算符名稱(chēng),那么請(qǐng)務(wù)必確保他們與運(yùn)算符兼容,避免意外調(diào)用他們。

Java調(diào)用Kotlin

JvmName & JvmMultifileClass

當(dāng)我們?cè)谶w移的時(shí)候會(huì)將Java的工具類(lèi)翻譯為Kotlin拓展函數(shù)或者頂層函數(shù)。但是這樣處理之后,在Java文件中是無(wú)法直接調(diào)用的,此時(shí)我們需要加注解 @file:JvmName(“文件名稱(chēng)”):

Ext.kt文件

@file:JvmName("ExtUtils")
package com.demo.javaAndKotlin

fun a(): String {
 ...
}

fun b(): String {
 ...
}

這里我們將名稱(chēng)命名為ExtUtils。此外,我們可能還有其他的頂層函數(shù)或者擴(kuò)展函數(shù)。按照上面這種方式我們也可以指定一個(gè)其他的名稱(chēng),但是如果我們也想使用ExtUtils這個(gè)名稱(chēng)的時(shí)候會(huì)報(bào)錯(cuò):

Duplicate JVM class name

此時(shí)我們需要在不同的文件中加入新的注解 @file:JvmMultifileClass 。意思是將所有的文件合并到一個(gè)新的名稱(chēng)為ExtUtils文件中。

ExtOther.kt文件

@file:JvmMultifileClass
@file:JvmName("ExtUtils")
package com.demo.javaAndKotlin

fun c(str: Any): String {
 ...
}

我們?cè)贓xt.kt文件中也加入@file:JvmMultifileClass注解,我們就可以在Java文件中直接使用ExtUtils來(lái)調(diào)用 a(),b(),c()方法了。

JvmField

在 kotlin中我們使用的數(shù)據(jù)類(lèi)即 data class 是不需要指定getter和setter的,可以直接通過(guò)字段名來(lái)訪問(wèn)它們。但是如果是在Java文件中調(diào)用data class依舊是需要使用getter和setter方法進(jìn)行調(diào)用的。這里我們是可以修改他們的,那就是使用 @JvmField 注解,通過(guò)注解,可以直接將字段暴露出去進(jìn)行訪問(wèn)。

data class Person(

 @JvmField var name: String,
 @JvmField var age: Int
)

//java中調(diào)用
Person person = new Person("",1);
person.name = "";
person.age = 10;

但是也有例外就是lateinit修飾的字段會(huì)自動(dòng)暴露,無(wú)需指定@JvmField注解。還有const修飾的字段也是一樣會(huì)自動(dòng)暴露。

另外,如果我們想在Java中調(diào)用setName的時(shí)候修改這個(gè)屬性名稱(chēng)不叫setName,這里我們需要使用@set:JvmName 注解。同理修改getName使用@get:JvmName 。需要注意的是,指定了@set:JvmName或者@get:JvmName注解后不需要在指定@JvmField了。

data class Person(

 @set:JvmName("changeName")
 var name: String,
 @JvmField var age: Int,
 @get:JvmName("likesPink")
 var likesPink: Boolean
){
 lateinit var address:String
}

JvmStatic

當(dāng)我們將Java文件的靜態(tài)方法遷移到Kotlin中時(shí),我們會(huì)將其放在 companion object中,但是這樣處理之后在Java文件中無(wú)法直接調(diào)用,得通過(guò)companion對(duì)象實(shí)例方法來(lái)調(diào)用。

class MyService {
 internal fun doWork() {
  ...
 }

 companion object {
  fun schedule(context: Context) {
   ...
  }
 }
}

//在Java中調(diào)用
MyService.Companion.schedule(this);

幸運(yùn)的是Kotlin提供了 @JvmStatic 注解。他會(huì)讓Kotlin在編譯器完成類(lèi)封裝后生成一個(gè)靜態(tài)方法。

class MyService {
 internal fun doWork() {
  ...
 }

 companion object {
   @JvmStatic
  fun schedule(context: Context) {
   ...
  }
 }
}

//在Java中調(diào)用
MyService.schedule(this);

JvmOverloads

在Kotlin中我們可以給函數(shù)的參數(shù)設(shè)置默認(rèn)值,即默認(rèn)參數(shù)。但是這個(gè)功能在Java中是沒(méi)有的。如果不做任何處理,那么在Java中調(diào)用函數(shù)的時(shí)候,就必須每個(gè)參數(shù)都要傳入。那么我們?cè)O(shè)置的默認(rèn)參數(shù)就沒(méi)有任何意義了。

所以,Kotlin給我們提供了 @JvmOverloads注解,使用這個(gè)注解后,會(huì)讓Kotlin編譯器按照從左向右的順序依次為每一個(gè)可選參數(shù)生成重載。

@JvmOverloads
fun Bitmap.resize(width: Int, height: Int = 200) {

}

//java調(diào)用
ExtUtils.resize(bitmap,100);

這里我們?cè)贙otlin中很容易就理解了Bitmap.resize方法的含義,但是ExtUtils.resize這樣調(diào)用的時(shí)候,方法名不夠明確。所以我們可以使用@JvmName注解來(lái)指定名稱(chēng)。

@JvmName("resizeBitmap")
@JvmOverloads
fun Bitmap.resize(width: Int, height: Int = 200) {

}
//java調(diào)用
ExtUtils.resizeBitmap(bitmap,100);

感謝你能夠認(rèn)真閱讀完這篇文章,希望小編分享的“Java與Kotlin之間怎樣進(jìn)行互操作”這篇文章對(duì)大家有幫助,同時(shí)也希望大家多多支持創(chuàng)新互聯(lián),關(guān)注創(chuàng)新互聯(lián)行業(yè)資訊頻道,更多相關(guān)知識(shí)等著你來(lái)學(xué)習(xí)!


分享標(biāo)題:Java與Kotlin之間怎樣進(jìn)行互操作
本文URL:http://weahome.cn/article/gopiig.html

其他資訊

在線咨詢

微信咨詢

電話咨詢

028-86922220(工作日)

18980820575(7×24)

提交需求

返回頂部