Dart語法學(xué)習(xí)精選

Dart的所有東西都是對(duì)象,包括數(shù)字,函數(shù)等。

它們都繼承自O(shè)bject,默認(rèn)是都是null(包括數(shù)字),所以數(shù)字,字符串都可以調(diào)用各種方法。

本文主要講解:Dart語法知識(shí)包括數(shù)據(jù)類型、變量常量、集合、流程控制、運(yùn)算、異常、函數(shù)、面向?qū)ο?/b>

一、Hello Dart

這是第一個(gè)Hello Dart程序,很多程序入口都是從main函數(shù)開始,所以dart也不例外,一起來看下百變的main函數(shù)

//main標(biāo)準(zhǔn)寫法

voidmain() {

print('Hello World!');//注意: Dart和Java一樣表達(dá)式以分號(hào)結(jié)尾,寫習(xí)慣Kotlin的小伙伴需要注意了, 這可能是你從Kotlin轉(zhuǎn)Dart最大不適之一。

}

//dart中void類型,作為函數(shù)返回值類型可以省略

main() {

print('Hello World!');

}

//如果函數(shù)內(nèi)部只有一個(gè)表達(dá)式,可以省略大括號(hào),使用"=>"箭頭函數(shù);

//而對(duì)于Kotlin則是如果只有一個(gè)表達(dá)式,可以省略大括號(hào),使用"="連接,類似 fun main(args: Array) = println('Hello World!')

voidmain()=>print('Hello World!');

//最簡(jiǎn)寫形式

main()=>print('Hello World!');

二、數(shù)據(jù)類型

在dart中的一切皆是對(duì)象,包括數(shù)字、布爾值、函數(shù)等,它們和Java一樣都繼承于Object, 所以它們的默認(rèn)值也就是null. 在dart主要有: 布爾類型bool、數(shù)字類型num(數(shù)字類型又分為int,double,并且兩者父類都是num)、字符串類型String、集合類型(List, Set, Map)、Runes類和Symbols類型(后兩個(gè)用的并不太多)

1、布爾類型(bool)

在dart中和C語言一樣都是使用bool來聲明一個(gè)布爾類型變量或常量,而在Kotlin則是使用Boolean來聲明,但是一致的是它對(duì)應(yīng)的值只有兩個(gè)true和false.

main() {

boolisClosed=true;//注意,dart還是和Java類似的 [類型][變量名]方式聲明,這個(gè)和Kotlin的 [變量名]:[類型]不一樣.

boolisOpened=false;

}

2、數(shù)字類型(num、int、double)

在dart中num、int、double都是類,然后int、double都繼承num抽象類,這點(diǎn)和Kotlin很類似,在Kotlin中Number、Int、Double都是類,然后Int、Double都繼承于Number. 注意,但是在dart中沒有float, short, long類型

![](/Users/mikyou/Library/Application Support/marktext/images/2019-10-24-22-02-40-image.png)

main() {

doublepi=3.141592653;

intwidth=200;

intheight=300;

print(width/height);//注意:這里和Kotlin、Java都不一樣,兩個(gè)int類型相除是double類型小數(shù),而不是整除后的整數(shù)。

print(width~/height);//注意: 這才是dart整除正確姿勢(shì)

}

此外和Java、Kotlin一樣,dart也擁有一些數(shù)字常用的函數(shù):

main() {

print(3.141592653.toStringAsFixed(3));//3.142 保留有效數(shù)字

print(6.6.floor());//6向下取整

print((-6.6).ceil());//-6 向上取整

print(9.9.ceil());//10 向上取整

print(666.6.round());//667 四舍五入

print((-666.6).abs());// 666.6 取絕對(duì)值

print(666.6.toInt());//666 轉(zhuǎn)化成int,這中toInt、toDouble和Kotlin類似

print(999.isEven);//false 是否是偶數(shù)

print(999.isOdd);//true 是否是奇數(shù)

print(666.6.toString());//666.6 轉(zhuǎn)化成字符串

}

3、字符串類型(String)

在Dart中支持單引號(hào)、雙引號(hào)、三引號(hào)以及$字符串模板用法和Kotlin是一模一樣的。

