快速切換至Kotlin for Android模式
關於Kotlin的文章,已經構思了很久。一直不知道該怎麼寫。文件式文章?那不如直接看文件,何必需要我再多“嗶嗶”呢。思來想後,決定寫一篇快速在Android開發中感受Kotlin的其妙的文章。
說實話,最開始搞Kotlin我是拒絕的。為啥?因為完全沒有感覺到用它替換Java開發有什麼實質性的改變;而且感覺語法很“彆扭”!(其實說白了,就是不想學,給自己找藉口。哈哈)
但是,後來機緣巧合卻感受到了Kotlin的有趣之處。當然這一切的開始,要克服寫久了Java的那一種“彆扭”(由其是Lambda寫的也不多的情況下)。OK,不扯了。文章將從我接觸Kotlin時,遇到“彆扭”的地方開始展開。
正文
靜態方法
第一個讓我懵逼的是靜態方法。在Kotlin裡邊被叫做了:伴生物件。這裡不扯“花裡胡哨”的介紹。直接上程式碼:
public class StringUtils{ public static void myFun(){ Log.d("StringUtils","Haha"); } } 複製程式碼
在Java中這麼一個簡單工具類中的靜態方法,Kotlin要怎麼寫?
class StringUtils{ companion object { fun myFun(){ Log.d("StringUtils","Haha") } } } 複製程式碼
匿名內部類
setOnClickListener是我們比較常用的匿名內部類的使用場景:
btn.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { Log.d("Listener","Haha") } } 複製程式碼
那麼到了Kotlin中又是什麼樣子了呢?
btn.setOnClickListener { Log.d("Listener","Haha") } 複製程式碼
直接幫我們Lambda化了。如果我們不想Lambda化那應該是什麼樣子?
btn.setOnClickListener(object : View.OnClickListener{ override fun onClick(v: View?) { Log.d("Listener","Haha") } }) 複製程式碼
也沒什麼特別的,其實就是Kotlin的語法。因為Kotlin裡邊宣告的變數要寫在前面,其型別用:號隔開,寫在後面。也就是現在這個樣子。不過需要注意的,這裡的 object 代表匿名物件型別。
這裡有一個小細節,不知道大兄弟們有沒有注意到。在Java中我們new匿名內部類的時候: new View.OnClickListener(){}
,是有()的。而在Kotlin中則: View.OnClickListener{}
沒有()。這裡也是屬於語法細節,加上()表示顯示的呼叫這個類的構造方法。

如果這樣的話,那就和new普通的類,沒什麼區別的(而不是匿名內部類)。藉著匿名內部類,我們直接來看一下Kotlin在RxJava中的實戰。
Kotlin in RxJava
先看一個很簡單的Java用法:
Observable.just(0) .map(new Function<Integer, String>() { @Override public String apply(Integer integer) throws Exception { return integer.toString(); } }) .subscribe(new Consumer<String>() { @Override public void accept(String s) throws Exception { Log.d("RxJava", s); } }, new Consumer<Throwable>() { @Override public void accept(Throwable throwable) throws Exception { Log.d("RxJava", throwable.getMessage()); } }); 複製程式碼
對於Kotlin來說,在Lambda的加持之下,寫法變得異常的簡潔(當然Java進行Lambda化也很簡潔):
Observable.just(0) .map({ it!!.toString() }) .subscribe({ t: String -> Log.d("RxJava", t) }, { t: Throwable -> Log.d("RxJava", t.message) }) 複製程式碼
如果對Lambda不是很熟悉的大兄弟們,肯定有點懵。那麼咱們換成普通的kotlin,,是不是感覺很熟悉? object 又出現了,沒錯這裡就是普通的匿名內部類而已。
Observable.just(0) .map(object : Function<Int, String> { override fun apply(t: Int): String { return t.toString() } }) .subscribe(object : Consumer<String> { override fun accept(t: String) { Log.d("RxJava", t) } }, object : Consumer<Throwable> { override fun accept(t: Throwable) { Log.d("RxJava", t.message) } }) 複製程式碼
Kotlin in Adapter
上述的幾塊程式碼,我們一起感受了Kotlin在RxJava中的變形。說實話,如果丟擲Lambda,真心談不上什麼大的變化。就是語法上的轉變。聊過了我們日常開發比重比較大的RxJava,接下來我們再來看一看另一個重頭戲Adapter。這裡直接上Kotlin程式碼:
class TestAdapter(var data: List<String>,var context:Context) : RecyclerView.Adapter<TestAdapter.ViewHolder>() { override fun onCreateViewHolder(parent: ViewGroup?, viewType: Int): ViewHolder { return ViewHolder(TextView(context)) } override fun getItemCount(): Int { return data.size } override fun onBindViewHolder(holder: ViewHolder?, position: Int) { holder!!.textView.text = "Haha" } class ViewHolder(var textView: TextView) : RecyclerView.ViewHolder(textView) } 複製程式碼
最開始看這個程式碼的時候,我是有點懵的,感覺不知所措。其實帶入Kotlin的語法,非常的好理解。在最開始宣告這個class的時候,我們直接在TestAdapter的 主構造方法 中聲明瞭兩個 var 的變數。這種寫法就類似於Java中的:
class TestAdapter { public List<String> data; public Context context; public TestAdapter(List<String> data, Context context) { this.data = data; this.context = context; } } 複製程式碼
這也就是為什麼我們能在class裡邊隨意呼叫data和context的原因。
注意 var ,如果我們在構造方法中宣告時不加上var,就可以理解為這個變數是區域性變數。只適用於構造方法中。
這中間override的程式碼應該沒什麼好說的,我們來看一下最後宣告的class ViewHolder。正常來說我們在Java中的ViewHolder都是這個樣子:
public class ViewHolder extends RecyclerView.ViewHolder { public TextView textView; public ViewHolder(TextView textView) { super(textView); this.textView= textView; } } 複製程式碼
那為什麼到了Kotlin之中,就變成了短短的一行 class ViewHolder(var textView: TextView) : RecyclerView.ViewHolder(textView)
了呢?其實也沒有什麼神奇的,就是正常語法而已。 這小結開始的時候,我們提到了 主構造方法 ,以及在 匿名內部類 這個小結中提到 加上()表示顯示的呼叫這個類的構造方法。 因此Kotlin的這段程式碼非常的好理解:

就是把主構造方法中傳遞的textView,傳給RecyclerView.ViewHolder()構造方法中。也就是和我們的Java程式碼一毛一樣的,只是寫法不同罷了。
尾聲
OK,關於Kotlin在我們Android開發這些彆扭的地方就暫時寫到這。其實說白了,這些都是 最基本的語法 問題。這裡挑出來的這幾個Android的場景,是我在自以為學會語法的時候,覺得彆扭的地方。當然彆扭的原因還是因為自己對語法並不夠理解。所以才有了這篇文章,希望可以給正準備走上Kotlin這條路上的大兄弟們一些幫助吧~
我是一個應屆生,最近和朋友們維護了一個公眾號,內容是我們在從應屆生過渡到開發這一路所踩過的坑,以及我們一步步學習的記錄,如果感興趣的朋友可以關注一下,一同加油~
