注:编码工具为IntelliJ
目录
为什么要学习Kotlin?
我本身是Android开发工程师,Kotlin被Google宣布为Android第一开发语言,主要是为了避免诉讼问题,Oracle近年来因为Android未经授权使用JavaAPI对Google提起了多场诉讼,Google饱受侵权困扰。
Android后续新技术如jetpack越来越多的使用kotlin作为主要开发语言,为了跟上时代。
国外越来越多的开发者和三方库使用kotlin进行开发。
Kotlin是全栈语言,它不仅能用来开发Android应用,还可以开发前端、Web应用甚至iOS应用。
Kotlin具有比Java更好的跨平台性,它可以直接生成对应操作系统平台的二进制编码执行,包括Windows、Linux、MacOS。。。
Java会被Android彻底舍弃吗?
大概率不会,因为Android多个版本的Framework层源码都是用Java开发的,Google不太可能将源码用Kotlin再写一遍。
变量声明
Kotlin用var和val关键字声明变量,其中var声明的变量既可读也可改,而val声明的变量则是只读的。如果修改了val声明的变量,则在编译器IDE就会报错。
注意:Kotlin代码中,语句最后的分号是可选的。
Kotlin声明变量格式:var/val 变量名 : 数据类型 = 变量值
小技巧:IntelliJ中可以使用 变量名.sout 的方式快捷打出打印语句println(变量名)。
fun main() {
var num = 188
num = 96
println(num)
val num2 = 188
// num2 = 96 只读变量,不可修改
println(num2)
}
输出:
96
188
内置数据类型
Kotlin中一切都是对象,没有基本数据类型一说,它将Java中的基本数据类型都封装成对应的类。当然,在编译以后,会将封装对象转换成Java的基本数据类型。
Kotlin代码:文件名为BuiltInType.kt
fun main() {
val c: Char = '0'
val b: Byte = 1
val s: Short = 2
val i: Int = 3
val l: Long = 4
val f: Float = 5f
val d: Double = 6.0
val bo: Boolean = true
println(c)
println(b)
println(s)
println(i)
println(l)
println(f)
println(d)
println(bo)
}
输出:
0
1
2
3
4
5.0
6.0
true
反编译为Java代码:
import kotlin.Metadata;
@Metadata(
mv = {1, 5, 1},
k = 2,
d1 = {"\u0000\b\n\u0000\n\u0002\u0010\u0002\n\u0000\u001a\u0006\u0010\u0000\u001a\u00020\u0001¨\u0006\u0002"},
d2 = {"main", "", "kt"}
)
public final class BuiltInTypeKt {
public static final void main() {
char c = '0';
byte b = 1;
short s = 2;
int i = 3;
long l = 4L;
float f = 5.0F;
double d = 6.0D;
boolean bo = true;
boolean var10 = false;
System.out.println(c);
var10 = false;
System.out.println(b);
var10 = false;
System.out.println(Short.valueOf(s));
var10 = false;
System.out.println(i);
var10 = false;
System.out.println(l);
var10 = false;
System.out.println(f);
var10 = false;
System.out.println(d);
var10 = false;
System.out.println(bo);
}
// $FF: synthetic method
public static void main(String[] var0) {
main();
}
}
除了对应Java基本数据类型的一些内置数据类型,还有如String、List、Set、Map、Array等常用的内置数据类型。
类型推断
当声明变量的同时给变量赋了值时,:(冒号)后面的数据类型可以省略,编译器会自动推断该变量的数据类型。
编译时常量
用const val修饰的变量称为编译时常量。
const val只能修饰全局变量
const val只能修饰primitive(Char/Byte/Short/Int/Long/Float/Double/Boolean)或String类型的变量。
Range表达式
fun main() {
val num = 33
if(num in 1..100){
println("normal")
}else{
println("abnormal")
}
}
输出:
normal
when表达式
fun main() {
val weekday = 1
val str = when(weekday)
{
1 -> "星期一"
2 -> "星期二"
3 -> "星期三"
4 -> "星期四"
5 -> "星期五"
6 -> "星期六"
7 -> "星期日"
else -> "输入错误"
}
println(str)
}
输出:
星期一
字符串模板
fun main() {
val name = "星期五"
val age = 18
println("我是$name, 今年${age}岁。")
}
输出:
我是星期五, 今年18岁。
函数
格式:可见性修饰符(默认public) fun 函数名(参数列表): 返回值(默认Unit){}
fun show(str: String){
println(str)
}
fun show(str: String): Unit {
println(str)
}
fun show(str: String) = println(str)
函数的默认参数
函数的某些参数有默认值,调用的时候如果不给有默认值的参数传值,则使用默认值。
fun main() {
print("World")
}
fun print(name: String, age: Int = 18, gender: Char = 'M'){
println("name = $name, age = $age, gender = $gender.")
}
输出:
name = World, age = 18, gender = M.
函数的具名参数
调用函数式,可以指定参数名传值。
fun main() {
print("jianghe", from = "ming")
}
fun print(name: String, age: Int = 18, gender: Char = 'M', from: String){
println("name = $name, age = $age, gender = $gender, from = $from.")
}
输出:
name = jianghe, age = 18, gender = M, from = ming.
TODO函数
调用处抛出异常
fun main() {
TODO("test")
}
输出:
Exception in thread "main" kotlin.NotImplementedError: An operation is not implemented: test
at TODOTestKt.main(TODOTest.kt:2)
at TODOTestKt.main(TODOTest.kt)
``:反引号
案例一:
fun main() {
`2021年10月30日 18时24分00秒`()
}
fun `2021年10月30日 18时24分00秒`(){
println("Into The New World")
}
输出:
Into The New World
案例二:
fun main() {
`5763209814`()
}
fun `5763209814`(){
println("Gravity")
}
输出:
Gravity
案例三:
fun main() {
`is`()
`in`()
}
fun `is`(){
println("2021-10-30 18:28:06")
}
fun `in`(){
println("Hi")
}
输出:
2021-10-30 18:28:06
Hi