这篇作为一个回归和整理,作为对之前Kotlin学习的补充和备忘吧
主要分为如下几个部分进行说明:
1. 编译运行Kotline
2. IntelliJ IDEA上的一些设置
2.1. 去掉参数提示param hints
3. 基础知识
3.1. 定义main函数
3.2. 基础数据类型
3.3. 绝对等于和相对等于
3.4. 控制语句
4. 数组/集合
5. 部分库函数
1. 编译运行Kotline
Android Studio天然对kotlin做了支持,我们可以利用这个IDE在模拟器上编译/运行基于Kotline的工程,同时也可以将以有的Java代码转换为Kotlin代码,但是你会发现在Kotline工程中运行一个单独的文件,会报如下错误
如上图所示,左边是一个利用AS新建的Kotlin工程,在针对KotlinLearning.kt运行的时候,会报类无法找到的异常
那我们就通过IntelliJ来编译运行.kt文件(kotlin文件后缀名),安装过程比较简单,不赘述,在安装的时候做下配置就好,如下图
安装完成之后,会要求我们重启下电脑(添加了path重启后才生效)。
使用IntelliJ IDEA来创建一个工程看看,打开你会发现这个界面类似AS,其实AS就是基于IntelliJ IDEA做的二次开发,那么配置相关的这边就不再叙述了。下图是我新建的工程和运行结果,
2. IntelliJ IDEA上的一些设置
2.1 去掉参数提示param hints
在写代码的时候,经常会出现如下形式,这个称呼为参数提示
我们可以通过选择这个位置,选择Disable Hints选项关闭这个提示功能
3. 基础知识
3.1 定义main函数
//定义main函数,语法规范
fun main (args: Array) {
println("hello wold")
}
作为一个文件的入口main函数都有其自己的规范写法,
这里的fun表示定义一个函数,
main表示一个kt文件的入口函数,相当于java class的main函数,
括号后面跟的是函数的参数,它表示定义了一个变量args,其参数类型为Array,Array里面存放String类型的数据
当这个函数没有返回值的时候,你可以在函数的最后用 : Unit 表示 如
fun main (args: Array) : Unit
当然,你也可以不写
3.2 基础数据类型
Kotlin中,除了字符型外,其数据类型和Java保持一致,其基本数据类型有:
Double,Float,Long,Int,Short,Byte
Kotlin中,字符型使用Char表示,其值需要用单引号扩起来;但是其有别于Java,其不能被直接看成数据
如下代码就会报错
fun checkChar(c: Char) {
if (c == 97)
}
Kotlin中,也存在和java类似的自动装箱和拆箱的概念,即较小值不能隐式转换为较大的值,这里需要通过显示转换的方法完整,如调用toInt将一个字符型转为整形
3.3 绝对等于和相对等于
Kotlin中,绝对等于和相对等于就类似java当中的==和equal,其中绝对等于表示两个变量的地址相同,并且其内容也相同,使用三个 === 表示;而相对等于则只要两个变量的内容相同即可,使用两个等好 == 表示; 同时Kotlin中,也有equal方法,也是表示对比变量内容
fun checkEqual (){
var str1 = "china"
var str2 = "china"
println(str1 == str2)
println(str1.equals(str2))
}
其输出分别为:
true, true
3.4. 控制语句
Kotlin中,语句和java类似,也分为条件语句,循环预计;只不过在kotlin中,封装了几个内置函数,这样就使得这些语句写起来更加的简洁
Kotlin中条件语句可以将计算结果直接付给一个变量,这个特性就直接取代了java当中的三元运算符;如下
fun controlSentence (a: Int, b: Int) {
var number = if (a > b) a else b
}
Kotlin中循环语句和java一致,通过for语句,do…while, while语句来进行循环,同时break,continue和return的含义和java保持一致;另外在kotlin中有一种用法也可以帮助跳出循环:即在标签处返回,这点和java的goto标签是一致的,不过我不太鼓励使用通过标签来跳出循环,因为这样的代码可读性真的很糟糕;
这里就简单说下在标签处返回的用法,标签一般搭配break,continue或者return来使用,其写法是在表达式后面紧跟分号,并且标签和break,continue之间是没有空格的,示例代码如下:
public fun showLabel() {
var time: String = "2019"
loop@ for (i in 1..4 {
print("showLabel开始循环**")
if (i === 1) time = "2020";break@loop
print("showLabel开始循环2**")
}
}
第5行,当 i 决定等于1的时候, 跳出循环,跳转到定义loop标签的位置,
其输出为:
showLabel开始循环**
我们再来看下for语句,对于任何一个有迭代器的集合,我们都可以使用in函数来达到快速循环的目的,代码如下:
public fun oToneList() {
var array = listOf("china", "china", "china")
for (i in array.indices) {
print(array[i])
}
}
4. 数组/集合
创建一个数组常见方法有
var array = arrayOf("hello","2",3,4,5);
var intArray = arrayOfNulls(5);
var emptyArray = emptyArray();
var charArray = charArrayOf('h', 'e', 'l', 'l', 'o');
还有如下的数组类型:ByteArray、ShortArray、IntArray、LongArray、CharArray、FloatArray、DoubleArray、BooleanArray,分别用于映射Java的byte[]、short[]、int[]、long[]、char[]、float[]、double[]、boolean[]这8种基本类型的数组。
数组API简介
for (index in array.indices) {
print("字符串下标:$index **");
}
var array = arrayOf("hello","2",3,4,5);
for ((index, value) in array.withIndex()) {
println("索引为${index}的元素是:${value}")
}
var array = arrayOf(3,4,5);
// 如果数组中每一个元素都大于2则返回true
array.all {it > 2} // 这里的it可以直接理解为item
// 如果数组中每一个元素的平方都大于20
array.all { it * it > 20 }
多维数组: 故名思议就是数组中的元素也是数组
//创建一维数组multiArray,其长度为4
//multiArray数组的元素是Array类型
var multiArray = arrayOfNulls>(4)
先看下类图
集合分为不可变集合和可变集合,不可变即可只读不可写,可变集合可读可写,即可以通过add,remove方法操作集合。可以看出list,set, map都是已接口的形式存在,它不能直接实例化,我们可以通过库函数来创建对应的实例
不可变集合
- listOf: 返回list类型(有序可重复)
- setof: 返回set类型(其和list不同的是set会去除重复的数据且无序)
- mapOf: 返回map类型(已key,value的形式存在,key和value用to来衔接)
// 由list本身判断数据类型
var immutableList = listOf(1,2,"3",4,"5")
// 指定数据类型为String
var immutableList2 = listOf("1","2","3","4","5")
var set1 = setOf(1,2,"3","4","2",1,2,3,4,5)
val map1 = mapOf("key1" to 2 , "key2" to 3)
可变集合
- mutableListOf: 返回list类型
- mutableSetOf: 返回set类型
- mutableMapOf: 返回map类型
var immutableList3 = mutableListOf(1,2,"3",4,"5")
var immutableList4 = mutableListOf("1","2","3","4","5")
var set1 = mutableSetOf(1,2,"3","4","2",1,2,3,4,5)
val mutableMap = mutableMapOf("key1" to 2 , "key1" to 3)
5. 部分库函数
for (index in 0 .. 10){
print(index)
}
// 输出为0 1 2 3 4 5 6 7 8 9 10
var list = listOf("a","b","c")
for (i in list){
print(i)
}
// 输出为 a b c
for (index in 0 until 10){
print(index)
}
// 输出为0 1 2 3 4 5 6 7 8 9
for (index in 10 downTo 0) {
print(index)
}
// 输出为0 1 2 3 4 5 6 7 8 9 10
for (index in 0 .. 10 step 2){
print(index)
}
// 输出为0 2 4 6 8 10
var list = listOf("a","b","c")
for (index in list.indices){
print("$index")
}
// 输出为 0 1 2
var list = listOf("a","b","c")
for ((index,value) in list.withIndex()){
print("$index:$value ")
}
// 输出为0:a 1:b 2:c
作用域函数的作用是 Kotlin 标准库(Standard.kt)的函数,其唯一目的是在对象的上下文中执行代码块。 其基本语法格式为:
Object.作用域函数{
}
var hello1: String = "hello"
var result1 = hello1.let {
println(it.length);
1000;
}
println(hello1);
println("let演示$result1");
// 输出为 5
// 输出为 hello
// 输出为 let演示1000
var hello: String = "hello"
val result =hello.apply {
println(this)
this + "world";
}
println("apply演示$result");
// 输出为 hello
// 输出为 apply演示 hello
var hello2: String = "hello"
val result2 = hello2.run {
println(this)
this + "world";
"run函数返回最后一行"
}
println("run函数演示$result2");
// 输出为 hello
// 输出为 run函数返回最后一行
var hello3 = listOf<String>("1","2","3","4","5")
var result3 = with(hello3) {
println(hello3[0]);
hello3;
1000;
}
println(result3);
println("with函数演示$result3");
// 输出为 1
// 输出为 1000
// 输出为 with函数演示1000
var hello5 = listOf<String>("1","2","3","4","5")
var result5 = hello5.takeUnless {
it.size > 3
}
println(result5);
// 输出为 null
repeat(9) {
println(it);
}
// 输出为 0 1 2 3 4 5 6 7 8
var hello4 = listOf<String>("1","2","3","4","5")
var result4 = hello4.takeIf {
it.size > 3
}
println(result4);
// 输出为 [1, 2, 3, 4, 5]
var hello7: String = "hello"
var result7 = hello7.also {
println(it.length);
it.reversed();
1000;
}
println(hello7);
println("also演示$result7");
// 输出为 5
// 输出为 hello
// 输出为 also演示hello