作为Flutter开发使用的语言,Dart的学习是必不可少的,它是一门专门为跨平台设计的语言,如果你有kotlin的知识,那么你的学习成本不高,在一定程度上他们很相像
**Android Studio**于2020.3(Arctic Fox) 版本后,都支持Flutter开发,只需要在插件中进行下载安装
先下载安装Dart:

顺便把Flutter也下载安装了:

Flutter开发需要对应的SDK,其中包含了Dart的SDK,下载地址:https://flutter.cn/docs/development/tools/sdk/releases

下载后解压到自己喜欢的目录,我这边是:C:\Program Files\FlutterSDK\flutter,配置环境变量(非必要):

选择Flutter SDK的目录:

按照描述填写工程信息并创建:

目前我们在**Android Studio**中搭建了Flutter环境,由于Flutter包含了Dart,所以Dart可以直接运行,创建工程后会自动帮我们构建项目目录,我们来到lib目录下进行Dart的学习

main函数是Dart程序的入口,创建一个Dart文件,并编写代码:
main() {// 定义一个数字变量var number = 42;print(number);
}
运行结果:

Dart是一个强类型语言,所以我们可以通过指定变量类型的方式去定义变量,如:int i = 42,但Dart不推荐该方式,和Kotlin一样,Dart支持类型推断,我们只需要使用var,后续Dart会自动识别该变量类型
main() {// 指定变量类型int i = 42;// 使用类型推断var a = '1a';print(i.runtimeType);print(a.runtimeType);
}
运行结果:

如果一个变量可以为空,那么定义该变量时,需要使用强类型+?的组合方式:
main() {// 空安全int? i = null;print(i == null);i = 10;print(i == null);
}
运行结果:

Dart编译器在变量为空时会提示你,非空时则不需要做特别处理:
main() {// 空安全int? i = null;if (i != null) print(i + 2);i = 10;print(i + 2);
}
如果你认为可空变量不为空,可以通过!强制调用,当变量为空时,抛出异常:
main() {// 空安全int? i = null;print(i! + 2);
}
运行结果:

使用late关键字申明变量,程序将在使用该变量时才进行创建
// Tortoise类型变量
late var t = Tortoise();// 定义一个类
class Tortoise {var name = "tortoise";// 构造实例方法Tortoise() {print("constructor init");}
}main() {print("start");print(t.name);print("end");
}
运行结果:

Dart编译器在定义非空变量时未赋值的情况进行提示报错,有时你仅仅想延后给该变量赋值,如在检查顶级变量和实例(引用类型)变量时,使用late修饰的变量,编译器就不会对它进行非空判断
使用final代替var进行定义变量后,该变量不可重新赋值:

const不能修饰实例类型,使用const代替var进行定义变量后,表示该变量是常量,const变量同时也是final的,通常使用在顶级变量与类静态常量中:

static修饰的成员变量在同类型实例中有且只存在一份,通常和const一起使用,标识一个类静态常量
class Tag {static const tag_1 = 10;static const tag_2 = 20;
}main() {print(Tag.tag_1);print(Tag.tag_2);
}
内置类型不是Java中的基本类型,它们都带有丰富的函数
Dart内置两种数字类型:int和double
main(){// int类型变量var i = 10;print(i + 20);// 格式化字符串转换为int,失败抛出异常print(int.parse("20"));
}
main(){// double类型变量var d = 10.45;// 向上取整print(d.ceil());// 格式化字符串转换为double,失败抛出异常print(double.parse("20.23"));
}
Dart可以使用'内容' 、"内容"、 ''' 多行内容 '''三种方式表示一个字符串
main() {var s1 = 'hello dart';var s2 = "hello dart";var s3 = '''hellodart''';print(s1);print(s2);print(s3);
}
运行结果:

在字符串中可以使用${表达式}将表达式结果代替占位符,表达式是一个标识符,可以省略掉{}
main() {var name = 'zhangsan';print("$name study dart,${name.toUpperCase()}");
}
运行结果:

在字符串前标识r,那么该字符串内容不会转义
main() {print(r"study dart \n very happy");
}
运行结果:

在Dart中使用bool定义布尔变量,用法就是true和false,比较简单不多做介绍
List类型称之为列表或数组,定义方式由[]包裹元素,内置增删改一系列函数
main() {// []包裹itemvar intArr1 = [1, 2, 3];List? intArr2;// 添加一个listintArr1.addAll([4, 6]);print(intArr1);
}
定义List时,可以使用...或...?(空不添加),在初始化时添加别List
main() {var intArr1 = [1, 2, 3];List? intArr2;var intArr3 = [0, ...intArr1];// ...初始化就添加别的Listvar intArr4 = [0, ...?intArr2];// ...?为空不添加print(intArr3);print(intArr4);
}
运行结果:

集合为无序无重复项的容器
Set中不会存在重复元素:
main() {var set1 = {1, 1, 1};// 只含有一个1print(set1);
}
运行结果:

可以在{}前使用<类型>创建一个该类型的空集合
main() {var set = {};set.add("hi");set.addAll({"dart", "flutter"});print(set);
}
Map原理和Set相同,存放键值对,键唯一
main() {var map = {0: "hi", 1: "dart"};print(map[0]);print(map[1]);
}
运行结果:

可以通过Map<键类型,值类型>()创建一个指定key类型value类型的空Map
main(){var map = Map();
}
Map添加元素直接使用[key]赋值即可;取值使用[key],不存在返回空
main(){var map = Map();// 添加或更新键值对map['a'] = 'A';map['b'] = 'B';print(map['a']);// 没有对应的键,返回nullprint(map['c']);
}
运行结果:

Unicode 字符的常见方式是使用 \uXXXX,其中 XXXX 是一个四位数的 16 进制数字。例如心形字符(♥)的 Unicode 为 \u2665。对于不是四位数的 16 进制数字,需要使用大括号将其括起来。例如大笑的 emoji 表情(😆)的 Unicode 为 \u{1f600}。
main() {var hi = "hi \u{1f600}";print(hi);// 期望只输出😆print(hi.substring(hi.length - 1));
}
运行结果:

上面我们期望只输出😆,但是内置函数并不会把 Unicode 字符当作一个字符,如果你需要读写单个 Unicode 字符,可以使用 characters 包中定义的 characters API,需要导入'package:characters/characters.dart'包
import 'package:characters/characters.dart';main() {var hi = "hi \u{1f600}";print(hi);// 期望只输出😆print(hi.substring(hi.length - 1));print(hi.characters.last);
}
运行结果:
