资讯详情

Android kotlin基本语法

1.kotlin变量

①可变量:使用var关键词表示可读可写

可读可写 变量名 : 类型= 初始化值

var text : String = "hello world"

var可重新赋值关键字的变量:

text = "hi"

②不可变量:使用val关键词意味着只读,只能赋值一次

只读 变量名 : 类型= 初始化值

val text : String = "hello world"

val不能重新赋值关键字的变量。

变量和常量都没有初始化值,但需要注意的是,当声明的变量或常量作为类别的全局使用时,必须进行初始化操作,否则会报错,而函数中不必要。

f8c212a2cee94143bd7775ae8a7d37c4.webp

类型推断:

在Java声明变量或常量需要明确告知所属类型,但在kotlin中间不需要显示,可以交给编译判断:

var x = 5 // 系统自动推断变量类型Int

③const关键词(编译时间常量)

在Kotlin中通过val只有定义的变量get方法,没有set方法,只能读不能写。但是其get方法可以复写,从而造成val定义的变量可能会发生值变化。这时候就需要采用const关键字。在Kotlin中除了val除了定义常量,关键字还提供了一个const标记常量的关键字。const修饰的val变量相当于java中static final,是真正意义上的java常量。

(1)不能直接用于实际编码const val,而必须写在companion object代码块里:

//companion object类似于Java的static

companion object {

const val C : Int = 0

}

(2)const关键词不能修改局部变量

const它是编译常量,因此不能定义为函数内部的局部变量。如果在函数内部定义,则必须在运行过程中调用函数赋值,则不能称为编译常量。因此,编译常量只能在函数之外定义,在编译过程中可以初始化。

④range 区间

range表达式由操作符形式组成 .. 的rangeTo函数辅以 in 和 !in 形成。

for (i in 1..4) print(i) // 输出“1234”

for (i in 4..1) print(i) // 什么都不输出,因为它在使用in必须确保前面的数字小于后面的数字

if (i in 1..10) { // 等同于 1 <= i && i <= 10

println(i)

}

if (i !in 1..10) { // 等同于 i<1 ||i >10

println(i)

}

// 使用 step 指定步长

for (i in 1..4 step 2) print(i) // 输出“13”

for (i in 4 downTo 1 step 2) print(i) // 输出“42”

// 使用until函数排除结束元素

for (i in 1 until 10) { // i in [1, 10) 排除了 10

println(i)

}

注意:使用 ../downTo使用包括前后,包括前后until只包括前不包括后。

2.when表达式

when将它的参数和所有的分支条件顺序比较,直到某个分支满足条件。

when它可以用作表达式(返回值)或句子。如果用作表达式,合格分支的值为整个表达式值,如果用作句子, 忽略个别分支的值。

when 类似java语言的switch操作符。

when以表达式为例:

val week = 2

val info = when (week) {

1 -> "今天星期一"

2 -> "今天星期二"

else ->"不是星期一,不是星期二"

}

相比较Java的switch而言,when更强大的是,它不仅能满足同一类型的条件判断,还能满足各种类型的判断:

when (x) {

in 1..10 -> print("x is in the range")

in validNumbers -> print("x is valid")

!in 10..20 -> print("x is outside the range")

else -> print("none of the above")

}

3.字符串模板

①$varName 表示变量值

val garden = "海洋公园"

val time = 6

println("今天我去${garden}玩了$time 小时")

注:如果$后面跟着文字,需要用{}$不跟文字(多一个空间)就可以不用{}

②${表达式} 表示表达式返回值

val isLogin = false