main() {

Stringname='Hello Dart!';//單引號(hào)

Stringtitle="'Hello Dart!'";//雙引號(hào)

Stringdescription="""

Hello Dart! Hello Dart!

Hello Dart!

Hello Dart! Hello Dart!

"""

;//三引號(hào)

numvalue=2;

Stringresult="The result is $value";//單值引用

numwidth=200;

numheight=300;

Stringsquare="The square is ${width*height}";//表達(dá)式的值引用

}

和Kotlin一樣,dart中也有很多字符串操作的方法,比如字符串拆分、子串等

main() {

Stringurl="https://mrale.ph/dartvm/";

print(url.split("://")[0]);//字符串分割split方法,類似Java和Kotlin

print(url.substring(3,9));//字符串截取substring方法, 類似Java和Kotlin

print(url.codeUnitAt(0));//取當(dāng)前索引位置字符的UTF-16碼

print(url.startsWith("https"));//當(dāng)前字符串是否以指定字符開頭, 類似Java和Kotlin

print(url.endsWith("/"));//當(dāng)前字符串是否以指定字符結(jié)尾, 類似Java和Kotlin

print(url.toUpperCase());//大寫, 類似Java和Kotlin

print(url.toLowerCase());//小寫, 類似Java和Kotlin

print(url.indexOf("ph"));//獲取指定字符的索引位置, 類似Java和Kotlin

print(url.contains("http"));//字符串是否包含指定字符, 類似Java和Kotlin

print(url.trim());//去除字符串的首尾空格, 類似Java和Kotlin

print(url.length);//獲取字符串長(zhǎng)度

print(url.replaceFirst("t","A"));//替換第一次出現(xiàn)t字符位置的字符

print(url.replaceAll("m","M"));//全部替換, 類似Java和Kotlin

}

4、類型檢查(is和is!)和強(qiáng)制類型轉(zhuǎn)換(as)

和Kotlin一樣,dart也是通過is關(guān)鍵字來對(duì)類型進(jìn)行檢查以及使用as關(guān)鍵字對(duì)類型進(jìn)行強(qiáng)制轉(zhuǎn)換,如果判斷不是某個(gè)類型dart中使用is!, 而在Kotlin中正好相反則用!is表示。

main() {

intnumber=100;

doubledistance=200.5;

numage=18;

print(numberisnum);//true

print(distanceis!int);//true

print(ageasint);//18

}

5、Runes和Symbols類型

在Dart中的Runes和Symbols類型使用并不多,這里做個(gè)簡(jiǎn)單的介紹, Runes類型是UTF-32字節(jié)單元定義的Unicode字符串,Unicode可以使用數(shù)字表示字母、數(shù)字和符號(hào),然而在dart中String是一系列的UTF-16的字節(jié)單元,所以想要表示32位的Unicode的值,就需要用到Runes類型。我們一般使用\uxxxx這種形式來表示一個(gè)Unicode碼,xxxx表示4個(gè)十六進(jìn)制值。當(dāng)十六進(jìn)制數(shù)據(jù)多余或者少于4位時(shí),將十六進(jìn)制數(shù)放入到花括號(hào)中,例如,微笑表情( )是\u{1f600}。而Symbols類型則用得很少,一般用于Dart中的反射,但是注意在Flutter中禁止使用反射。

main() {

varclapping='\u{1f44f}';

print(clapping);

print(clapping.codeUnits);//返回十六位的字符單元數(shù)組

print(clapping.runes.toList());

Runes input=newRunes(

'\u2665? \u{1f605}? \u{1f60e}? \u{1f47b}? \u{1f596}? \u{1f44d}');

print(newString.fromCharCodes(input));

}

6、Object類型

在Dart中所有東西都是對(duì)象,都繼承于Object, 所以可以使用Object可以定義任何的變量,而且賦值后,類型也可以更改。

main() {

Objectcolor='black';

color=0xff000000;//運(yùn)行正常,0xff000000類型是int, int也繼承于Object

}

7、dynamic類型

在Dart中還有一個(gè)和Object類型非常類似的類型那就是dynamic類型,下面講到的var聲明的變量未賦值的時(shí)候就是dynamic類型, 它可以像Object一樣可以改變類型。dynamic類型一般用于無法確定具體類型, 注意:建議不要濫用dynamic,一般盡量使用Object, 如果你對(duì)Flutter和Native原生通信PlatformChannel代碼熟悉的話,你會(huì)發(fā)現(xiàn)里面大量使用了dynamic, 因?yàn)榭赡躰ative數(shù)據(jù)類型無法對(duì)應(yīng)dart中的數(shù)據(jù)類型,此時(shí)dart接收一般就會(huì)使用dynamic.

