阅读《Android第一行代码 第三版》的个人笔记 仅供参考
一、变量和函数
变量
两种变量关键字: val(value) 声明一个不可变的变量,对应Java中的final变量 var(variable)声明一个可变的变量,对应非final变量
val a=10 //不可变
var b=10 //可变
变量类型: Kotlin有着类型推导机制,有些情况下不需要显示的声明变量的类型,
var a: Int = 10 //显式声明变量类型
var b = 10
Kotlin数据类型 | Java数据类型 | 数据类型说明 |
---|
Int | int | 整形 | Long | long | 长整型 | Short | short | 短整型 | Float | float | 单精度浮点数 | Double | double | 双精度浮点数 | Boolean | boolean | 布尔型 | Char | char | 字符型 | Byte | byte | 字节型 |
Kotlin中的抛弃了Java中基本类型,全部使用了对象数据类型,都可以调用方法,访问属性
函数
与Java中概念基本相同,基本格式为:
fun 函数(方法)名 (参数名1: 参数类型1 , 参数名3: 参数类型2 ): 返回值类型
{
return 0//方法体
}
语法糖:当函数中只有一条代码时,可以不编写函数体,直接将唯一的一行代码写在函数定义的尾部,中间使用等号连接
//原始代码
fun largerNum(num1:Int , num2:Int ):Int {
return max(num1,num2)
}
//简化
fun largerNum(num1: Int , num2: Int ): Int = max(num1, num2)
//类型推导简化
fun largerNum(num1: Int ,num2: Int )=max(num1,num2)
二、逻辑控制
if条件语句
Kotlin的if语句与Java中的if几乎一致,但Kotlin中if语句可以有返回值,返回值为每个条件中的最后一行代码的返回值
fun largerNum(num1: Int , num2: Int):Int{
var larger = if(num1>num2){ num1 }else{ num2 }
return larger;
}
//简化
fun largerNum(num1: Int , num2: Int) = if(num1>num2) num1 else num2
when条件语句
类似于Switch,但许多不同
//基本用法
//匹配值 -> { 执行逻辑 }
fun getScore(name: String) = when(name)
{
"liu" -> 66
"li" -> 80
"yang" ->75
else -> 0
}
与if一样具有返回值 其中when语句可以传入任意类型的参数 使用 is 关键字可以进行类型匹配,相当于java中的 instanceof关键字
fun checkNumber(num: Number)=when(num)
{
is Int -> " is Int"
is Float -> "is Float"
else -> "can't identify"
}
还存在没有传入参数的用法
fun getScore (name :String ) = when {
name.startWith("Tom") -> 80
//判断字符串或对象相等可以直接使用 == 关键字
name=="Jim" -> 70
else -> 0
}
循环语句
for循环
如何表示一个区间:
val range = 0..10 // [0,10]
val range = 0 until 10 // [0,10)
val range = 10 downTo 0 // [10,0]
//step 关键字 改变区间的梯度
val range = 0 ..10 step 2
for-in 的使用:
for( i in 0 until 10 step 2)
{
println (i)
}
//结果为输出 0 2 4 6 8
三、面向对象
类与对象
创建一个类和对象
//构建一个类
class person{
var name = ""
var age = 0
fun eat(){
//...
}
}
//创建对象
val p0 = Person()
p0.name = "lzl"
继承与构造函数
Kotlin中非抽象类默认都是不可被继承的,相当于默认声明了final,想要能够被继承需要加入open关键字
//构建一个类
open class person{
var name = ""
var age = 0
fun eat(){
//...
}
}
//继承
class Student : Person(){
var sno = ""
}
//构造函数以及初始化结构体
// 注意 构造函数中已经包含了对变量sno的定义
class Student ( val sno : String ) : Person(){
init{
println("sno is" + sno)
}
}
//继承的父类如果需要传入值
open class Person (val name : String , val age : Int) {
//...
}
class Student(val sno : String , name : String , age : Int ) : Person ( name , age ) {
}
//次构造函数
class Student(val sno : String , name : String , age : Int ) : Person ( name , age ) {
constructor(name : String , age : Int ) : this ( "" , 0 , name , age ) {
}
constructor( ) : this( "" , 0 ) {
}
}
//没有主构造函数的情况
class Student : Person {
constructor(name : String , age : Int ) : super ( name , age ) {
}
}
接口
interface Study {
fun readBook()
fun doHomeWork()
}
class Student : Person,Study {
override fun readBook() { //... }
override fun doHomeWork() { //... }
}
可见性修饰符
修饰符 | Java | Kotlin |
---|
public | 所有类可见 | 所有类可见(默认) | private | 当前类可见 | 当前类可见 | protected | 当前类、子类、同一包内可见 | 当前类、子类可见 | default | 同一包路径内可见(默认) | 无 | internal | 无 | 同意模块内可见 |
数据类与单例
数据类的几个重要方法:equals()、hashCode()、toString() Kotlin构建数据类,使用data关键字,可以使用 == 、
data class CallPhone(val brand : String , val price : Double )
val call1 = CallPhone( "钛合金手机" , 8848 )
val call2 = CallPhone( "鸭梨" , 9999 )
//可以直接输出(toString)
println(call1)
//可以比较是否相同
println(call1==call2)
单列类 使用object关键字
//构建
object Single {
fun testFunction() { }
//....
}
//使用
Single.testFunction()
四、Lambda编程
lambda 可以理解为一小段可以作为参数传递的代码 { 参数名1:类型 ,参数名2:类型 -> 函数体 }
集合的创建与遍历
List
有序集合
//创建一个不可变集合
val list = listOf( "Apple" , "Banana" , "Orange" )
for ( fruit in list ) {
println( fruit )
}
//创建一个可变集合
val list = mutableListOf( "Apple" , "Banana" , "xxx" )
list.add("abab")
Set
无序,无重复值
val set = setOf(( "Apple" , "Banana" , "Orange" )
val set = mutableSetOf( "Apple" , "Banana" , "xxx" )
Map
val map = HashMap<String , Int>()
map["Apple"] = 1
map["Banana"] = 2
map["1111111"] = 11111111
//遍历
for( (fruit,number) in map)
{ //... }
集合的函数式API
maxBy() 根据传入的条件来遍历集合,找到该条件下的最大值
//获取水果名最长的水果
val maxLengthFruit = list.maxBy( { fruit : String -> fruit.length } )
//简化
val maxLengthFruit = list.maxBy{ it.length }
map() 映射函数,将集合内的每一个值按照传入的规则映射成新的值
//获得新的一个大写集合
val newlist = list.map{ it.toUpperCase }
filter() 过滤函数,按照指定条件过滤
//获取名字长度小于3的大写水果集合
val newlist = list.filter{ it.length<3 }.map{ it.toUpperCase }
any()、all() 判断是否符合条件
val reault = list.any{ it.length <=5 } //true
val result = list.all{ it.length <=5 } //false
空指针检查
Kotlin中默认所有的参数和变量都不可以为空
可空类型
声明时在类名后加上问号(?)
fun doStudy( study: Study? ) {
if(study!=null) {
//...
}
}
判空辅助工具
使用 ?. 当对象不为空时正常调用,为空时不进行操作
//if(study!=null) study.readBook();
study?.readBook()
使用 ?: 操作符两边都接收一个表达式,如果左边不为空则返回左边的结果,否则返回右边的结果
//获取文本长度,如果为空则返回0
fun getTextLength(text : String ) = text?.length ?: 0
使用 !! 断言不会为空
study!!.readBook()
使用 let 函数 将对象本身作为参数传入Lambda表达式中 处理全局对象的判空问题,if语句无法做到这一点
//如果不为空则将对象传入表达式中,调用方法
study?.let { stu ->
stu.readBook()
stu.doHomeWork()
}
杂项
字符串内嵌表达式
${ } 只有一个参数时可以省略括号{}
" hello , ${ obj.name } . nice to meet you ! "
" hello , " + obj.name + " . nice to meet you ! "
函数的默认参数值
在参数类名的后面直接赋值,即可作为默认值使用
//无默认值必须传入两个参数
fun printTest( num : Int , str : String ) { //... }
printTest( 10 , "abcd" )
//设定默认值
fun printTest( num : Int = 10 , str : String = "abcd" ) { //... }
//只用传入第一个参数
printTest( 10 )
//传入第二个参数
printTest( str = "abcd") //需要指明参数
//不按顺序传入两个参数
printTest( str = "abcd" , num =10 )
|