println("服务器返回值:${if(isLogin) "登录成功" else "登录失败"}"

4.函数

修饰符(默认为public) fun关键字 函数名(参数名: 参数类型) : 函数返回值类型 {}

private fun methodName(age: Int, name: String):Int {

}

①具有返回值的函数

fun sum(a: Int, b: Int): Int {

return a b

}

②无返回值函数

fun printSum(a: Int, b: Int): Unit {

print(a b)

}

Unit不能写,系统默认是Unit。Unit相当于Java里的void。

所以上面的例子也可以写成:

fun printSum(a: Int, b: Int) {

print(a b)

}

③可变长参数函数 vararg

fun vars(vararg v:Int){

for(vt in v){

print(vt)

}

}

// 测试

fun main(args: Array<String>) {

vars(一、二、三、四、五) // 输出12345

}

④默认参数为函数参数

private fun getStu(name: String, age: Int = 18) {

println("她的名字是$name, 年龄是$age")

}

注意这种方法有两个参数,其中第二个是默认值。此时,该方法可以输入两个参数或一个参数(第二个参数使用默认值)。

getStu("lili", 15)

输出:她的名字是lili, 年龄是15

getStu("lili")

输出:她的名字是lili, 年龄是18

⑤具名函数参数

例如,有一个参数特别多的函数:

private fun getStu(name: String, age: Int, sex: String, phone: String, pwd: String, score: Int, job: String, address: String) {

}

由于参数特别多,在使用该函数时,需要根据参数顺序逐一传输。此时,可以使用具名函数参数,因此无需考虑参数的顺序:

getStu(age = 15, job = "doctor", phone = "15132458765", score = 99, address = "eijing", name = "lili", sex = "girl", pwd = "123")

 

5.匿名函数

匿名函数的完整格式为:

修饰符 函数名: (参数类型,参数类型) -> 返回值类型 = {参数名,参数名 -> 函数实现}

举例:

fun main(args: Array<String>) {

    val sum: (Int, Int) -> Int = {x,y -> x+y}

    println(sum(1,2)) // 输出 3

}

其中val sum: (Int, Int) -> Int = {x,y -> x+y}就是匿名函数,它等价于:

fun sum(x: Int, y: Int): Int {

    return x + y

}

匿名函数还可以分开写:

fun main(args: Array<String>) {

    //第一步:函数输入输出的声明

    val sum: (Int, Int) -> Int

    //第二步:对上面函数的实现,在实现里,最后一行语句代表函数的返回值,但是不能写return关键字

    sum = {x,y ->

        x - y

        x+y  //这个才是返回值

    }

    //第三步:调用此函数

    println(sum(1,2)) // 输出 3

}

注意:

(1)匿名函数不要写return,最后一行就是返回值(隐式返回)。

(2)调用匿名函数时,可以用sum(1,2) 或者 sum.invoke(1,2)。

(3)匿名函数的函数名前面为什用val,而不是fun?匿名函数是没有函数名的,这里的函数名指的是这个匿名函数的返回值,是一个变量,所以用val。

①it关键字

在匿名函数里,如果只有一个参数,则不用显示声明参数,可以用it代替。参数多于一个时,不能使用it。

举例:

val text: (String) -> String = { "hello, $it "}

println(text("lili")) //输出 hello,lili

②匿名函数的类型推断

在匿名函数里,如果匿名函数名后面使用“:”的话,返回值的类型必须显示指定出来:

val sum: (Int, Int) -> Int = {x,y -> x+y}

此时可以使用“=”,则不用显示指明返回值的类型了,会自动推断返回类型。

使用格式为:

修饰符 函数名 = {参数名: 参数类型, 参数名: 参数类型 -> 函数实现}

举例:

val sum = {x: Int, y: Int -> x + y}

同样,{}里面最后一行是返回值。系统会根据最后一行判断返回类型的。

 

6.参数是函数的函数

fun login(name: String, pwd: String, responseResult: (String, Int) -> Unit) {

    if(name == "aqw" && pwd == "1234") {

        responseResult("success", 200)

    } else {

        responseResult("fail", 404)

    }

}

login方法一共有三个参数,其中第三个参数是一个匿名函数的形式,这个匿名函数有两个参数,并且没有返回值。

调用login方法有三种方式:

1)login("aqw", "1234") { msg: String, code: Int -> 

    println("最终登录情况为:msg:$msg, code:$code")

}

2)login("aqw", "1234", { msg: String, code: Int -> 

    println("最终登录情况为:msg:$msg, code:$code")

})

3)login("aqw", "1234"), responseResult = { msg: String, code: Int -> 

    println("最终登录情况为:msg:$msg, code:$code")

})

 

7.内联函数inline

当函数中使用lambda作为参数时,需要声明为内联。如果不使用内联,在调用端会生成多个对象来完成lambda的调用,从而完成性能损耗。

使用内联,相当于c++里的#define宏定义,会把代码替换到调用处,调用处没有任何函数开辟、对象开辟的损耗。

inline fun login(name: String, pwd: String, responseResult: (String, Int) -> Unit) {

    if(name == "aqw" && pwd == "1234") {

        responseResult("success", 200)

    } else {

        responseResult("fail", 404)

    }

}

所以,如果函数参数有lambda,尽量使用inline内联关键字,这样内部会做优化,减少函数开辟、对象开辟的损耗。

 

8.函数引用::

假设现在有一个函数,它的一个参数是lambda(比如上边的login函数),此时还有一个函数:

fun methodName(msg: String, code: Int) {

    println("结果是: msg:$msg, code: $code")

}

现在要把methodName这个函数当做login的第三个参数传进去,因为lambda属于函数类型的对望,所以这里不能直接传函数进入,就需要用到函数引用了:

login("aqw", "1234", ::methodName)

或者

val obj = ::methodName

login("aqw", "1234", obj)

这里函数引用相当于把普通函数变成了函数类型的对象。

 

9.函数类型作为返回值

一个函数,它的返回值还可以是一个函数:

fun methodName(info: String): (String, Int) -> String {

    println("info: $info")

    return { name: String, age: Int ->

        "我是返回值函数 name: $name, age: $age"

    }

}

methodName是一个函数,它的参数是String,返回值是一个函数,返回值函数的参数是String,Int,返回值函数的返回值是String。

methodName的调用方式为:

val returnMethod = methodName("hello")

val value = returnMethod("lili", 18)

println("value:$value")

 

10.NULL检查机制

①kotlin变量默认是不可空类型,不能随意赋值为null。

举例:

var text: String = "hello"

text = null  报错,提示不能给非空变量赋值为null

②要想使用null,可以在变量声明的时候指定为可空类型:

var text: String? = "hello"

text = null

③kotlin的空安全设计

对于声明可为空的参数,在使用时候要进行空判断处理,处理的方式有两种: (1)使用非空断言操作符,字段后加!!像Java一样抛出异常。

var age: String? = "23"  //age声明为可空类型

val ages = age!!.toInt() //不管age是不是null都会执行toInt(),和java一样,抛出空指针异常。

注:如果百分百能够保证age是有值的,才可以使用!!断言,否则会有java空指针异常的风险。

(2)字段后加?在值为空的时候不做处理直接返回null或者配合?:做空判断处理。

var age: String? = "23"  //age声明为可空类型

age.toInt() //报错,因为age为可空类型,即age可能为null,要想使用age,需要给出补救措施

val ages1 = age?.toInt() //补救措施一:age是可空类型,如果age真的是null,?后面这一段代码不执行,所以不会引发空指针异常 ,返回null

val ages2 = age?.toInt() ?: -1 //补救措施二:age为空返回-1

(3)使用带let的安全调用

var age: String? = "23"  //age声明为可空类型

age?.let {

}

let可以把age拿进{}里面来使用,在{}里面默认有一个it,$it的值就是age的值。如果age真的是null,则{}里面的代码不会执行,也就是说,只要执行到{}里,$it肯定不是null。

(4)使用if判断null值,和java一样

var age: String? = "23"

if(age != null) {

    val ages = age.toInt()

} else {

    ……

}

(5)空合并操作符 ?:

var age: String? = "23"

println(age ?: "age是null") //如果age是null,则会输出?:后面的语句(age是null),否则输出age本身的值(23)

 

6.类型检测及自动类型转换

可以使用is运算符检测一个表达式是否某类型的一个实例(类似于Java中的instanceof关键字)。

fun getStringLength(obj: Any): Int? {

    if (obj is String) {

        // 做过类型判断以后,obj会被系统自动转换为String类型

        return obj.length 

    }

}

7.基本数据类型

kotlin的基本数值类型包括Byte、Short、Int、Long、Float、Double 等。不同于Java的是,字符不属于数值类型,是一个独立的数据类型。

Kotlin中没有基础数据类型,只有封装的数字类型,每定义一个变量,Kotlin都封装了一个对象,这样可以保证不会出现空指针。数字类型也一样,所以在比较两个数字的时候,就有比较数据大小和比较两个对象是否相同的区别了。在 Kotlin 中,三个等号 === 表示比较对象地址,两个 == 表示比较两个值大小。

fun main(args: Array<String>) {

    val a: Int = 10000

    println(a === a) // true,值相等,对象地址相等

    //经过了装箱,创建了两个不同的对象

    val boxedA: Int? = a

    val anotherBoxedA: Int? = a 

   //虽然经过了装箱,但值是相等的,都是10000

    println(boxedA === anotherBoxedA) // false,值相等,对象地址不一样

    println(boxedA == anotherBoxedA) // true,值相等

}

 

8.位操作符

对于Int和Long类型,还有一系列的位操作符可以使用,分别是:

shl(bits) – 左移位 (Java’s <<)

shr(bits) – 右移位 (Java’s >>)

ushr(bits) – 无符号右移位 (Java’s >>>)

and(bits) – 与

or(bits) – 或

xor(bits) – 异或

inv() – 反向

 

 

 

 

 

 

 

 

 

 

 

 

 

标签: 继电器aqw215a

锐单商城拥有海量元器件数据手册IC替代型号,打造 电子元器件IC百科大全!

锐单商城 - 一站式电子元器件采购平台