Object和dynamic區(qū)別在于: Object會(huì)在編譯階段檢查類型,而dynamic不會(huì)在編譯階段檢查類型。

main() {

dynamiccolor='black';

color=0xff000000;//運(yùn)行正常,0xff000000類型是int, int也繼承于Object

}

三、變量和常量

1、var關(guān)鍵字

在dart中可以使用var來替代具體類型的聲明,會(huì)自動(dòng)推導(dǎo)變量的類型,這是因?yàn)関ar并不是直接存儲(chǔ)值,而是存儲(chǔ)值的對(duì)象引用,所以var可以聲明任何變量。這一點(diǎn)和Kotlin不一樣,在Kotlin中聲明可變的變量都必須需要使用var關(guān)鍵字,而Kotlin的類型推導(dǎo)是默認(rèn)行為和var并沒有直接關(guān)系。注意: 在Flutter開發(fā)一般會(huì)經(jīng)常使用var聲明變量,以便于可以自動(dòng)推導(dǎo)變量的類型。

main() {

intcolorValue=0xff000000;

varcolorKey='black';//var聲明變量 自動(dòng)根據(jù)賦值的類型,推導(dǎo)為String類型

// 使用var聲明集合變量

varcolorList=['red','yellow','blue','green'];

varcolorSet={'red','yellow','blue','green'};

varcolorMap={'white':0xffffffff,'black':0xff000000};

}

但是在使用var聲明變量的時(shí)候,需要注意的是:如果var聲明的變量開始不初始化,不僅值可以改變它的類型也是可以被修改的,但是一旦開始初始化賦值后,它的類型就確定了,后續(xù)不能被改變。

main() {

varcolor;// 僅有聲明未賦值的時(shí)候,這里的color的類型是dynamic,所以它的類型是可以變的

color='red';

print(colorisString);//true

color=0xffff0000;

print(colorisint);//true

varcolorValue=0xffff0000;//聲明時(shí)并賦值,這里colorValue類型已經(jīng)推導(dǎo)出為int,并且確定了類型

colorValue='red';//錯(cuò)誤,這里會(huì)拋出編譯異常,String類型的值不能賦值給int類型

print(colorValueisint);//true

}

2、常量(final和const)

在dart中聲明常量可以使用const或final兩個(gè)關(guān)鍵字,注意: 這兩者的區(qū)別在于如果常量是編譯期就能初始化的就用const(有點(diǎn)類似Kotlin中的const val) 如果常量是運(yùn)行時(shí)期初始化的就用final(有點(diǎn)類似Kotlin中的val)

main() {

constPI=3.141592653;//const定義常量

finalnowTime=DateTime.now();//final定義常量

}

四、集合(List、Set、Map)

1、集合List

在dart中的List和Kotlin還是很大的區(qū)別,換句話說Dart整個(gè)集合類型系統(tǒng)的劃分都和Kotlin都不一樣,比如Dart中集合就沒有嚴(yán)格區(qū)分成可變集合(Kotlin中MutableList)和不變集合(Kotlin中的List),在使用方式上你會(huì)感覺它更像數(shù)組,但是它是可以隨意對(duì)元素增刪改成的。

List初始化方式

main() {

List colorList = ['red', 'yellow', 'blue', 'green'];//直接使用[]形式初始化

var colorList = ['red', 'yellow', 'blue', 'green'];

}

List常用的函數(shù)

main() {

List colorList = ['red', 'yellow', 'blue', 'green'];

colorList.add('white');//和Kotlin類似通過add添加一個(gè)新的元素

print(colorList[2]);//可以類似Kotlin一樣,直接使用數(shù)組下標(biāo)形式訪問元素

print(colorList.length);//獲取集合的長(zhǎng)度,這個(gè)Kotlin不一樣,Kotlin中使用的是size

colorList.insert(1, 'black');//在集合指定index位置插入指定的元素

colorList.removeAt(2);//移除集合指定的index=2的元素,第3個(gè)元素

colorList.clear();//清除所有元素

print(colorList.sublist(1,3));//截取子集合

print(colorList.getRange(1, 3));//獲取集合中某個(gè)范圍元素

print(colorList.join('<--->'));//類似Kotlin中的joinToString方法,輸出: red<--->yellow<--->blue<--->green

print(colorList.isEmpty);

print(colorList.contains('green'));

}

