您好,登錄后才能下訂單哦!
Kotlin基礎教程之Run,標簽Label,函數Function-Type
在Java中可以使用{}建立一個匿名的代碼塊,代碼塊會被正常的執行,除了改變了作用域之外,似乎并沒有什么其他的作用。然而在Kotlin中卻不能這么做,這是為什么呢?
其實,我們都知道一個函數一定與一個內存地址相關,而一個匿名的代碼塊其實也相當于是一個匿名的函數。在Kotlin中一般使用run函數來運行一段匿名代碼塊。
如下:
在Kotlin中使用標識符后跟@符號來定義一個標簽,使用@后跟標識符來引用一個標簽,run函數的語法初看起來似有一些怪異,其實run函數以一個函數作為參數,而一個匿名的代碼塊就可以是一個匿名函數,當我們在IntelliJ IDEA中把鼠標光標放到匿名代碼塊的大括號上時,會顯示出匿名代碼塊對應的函數簽名
local final fun <anonymous> ():Int defined in com.kotlin_learn.control_flow.fun_run
如圖:
local代表作用域,定義在函數內部,作用域僅為local,final代表不可變,<anonymous>即為匿名,()是參數列表,Int是返回值,com.kotlin_learn.control_flow.fun_run是函數定義位置的完整路徑。
由此可見,run函數的參數,那段匿名代碼塊被編譯器轉換為了一個匿名函數是毫無疑問的。
當然run函數是可以有返回值的,所以匿名代碼塊也可以是有返回值的匿名函數。
每一個函數都與一個或多個地址相對應,而每一個標簽Label也是與一個或多個地址相對應,所以函數本身即是標簽。
所以可以使用return@run之類的語法。
匿名函數雖然沒有函數名,然而我們可以定義一個具名標簽來代表這個函數,于是可以使用return@outer 2將2返回給i。
也許有人會有疑問,為什么不直接使用return 2呢,原因是return 將會從fun_run函數返回,而不是從匿名函數返回。
關于return和函數嵌套定義的問題下面還會說。
這段代碼的運行結果如下:
接下來說一說forEach函數,與其他語言中不同,在Kotlin中forEach并不是一種語法,而是一類函數,forEach是iterator的函數,任何實現了iterator的類都可以使用forEach。forEach函數的參數也是一個函數,其參數是一個模板函數,可以是具名函數,匿名函數,lambda。forEach會對iterator迭代的每一個元素都調用一次傳入的函數。
之所以講到forEach,是為了熟悉標簽的用法和return的用法。
如下:
別忘了infix function call。
運行結果如下:
接下來說一說function type,討論一下函數。
對程序員來說,函數是很熟悉的,然而我們對函數就真的那么熟悉么?
函數也可以是類型,可以是變量,甚至常量。
如下:
在這段代碼中我們定義了幾個函數類型的變量和常量,并且在之間進行賦值等操作,其實和C++中的函數指針很相似,但是也有獨特的地方。比如嵌套函數定義,函數標簽的引用以及帶標簽的返回值等等。我們也看到了在一個匿名函數(end1代表的那個)中如何使用lambda表達式定義函數的參數列表和自動判斷的返回類型。
這段代碼運行結果如下:
剛才我們提到了函數嵌套定義,這是一個需要小心的地方。
看如下的代碼:
從Java/C++一系出身的程序員(比如我:))很容易把這里的嵌套函數定義看成是匿名代碼塊的嵌套,以為程序會從外往內執行。從Pascal/PL一系出身的程序員就不會有這種問題,千萬記住,函數雖然可以嵌套定義,但是如果沒有調用是不會從外向內執行的。
所以輸出很簡單:
我們也看到了return的用法,這里的f1,f2,f3雖然是內部定義的函數,但是依然可以作為標簽使用。
可見Kotlin是一種集大成的語言,甚至借鑒了古老的unix腳本和Pascal的語法,借鑒了很多語言的特性,再加上強大的編譯器(Kotlin編譯器會幫你做很多東西,遠比其他語言做的多得多),使Kotlin的代碼非常簡潔優雅而且編程相當靈活高效。
在Kotlin中,太多的功能都是通過使用函數作為參數來實現,有的已經不能叫做語法,然而函數嵌套,infix function call,lambda,函數參數,可變參數列表,靈活的標簽,強大的return,自動類型判斷,Range,iterator,操作符重載,省略,模板...這些太多的功能,導致Kotlin的語法眼花繚亂,雖然有時看起來很優雅,但是也可能給人閱讀代碼帶來巨大的困難。
最后以一段沒什么卵用的代碼結束本篇。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。