分享

Kotlin学习笔记(二):变量与函数

 dxw121 2017-07-21


之前文章起名为Kotlin教程,后来想想可能不大合适,决定改为Kotlin学习笔记。上一篇文章发布后,有几个读者留言问在没有学Java的情况下,直接学Kotlin行不行?我认为是没有问题的。好了,上一篇文章已经简单了解Kotlin的一些特色,后面也用Kotlin写了一个最简单的HelloWorld,如果还不大清楚的朋友,可以先阅读上一篇文章:Kotlin学习笔记(一):走进Kotlin的世界。

包名

Kotlin在包名声明和类型导入上和Java基本一样,风格如下:

package xxx.xxx.xxx //包名声明

import xxx.xxx.xxx //类型导入
...

和每个Java文件都会默认导入import java.lang.* 一样,Kotlin也会默认导入如下的包,并且根据运行在不同平台上,默认导入的包会有些许差异。

// 每个Kotlin文件会默认导入下面的包 kotlin.* kotlin.annotation.* kotlin.collections.* kotlin.comparisons.* kotlin.io.* kotlin.ranges.* kotlin.sequences.* kotlin.text.* // JVM下的Kotlin还会导入 java.lang.* kotlin.jvm.* // JS下的Kotlin还会导入 kotlin.js.*

数值类型

Kotlin的数值类型包括Byte(1个字节)、Short(2个字节)、Int(4个字节)、Long(8个字节)、Float(4个字节)、Double(8个字节)。

字面常量

  • 十进制数:123

  • 长整型要加L:123L

  • 十六进制数:0x0f

  • 二进制数:0b00001011

  • Kotlin不支持八进制数

  • 双精度浮点数(Double):123.5 、 123.5e10

  • 单精度浮点数(Float)要加f或F:123.5f

Kotlin1.1版本开始,可以使用下划线来增强可读性

val oneMillion = 1_000_000 val creditCardNumber = 1234_5678_9012_3456L val socialSecurityNumber = 999_99_9999L val hexBytes = 0xFF_EC_DE_5E val bytes = 0b11010010_01101001_10010100_10010010

布尔值

关键字Boolean,只有true和false两种取值,和Java一样可以使用&&||!进行与或非操作。

运算符

Kotlin支持标准的算数操作符,同时也支持下面各种位运算

  • shl(bits) – 有符号左移(signed shift left,相当于Java的<<)

  • shr(bits) – 有符号右移(signed shift right,相当于Java的>>)

  • ushr(bits) – 无符号右移(unsigned shift right,相当于Java的>>>)

  • and(bits) – 按位与(bitwise and,相当于Java的&)

  • or(bits) – 按位或(bitwise or,相当于Java的|)

  • xor(bits) – 按位异或(bitwise xor,相当于Java的^)

  • inv() – 按位取反(bitwise inversion,相当于Java的~)

以上这些位运算符只对Int和Long型有用。

var x = (1 shl 2) and 0x000FF000 var y = 0x000FF000 var z = y.inv() //z是y取反获得的

字符

关键字Char,和Java中char基本用法差别不大。

var useChar: Char = 'c'

数组

关键字Array,Kotlin中数组的使用和Java差别挺大,比如我要创建数组,就得使用arrayOf

//使用arrayOf简单创建数组 var students: Array<String> = arrayOf('Clock', 'D_clock', '技术视界') var studentNums = arrayOf(1, 2, 3)

使用arrayOfNulls可以创建一个指定长度,元素内容为空的数组

//创一个长度为10,元素内容皆为null的数组 var emptyArray = arrayOfNulls<String>(10)

Kotlin对一些基础类型定义数组会有拆装箱的开销,所以也可以使用自身封装好的一些API进行创建数组,以降低开销

//创建一个int数组,避免封箱装箱操作 var intArray = intArrayOf(1, 2, 3)

Kotlin数组还支持使用闭包进行初始化,就像下面这样