List的遍歷方式

main() {

List colorList = ['red', 'yellow', 'blue', 'green'];//for-i遍歷

for(var i = 0; i < colorList.length; i++) {//可以使用var或int

print(colorList[i]);

}

//forEach遍歷

colorList.forEach((color) => print(color));//forEach的參數(shù)為Function. =>使用了箭頭函數(shù)

//for-in遍歷

for(var color in colorList) {

print(color);

}

//while+iterator迭代器遍歷,類似Java中的iteator

while(colorList.iterator.moveNext()) {

print(colorList.iterator.current);

}

}

2、集合Set

集合Set和列表List的區(qū)別在于集合中的元素是不能重復(fù)的。所以添加重復(fù)的元素時(shí)會(huì)返回false,表示添加不成功.

Set初始化方式

main() {

Set colorSet= {'red', 'yellow', 'blue', 'green'};//直接使用{}形式初始化

var colorList = {'red', 'yellow', 'blue', 'green'};

}

集合中的交、并、補(bǔ)集,在Kotlin并沒有直接給到計(jì)算集合交、并、補(bǔ)的API

main() {

varcolorSet1={'red','yellow','blue','green'};

varcolorSet2={'black','yellow','blue','green','white'};

print(colorSet1.intersection(colorSet2));//交集-->輸出: {'yellow', 'blue', 'green'}

print(colorSet1.union(colorSet2));//并集--->輸出: {'black', 'red', 'yellow', 'blue', 'green', 'white'}

print(colorSet1.difference(colorSet2));//補(bǔ)集--->輸出: {'red'}

}

Set的遍歷方式(和List一樣)

main() {

Set<String>colorSet={'red','yellow','blue','green'};

//for-i遍歷

for(vari=0; i<colorSet.length; i++) {

//可以使用var或int

print(colorSet[i]);

}

//forEach遍歷

colorSet.forEach((color)=>print(color));//forEach的參數(shù)為Function. =>使用了箭頭函數(shù)

//for-in遍歷

for(varcolorincolorSet) {

print(color);

}

//while+iterator迭代器遍歷,類似Java中的iteator

while(colorSet.iterator.moveNext()) {

print(colorSet.iterator.current);

}

}

3、集合Map

集合Map和Kotlin類似,key-value形式存儲(chǔ),并且Map對(duì)象的中key是不能重復(fù)的

Map初始化方式

main() {

Map<String,int>colorMap={'white':0xffffffff,'black':0xff000000};//使用{key:value}形式初始化

varcolorMap=<String,int>{'white':0xffffffff,'black':0xff000000};

}

Map中常用的函數(shù)

main() {

Map<String,int>colorMap={'white':0xffffffff,'black':0xff000000};

print(colorMap.containsKey('green'));//false

print(colorMap.containsValue(0xff000000));//true

print(colorMap.keys.toList());//['white','black']

print(colorMap.values.toList());//[0xffffffff, 0xff000000]

colorMap['white']=0xfffff000;//修改指定key的元素

colorMap.remove('black');//移除指定key的元素

}

Map的遍歷方式

main() {

Map<String,int>colorMap={'white':0xffffffff,'black':0xff000000};

//for-each key-value

colorMap.forEach((key, value)=>print('color is $key, color value is $value'));

}

Map.fromIterables將List集合轉(zhuǎn)化成Map

main() {

List<String>colorKeys=['white','black'];

List<int>colorValues=[0xffffffff,0xff000000];

Map<String,int>colorMap=Map.fromIterables(colorKeys, colorValues);

}

4、集合常用的操作符

dart對(duì)于集合操作的也非常符合現(xiàn)代語言的特點(diǎn),含有豐富的集合操作符API,可以讓你處理結(jié)構(gòu)化的數(shù)據(jù)更加簡(jiǎn)單。

main() {

List<String>colorList=['red','yellow','blue','green'];

//forEach箭頭函數(shù)遍歷

colorList.forEach((color)=>{print(color)});

colorList.forEach((color)=>print(color));//箭頭函數(shù)遍歷,如果箭頭函數(shù)內(nèi)部只有一個(gè)表達(dá)式可以省略大括號(hào)

//map函數(shù)的使用

print(colorList.map((color)=>'$color_font').join(","));

//every函數(shù)的使用,判斷里面的元素是否都滿足條件,返回值為true/false

print(colorList.every((color)=>color=='red'));

//sort函數(shù)的使用

List<int>numbers=[0,3,1,2,7,12,2,4];

numbers.sort((num1, num2)=>num1-num2);//升序排序

numbers.sort((num1, num2)=>num2-num1);//降序排序

print(numbers);

//where函數(shù)使用,相當(dāng)于Kotlin中的filter操作符,返回符合條件元素的集合

print(numbers.where((num)=>num>6));

//firstWhere函數(shù)的使用,相當(dāng)于Kotlin中的find操作符,返回符合條件的第一個(gè)元素,如果沒找到返回null

print(numbers.firstWhere((num)=>num==5, orElse: ()=>-1));//注意: 如果沒有找到,執(zhí)行orElse代碼塊,可返回一個(gè)指定的默認(rèn)值

//singleWhere函數(shù)的使用,返回符合條件的第一個(gè)元素,如果沒找到返回null,但是前提是集合中只有一個(gè)符合條件的元素, 否則就會(huì)拋出異常

print(numbers.singleWhere((num)=>num==4, orElse: ()=>-1));//注意: 如果沒有找到,執(zhí)行orElse代碼塊,可返回一個(gè)指定的默認(rèn)值

//take(n)、skip(n)函數(shù)的使用,take(n)表示取當(dāng)前集合前n個(gè)元素, skip(n)表示跳過前n個(gè)元素,然后取剩余所有的元素

print(numbers.take(5).skip(2));

//List.from函數(shù)的使用,從給定集合中創(chuàng)建一個(gè)新的集合,相當(dāng)于clone一個(gè)集合

print(List.from(numbers));

//expand函數(shù)的使用, 將集合一個(gè)元素?cái)U(kuò)展成多個(gè)元素或者將多個(gè)元素組成二維數(shù)組展開成平鋪一個(gè)一位數(shù)組

varpair=[

[1,2],

[3,4]

];

print('flatten list: ${pair.expand((pair)=>pair)}');

varinputs=[1,2,3];

print('duplicated list: ${inputs.expand((number)=>[

number,

number,

number

])}');

}

五、流程控制

1、for循環(huán)

main() {

List<String>colorList=['red','yellow','blue','green'];

for(vari=0; i<colorList.length; i++) {//可以用var或int

print(colorList[i]);

}

}

2、while循環(huán)

main() {

List<String>colorList=['red','yellow','blue','green'];

varindex=0;

while(index<colorList.length) {

print(colorList[index++]);

}

}

3、do-while循環(huán)

main() {

List<String>colorList=['red','yellow','blue','green'];

varindex=0;

do{

print(colorList[index++]);

}while(index<colorList.length);

}

4、break和continue

main() {

List<String>colorList=['red','yellow','blue','green'];

for(vari=0; i<colorList.length; i++) {//可以用var或int

if(colorList[i]=='yellow') {

continue;

}

if(colorList[i]=='blue') {

break;

}

print(colorList[i]);

}

}

5、if-else

voidmain() {

varnumbers=[1,2,3,4,5,6,7,8,9,10,11];

for(vari=0; i<numbers.length; i++) {

if(numbers[i].isEven) {

print('偶數(shù): ${numbers[i]}');

}elseif(numbers[i].isOdd) {

print('奇數(shù): ${numbers[i]}');

}else{

print('非法數(shù)字');

}

}

}

6、三目運(yùn)算符(? : )

voidmain() {

varnumbers=[1,2,3,4,5,6,7,8,9,10,11];

for(vari=0; i<numbers.length; i++) {

numtargetNumber=numbers[i].isEven?numbers[i]*2:numbers[i]+4;

print(targetNumber);

}

}

7、switch-case語句

Color getColor(StringcolorName) {

Color currentColor=Colors.blue;

switch(colorName) {

case"read":

currentColor=Colors.red;

break;

case"blue":

currentColor=Colors.blue;

break;

case"yellow":

currentColor=Colors.yellow;

break;

}

returncurrentColor;

}

8、Assert(斷言)

在dart中如果條件表達(dá)式結(jié)果不滿足條件,則可以使用assert語句中斷代碼的執(zhí)行。特別是在Flutter源碼中隨處可見都是assert斷言的使用。注意:斷言只在檢查模式下運(yùn)行有效,如果在生產(chǎn)模式運(yùn)行,則斷言不會(huì)執(zhí)行。