//使用闭包初始化一个Array<String>,数组内容为['0', '1', '4', '9', '16'] var asc = Array(5, { i -> (i * i).toString() })

字符串

关键字String,用法和Java差别不大。

var useString: String = 'I am a boy' var firstChar: Char = useString[0] //相当于Java的String.charAt(0)

Kotlin的同样支持字符串模板,但是相比Java的String.format要简洁很多。比如:

var nickname: String = 'D_clock爱吃葱花' println('my nickname is $nickname')//输出昵称 println('nickname length: ${nickname.length}')//输出昵称的长度

定义变量

Kotlin的变量分为可变和不可变,和Java中是否对变量声明final一样,它定义一个变量的语法如下:

可变类型 变量名:数据类型
  • 可变类型分为var、val两种,分别代表可变、不可变;

  • 数据类型包括Kotlin内置的数据类型以及自定义类deng ;

  • 定义变量时需要明确数据类型;

对照Kotlin和Java给出一段简单的示例代码

/***Kotlin版代码***/ //定义可变变量 var id: Int = 1 // var name: String = 'D_clock爱吃葱花' //定义不可变变量 val useVal: Int = 1000 /***Java版代码***/ int id = 1; String name = 'D_clock爱吃葱花'; final int useFinal = 1000;

Kotlin是支持类型推导,在定义变量时可以不显式声明类型,而通过赋值来确定变量类型。因此,定义变量的代码也可以写成下面这样

//类型推导 var tmpId = 1 var tmpName = 'D_clock爱吃葱花'

定义函数

Kotlin定义一个函数的风格大致如下

访问控制符 fun 方法名(参数,参数,参数) : 返回值类型{    ...    ... }
  • 访问控制符:与Java有点差异,Kotlin的访问范围从大到小分别是public、internal、protected、private,不声明默认是public;

  • 返回值类型:不需要返回类型的函数,后面的 : 返回值类型可以缺省(这里可以看到无论是变量还是方法,Kotlin都喜欢名字在前,类型在后);

/***Kotlin版代码***/ //有返回参数的函数 fun getName(): String {    return 'Kotlin' } //无返回参数的函数 fun displayName(name: String) {    println('name: $name') } /***Java版代码***/ public String getName() {    return 'Java'; } public void displayName(String name) {    System.out.println('name: ' name); }

相比Java,Kotlin支持包级函数,即函数不依赖于类而存在。

/***Kotlin版代码***/ package lesson1 /** * Created by Clock on 2017/6/18. */ fun main(args: Array<String>) {    println('Kotlin') } /***Java版代码***/ package lesson1; /** * Created by Clock on 2017/6/18. */ public class Lesson1 {    public static void main(String[] args) {        System.out.println('Java');    } }

对比上面的代码,Java创建一个方法前还需要先创建一个类。刚开始安装IntelliJ IDEA编写代码时,我还有个疑惑,为什么有创建Kotlin File/Class两个选择,到这里就明白了。

参数变长

Kotlin的参数变长非常简单,传递的参数使用关键字vararg标明即可

/***Kotlin版代码***/ //参数变长 fun displayActors(vararg name: String) {    println('actors: ' name); } /***Java版代码***/ public void displayActors(String... name) {    System.out.println('actors :' name); }

相比Java,变长参数在Kotlin代码中要常见很多。

静态变量和函数

Kotlin没有Java中的static概念,如果在Kotlin中需要像Java一样定义静态变量和函数可以使用companion object,companion object后可以加上自定义的object名,也可以省略。

/***Kotlin版代码***/ class KotlinStatic {    companion object Test {        var kotlinInt: Int = 0        fun getInstance(): KotlinStatic {            return KotlinStatic()        }    } } /***Java版代码***/ public class Lesson1 {    public static int javaInt = 0;    public static Lesson1 getInstance() {        return new Lesson1();    } }

这样在需要使用的地方就可以做如下调用了