assert(text!=null);//text為null,就會(huì)中斷后續(xù)代碼執(zhí)行

assert(urlString.startsWith('https'));

六、運(yùn)算符

1、算術(shù)運(yùn)算符

| 名稱 | 運(yùn)算符 | 例子 |

|:---:|:---:|:-------------------------:|

| 加 | + | var result = 1 + 1; |

| 減 | - | var result = 5 - 1; |

| 乘 | * | var result = 3 * 5; |

| 除 | / | var result = 3 / 5;?//0.6?|

| 整除 | ~/ | var result = 3 ~/ 5; //0 |

| 取余 | % | var result = 5 % 3; //2 |

2、條件運(yùn)算符

| 名稱 | 運(yùn)算符 | 例子 |

|:----:|:---:|:------:|

| 大于 | > | 2 > 1 |

| 小于 | < | 1 < 2 |

| 等于 | == | 1 == 1 |

| 不等于 | != | 3 != 4 |

| 大于等于 | >= | 5 >= 4 |

| 小于等于 | <= | 4 <= 5 |

3、邏輯運(yùn)算符

| 名稱 | 運(yùn)算符 | 例子 |

|:---:|:----:|:----------------:|

| 或 | \|\| | 2 > 1 \|\| 3 < 1 |

| 與 | && | 2 > 1 && 3 < 1 |

| 非 | !| !(2 > 1) |

4、位運(yùn)算符

| 名稱 | 運(yùn)算符 |

|:---:|:---:|

| 位與 | & |

| 位或 | \| |

| 位非 | ~ |

| 異或 | ^ |

| 左移 | << |

| 右移 | >> |

5、三目運(yùn)算符

condition ? expr1 : expr2

varisOpened=(value==1)?true:false;

6、空安全運(yùn)算符

| 操作符 | 解釋 |

|:-----------------------:|:---------------------------------------:|

| result = expr1 ?? expr2 | 若expr1為null, 返回expr2的值,否則返回expr1的值 |

| expr1 ??= expr2 | 若expr1為null, 則把expr2的值賦值給expr1 |

| result = expr1?.value | 若expr1為null, 就返回null,否則就返回expr1.value的值 |

1、result = expr1 ?? expr2

如果發(fā)現(xiàn)expr1為null,就返回expr2的值,否則就返回expr1的值, 這個(gè)類似于Kotlin中的result = expr1 ?: expr2

main() {

varchoice=question.choice??'A';

//等價(jià)于

varchoice2;

if(question.choice==null) {

choice2='A';

}else{

choice2=question.choice;

}

}

2、expr1 ??= expr2等價(jià)于expr1 = expr1 ?? expr2(轉(zhuǎn)化成第一種)

main() {

varchoice??='A';

//等價(jià)于

if(choice==null) {

choice='A';

}

}

3、result = expr1?.value

如果expr1不為null就返回expr1.value,否則就會(huì)返回null, 類似Kotlin中的 ?. 如果expr1不為null,就執(zhí)行后者

varchoice=question?.choice;//等價(jià)于

if(question==null){

returnnull;

}else{

returnquestion.choice;

}

question?.commit();//等價(jià)于

if(question==null){

return;//不執(zhí)行commit()

}else{

question.commit();//執(zhí)行commit方法

}

7、級(jí)聯(lián)操作符(..)

級(jí)聯(lián)操作符是.., 可以讓你對(duì)一個(gè)對(duì)象中字段進(jìn)行鏈?zhǔn)秸{(diào)用操作,類似Kotlin中的apply或run標(biāo)準(zhǔn)庫函數(shù)的使用。

question

..id='10001'

..stem='第一題: xxxxxx'

..choices=<String>['A','B','C','D']

..hint='聽音頻做題';

Kotlin中的run函數(shù)實(shí)現(xiàn)對(duì)比

question.run {

id ='10001'

stem ='第一題: xxxxxx'

choices = ['A','B','C','D']

hint ='聽音頻做題'

}

8、運(yùn)算符重載

在dart支持運(yùn)算符自定義重載,使用operator關(guān)鍵字定義重載函數(shù)

classVip{

finalintlevel;

finalintscore;

constVip(this.level,this.score);

booloperator>(Vip other)=>

level>other.level||(level==other.level&&score>other.score);

booloperator<(Vip other)=>

level<other.level||(level==other.level&&score<other.score);

booloperator==(Vip other)=>

level==other.level&&

score==other.level;//注意: 這段代碼可能在高版本的Dart中會(huì)報(bào)錯(cuò),在低版本是OK的

//上述代碼,在高版本Dart中,Object中已經(jīng)重載了==,所以需要加上covariant關(guān)鍵字重寫這個(gè)重載函數(shù)。

@override

booloperator==(covariant Vip other)=>

(level==other.level&&score==other.score);

@override

intgethashCode=>super.hashCode;//伴隨著你還需要重寫hashCode,至于什么原因大家應(yīng)該都知道

}

main() {

varuserVip1=Vip(4,3500);

varuserVip2=Vip(4,1200);

if(userVip1>userVip2) {

print('userVip1 is super vip');

}elseif(userVip1<userVip2) {

print('userVip2 is super vip');

}

}

七、異常

dart中的異常捕獲方法和Java,Kotlin類似,使用的也是try-catch-finally; 對(duì)特定異常的捕獲使用on關(guān)鍵字. dart中的常見異常有:NoSuchMethodError(當(dāng)在一個(gè)對(duì)象上調(diào)用一個(gè)該對(duì)象沒有 實(shí)現(xiàn)的函數(shù)會(huì)拋出該錯(cuò)誤)、ArgumentError(調(diào)用函數(shù)的參數(shù)不合法會(huì)拋出這個(gè)錯(cuò)誤)

main() {

intnum=18;

intresult=0;

try{

result=num~/0;

}catch(e) {//捕獲到IntegerDivisionByZeroException

print(e.toString());

}finally{

print('$result');

}

}

//使用on關(guān)鍵字捕獲特定的異常

main() {

intnum=18;

intresult=0;

try{

result=num~/0;

} on IntegerDivisionByZeroExceptioncatch(e) {//捕獲特定異常

print(e.toString());

}finally{

print('$result');

}

}

八、函數(shù)

在dart中函數(shù)的地位一點(diǎn)都不亞于對(duì)象,支持閉包和高階函數(shù),而且dart中的函數(shù)也會(huì)比Java要靈活的多,而且Kotlin中的一些函數(shù)特性,它也支持甚至比Kotlin支持的更全面。比如支持默認(rèn)值參數(shù)、可選參數(shù)、命名參數(shù)等.

1、函數(shù)的基本用法

main() {

print('sum is ${sum(2,5)}');

}

numsum(numa,numb) {

returna+b;

}

2、函數(shù)參數(shù)列表傳參規(guī)則

//num a, num b, num c, num d 最普通的傳參: 調(diào)用時(shí),參數(shù)個(gè)數(shù)和參數(shù)順序必須固定

add1(numa,numb,numc,numd) {

print(a+b+c+d);

}

//[num a, num b, num c, num d]傳參: 調(diào)用時(shí),參數(shù)個(gè)數(shù)不固定,但是參數(shù)順序需要一一對(duì)應(yīng), 不支持命名參數(shù)

add2([numa,numb,numc,numd]) {

print(a+b+c+d);

}

//{num a, num b, num c, num d}傳參: 調(diào)用時(shí),參數(shù)個(gè)數(shù)不固定,參數(shù)順序也可以不固定,支持命名參數(shù),也叫可選參數(shù),是dart中的一大特性,這就是為啥Flutter代碼那么多可選屬性,大量使用可選參數(shù)

add3({numa,numb,numc,numd}) {

print(a+b+c+d);

}

//num a, num b, {num c, num d}傳參: 調(diào)用時(shí),a,b參數(shù)個(gè)數(shù)固定順序固定,c,d參數(shù)個(gè)數(shù)和順序也可以不固定

add4(numa,numb, {numc,numd}) {

print(a+b+c+d);

}

main() {

add1(100,100,100,100);//最普通的傳參: 調(diào)用時(shí),參數(shù)個(gè)數(shù)和參數(shù)順序必須固定

add2(100,100);//調(diào)用時(shí),參數(shù)個(gè)數(shù)不固定,但是參數(shù)順序需要一一對(duì)應(yīng), 不支持命名參數(shù)(也就意味著順序不變)

add3(

b:200,

a:200,

c:100,

d:100);//調(diào)用時(shí),參數(shù)個(gè)數(shù)不固定,參數(shù)順序也可以不固定,支持命名參數(shù)(也就意味著順序可變)

add4(100,100, d:100, c:100);//調(diào)用時(shí),a,b參數(shù)個(gè)數(shù)固定順序篤定,c,d參數(shù)個(gè)數(shù)和順序也可以不固定

}

3、函數(shù)默認(rèn)參數(shù)和可選參數(shù)(以及與Kotlin對(duì)比)

dart中函數(shù)的默認(rèn)值參數(shù)和可選參數(shù)和Kotlin中默認(rèn)值參數(shù)和命名參數(shù)一致,只是寫法上不同而已

add3({numa,numb,numc,numd=100}) {//d就是默認(rèn)值參數(shù),給的默認(rèn)值是100

print(a+b+c+d);

}

main() {

add3(b:200, a:100, c:800);

}

與Kotlin對(duì)比

funadd3(a: Int, b: Int, c: Int, d: Int =100) {

println(a + b + c + d)

}

funmain(args: Array) {

add3(b =200, a =100, c =800)

}

4、函數(shù)類型與高階函數(shù)

在dart函數(shù)也是一種類型Function,可以作為函數(shù)參數(shù)傳遞,也可以作為返回值。類似Kotlin中的FunctionN系列函數(shù)

main() {

Function square=(a) {

returna*a;

};

Function square2=(a) {

returna*a*a;

};

add(3,4, square, square2)

}

numadd(numa,numb, [Function op, Function op2]) {

//函數(shù)作為參數(shù)傳遞

returnop(a)+op2(b);

}

5、函數(shù)的簡(jiǎn)化以及箭頭函數(shù)

在dart中的如果在函數(shù)體內(nèi)只有一個(gè)表達(dá)式,那么就可以使用箭頭函數(shù)來簡(jiǎn)化代碼,這點(diǎn)也和Kotlin類似,只不過在Kotlin中人家叫l(wèi)ambda表達(dá)式,只是寫法上不一樣而已。

add4(numa,numb, {numc,numd}) {

print(a+b+c+d);

}

add5(numa,numb, {numc,numd})=>print(a+b+c+d);

九、面向?qū)ο?/p>