package lesson0 import lesson1.KotlinStatic /** * Created by Clock on 2017/6/17. */ fun main(args: Array<String>) {    println('Hello, world!')    KotlinStatic.kotlinInt    KotlinStatic.getInstance() }

虽然看起来companion object实现了类似Java中static一样的功能,但与Java不同的是,Kotlin在运行时是会创建一个companion object实例对象。在Kotlin中,如果真的想要实现和Java中的static变量或函数,官方更推荐使用包级别的变量或函数来实现。

If表达式(语句)

Kotlin中的If不同于Java,它是不仅能够作为一个判断语句,而且还是一个表达式,即执行If判断是有返回值的。

fun useIf() {    //使用If表达式判断a、b的大小    var a = 5    var b = 3    var result = if (a > b) {        println('a > b')        true //返回结果    } else {        println('a <= b')        false    }    println('result: $result') }

If表达式里每个条件代码块中的最后一行执行语句即为返回值,相当于Java中的三元运算符:条件 ? 然后 : 否则,所以在把If当成表达式使用时必须有else分支,这样在逻辑上才能保证最终一定有返回值,否则会报语法错误。

When表达式(语句)

Kotlin中的When和If一样,既可以作为语句,也可以作为表达式,在作为语句时,它相当于Java中的switch。下面是对传入的参数input做一个判断

fun useWhen(input: Int) {    var result = when (input) {        //判断input是否为1        1 -> println('input == 1')        //判断input是否为2        2 -> {            println('input == 2')        }        //input是否在10到20的范围内        in 10..20 -> println('input number in the range')        //input是否不在20到30的范围内        !in 20..30 -> println('input number outside the range')        else -> { //When作为表达式使用时,最后一定要以else            println('input: $input')        }    }    println('result: $result') }

从上面的代码看,你会发现它比Java的switch灵活多了。这里只是使用When语句,如果要使用When表达式,则应该If表达式一样,最终一定要以else结尾。

For循环

for循环能够对任何提供迭代器(iterator)的对象进行遍历,语法格式如下:

for (item in collection){    //代码块    ... }

和Java有区别,但是也非常简单,Kotlin中的for更类似Java中的增强for循环。

fun useFor() {    val students: Array<String> = arrayOf('Clock', 'D_clock', '技术视界')    for (student in students) {//输出学生名字        println('student: $student')    }    for ((index, student) in students.withIndex()) {//输出学生的下标和名字        println('the element at $index is $student')    } }

While循环

Kotlin中的white(){}和do{}while()和Java差不多,这里不多做赘述。

fun useWhile() {    var counter = 10    while (counter > 0) {        counter--        println('counter: $counter')    }    do {        counter        println('counter: $counter')    } while (counter < 10) }

返回和跳转

Kotlin和Java一样有下面三种跳转表达式

  • continue:跳过这一次循环

  • break:终止包裹它的循环

  • return:从包裹它的函数或者匿名函数中返回

以上三种跳转都支持跳转到指定的标签处。标签的使用方式也简单,使用@在对应的循环或者匿名函数做标记即可,就像下方的示例代码一样

fun useJump() {    val numbers = arrayOf(1, 2, 3, 4, 5)    val numbers2 = arrayOf(1, 3, 5, 7, 9)    //设置testLab标签名    testLab@ for (num in numbers) {        println('num: $num')        for (num2 in numbers2) {            if (num == 3) {               break@testLab//直接中断标签指定的整个循环            }        }    } }

总结

以上是本文整理的Kotlin一些基础语法笔记,如果有错误疏漏,欢迎指正。

    本站是提供个人知识管理的网络存储空间,所有内容均由用户发布,不代表本站观点。请注意甄别内容中的联系方式、诱导购买等信息,谨防诈骗。如发现有害或侵权内容,请点击一键举报。
    转藏 分享 献花(0

    0条评论

    发表

    请遵守用户 评论公约

    类似文章 更多