在dart中一切皆是對(duì)象,所以面向?qū)ο笤贒art中依然舉足輕重,下面就先通過一個(gè)簡(jiǎn)單的例子認(rèn)識(shí)下dart的面向?qū)ο螅罄m(xù)會(huì)繼續(xù)深入。

1、類的基本定義和使用

abstractclassPerson{

Stringname;

intage;

doubleheight;

Person(this.name,this.age,this.height);//注意,這里寫法可能大家沒見過, 這點(diǎn)和Java是不一樣,這里實(shí)際上是一個(gè)dart的語法糖。但是這里不如Kotlin,Kotlin是直接把this.name傳值的過程都省了。

//與上述的等價(jià)代碼,當(dāng)然這也是Java中必須要寫的代碼

Person(Stringname,intage,doubleheight) {

this.name=name;

this.age=age;

this.height=height;

}

//然而Kotlin很徹底只需要聲明屬性就行,下面是Kotlin實(shí)現(xiàn)代碼

abstractclassPerson(val name:String, val age: Int, val height: Double)

}

classStudentextendsPerson {//和Java一樣同時(shí)使用extends關(guān)鍵字表示繼承

Student(Stringname,intage,doubleheight,doublegrade):super(name, age, height);//在 Dart里:類名(變量,變量,...) 是構(gòu)造函數(shù)的寫法, :super()表示該構(gòu)造調(diào)用父類,這里構(gòu)造時(shí)傳入三個(gè)參數(shù)

}

2、類中屬性的getter和setter訪問器(類似Kotlin)

abstractclassPerson{

String_name;////相當(dāng)于kotlin中的var 修飾的變量有setter、getter訪問器,在dart中沒有訪問權(quán)限, 默認(rèn)_下劃線開頭變量表示私有權(quán)限,外部文件無法訪問

finalint_age;//相當(dāng)于kotlin中的val 修飾的變量只有g(shù)etter訪問器

Person(this._name,this._age);//這是上述簡(jiǎn)寫形式

//使用set關(guān)鍵字 計(jì)算屬性 自定義setter訪問器

setname(Stringname)=>_name=name;

//使用get關(guān)鍵字 計(jì)算屬性 自定義getter訪問器

boolgetisStudent=>_age>18;

}

喜歡的點(diǎn)個(gè)贊或者關(guān)注哦,謝謝

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

推薦閱讀更多精彩內(nèi)容