級(jí)別: ★☆☆☆☆
標(biāo)簽:「Flutter 」「Dart」「Dart基礎(chǔ)類(lèi)型」
作者: WYW
審校: QiShare團(tuán)隊(duì)
前言:
4篇Dart基礎(chǔ)已經(jīng)全部更新完成。目錄如下:
Dart 基礎(chǔ) (一)
Dart 基礎(chǔ) (二)
Dart 基礎(chǔ) (三)
Dart 基礎(chǔ) (四)
筆者最近看了Flutter相關(guān)的內(nèi)容,而Flutter的基礎(chǔ)庫(kù)是由Dart編寫(xiě)的,所以筆者學(xué)習(xí)了關(guān)于Dart的部分內(nèi)容,整理了幾篇關(guān)于Dart基礎(chǔ)的文章。
Flutter 、Dart簡(jiǎn)介
Flutter is Google’s portable UI toolkit for building beautiful, natively-compiled applications for mobile, web, and desktopfrom a single codebase. (引自Flutter.dev)
Flutter 是谷歌的便攜式UI工具包,可以使用一套代碼庫(kù),來(lái)創(chuàng)建漂亮的本地編譯的移動(dòng)端(iOS、Android)應(yīng)用,web(瀏覽器中的頁(yè)面)、桌面(Mac、Windows、Linux)應(yīng)用。
Flutter 當(dāng)前最新穩(wěn)定版本是1.5。
Dart([KK] 英語(yǔ)發(fā)音:/dɑrt/, [DJ] 英語(yǔ)發(fā)音:/dɑ:t/)是一種適用于萬(wàn)維網(wǎng)的開(kāi)放源代碼編程語(yǔ)言,由Google主導(dǎo)開(kāi)發(fā),于2011年10月公開(kāi)。它的開(kāi)發(fā)團(tuán)隊(duì)由Google Chrome瀏覽器V8引擎團(tuán)隊(duì)的領(lǐng)導(dǎo)者拉爾斯·巴克主持,目標(biāo)在于成為下一代結(jié)構(gòu)化Web開(kāi)發(fā)語(yǔ)言。
類(lèi)似JavaScript,Dart也是一種面向?qū)ο笳Z(yǔ)言,但是它采用基于類(lèi)編程。它只允許單一繼承,語(yǔ)法風(fēng)格接近C語(yǔ)言。
Dart is a client-optimized language for fast apps on any platform
Dart是客戶端的優(yōu)化過(guò)的語(yǔ)言,可用于在任何平臺(tái)(包括移動(dòng)端(iOS、Android)、Web頁(yè)面、桌面(Mac、Windows、Linux)應(yīng)用),來(lái)創(chuàng)建運(yùn)行流暢的應(yīng)用。
當(dāng)前Dart最新版本是2.4.0,2019-06-27 Dart開(kāi)發(fā)團(tuán)隊(duì)發(fā)布2.4.0版本Dart。 Dart change log
下邊,我們聊一下,關(guān)于Dart安裝,及查看代碼運(yùn)行效果的內(nèi)容
安裝Dart
Dart 安裝方式可查看:http://dart.goodev.org/install
在 Mac 安裝 Dart 可查看 : http://dart.goodev.org/install/mac
在線演示Dart運(yùn)行效果
DartPad:Dart 在線演示:https://dartpad.dartlang.org
DartPad, an open-source tool, allows you to play with the Dart language features in any modern browser.
DartPad 是一個(gè)開(kāi)源工具,我們可以在現(xiàn)代瀏覽器中使用DartPad來(lái)演示Dart語(yǔ)言特性。
筆者的理解就是,我們可以用DartPad在線查看Dart編程效果。
下邊我們聊一下,Dart的基礎(chǔ)語(yǔ)法相關(guān)的內(nèi)容。
Dart導(dǎo)入頭文件(資源庫(kù))的方式
// dart:io 為非Web應(yīng)用提供文件,Socket,HTTP,和其他IO支持。
import 'dart:io';
// 導(dǎo)入Android設(shè)計(jì)風(fēng)格的material庫(kù)
import 'package:flutter/material.dart';
// 導(dǎo)入iOS 的設(shè)計(jì)風(fēng)格cupertino庫(kù)
import 'package:flutter/cupertino.dart';
// 只導(dǎo)入material庫(kù)中的AppBar
import 'package:flutter/material.dart' show AppBar;
// 導(dǎo)入除了material庫(kù)中 除BottomNavigationBar之外 的內(nèi)容
import 'package:flutter/material.dart' hide BottomNavigationBar;
Dart基本語(yǔ)法
-
1. 輸出語(yǔ)句
一般我們開(kāi)始學(xué)習(xí)某門(mén)語(yǔ)言的時(shí)候都會(huì)先輸出,Hello World!或者是Hello 語(yǔ)言名。
Dart的輸出語(yǔ)句和Swift一樣,都是print
。Dart的語(yǔ)句需要使用分號(hào)結(jié)尾。
main(){
print('Hello World!');
print('Hello Dart!');
}
// 輸出結(jié)果:
/**
Hello World!
Hello Dart!
*/
- 2. 變量
定義變量使用 關(guān)鍵字var
;
如定義變量名為name,值為QiShare的變量。
var name = 'QiShare';
print(name);
// 輸出結(jié)果:
// QiShare
Dart變量默認(rèn)值為null
int fansCount;
// String fansCount;
if (fansCount == null) {
print('null');
} else {
print('not null fansCount ${fansCount}');
}
// 輸出結(jié)果:
/**
null
*/
輸出變量,需要拼接字符串和變量一起輸出的情況下,所有的內(nèi)容都使用''
包起來(lái)
${變量}
可以用于訪問(wèn)相應(yīng)的變量的值。
取變量值是否使用{}
分情況:
1.直接訪問(wèn)實(shí)例的情況 直接使用 $實(shí)例 即可;
2.訪問(wèn)實(shí)例的成員變量的情況 需要使用 ${實(shí)例.變量} ;
3.只是單純輸出實(shí)例或者是實(shí)例的成員變量的情況,不需要使用$。
3. 字符串
字符串拼接及多行字符串
// 字符串拼接
var name = 'QiShare' + 'QiShare';
print(name);
// 輸出結(jié)果:
// QiShareQiShare
// 多行字符串
var name = '''
QiShare
QiShare
QiShare
''';
print(name);
// 輸出結(jié)果:
/**
QiShare
QiShare
QiShare
*/
關(guān)于變量是否對(duì)外可訪問(wèn),在iOS Objective-C里邊,如果我們想類(lèi)文件A的某個(gè)變量對(duì)外可見(jiàn),可以在類(lèi)A.h文件里邊把變量聲明為屬性。然后只要引用了A.h的類(lèi),就能夠訪問(wèn)A.h中聲明的屬性。
在Dart中,如果要指定某個(gè)變量對(duì)外可訪問(wèn),可以在類(lèi)文件的頂部聲明變量。
如果想要指定某個(gè)類(lèi)的實(shí)例變量對(duì)外可訪問(wèn),直接寫(xiě)在類(lèi)聲明的內(nèi)部即可。并且變量不要使用下劃線開(kāi)頭。
對(duì)于私有的變量,或者方法,使用下劃線 “_” 在變量、方法前,則該變量、方法將分別為私有變量、私有方法。
對(duì)于其他的多個(gè)常量,整個(gè)項(xiàng)目中使用的情況,可以單獨(dú)創(chuàng)建一個(gè)類(lèi)文件用于存放公共的常量。
4. 變量類(lèi)型檢查及值檢查
開(kāi)發(fā)過(guò)程中,在對(duì)服務(wù)端下發(fā)的數(shù)據(jù),進(jìn)行處理的時(shí)候,有時(shí)需要進(jìn)行變量類(lèi)型判斷,值的檢測(cè)??梢詤⒖既缦碌?種檢測(cè)方式。
一個(gè)是變量類(lèi)型檢查,使用runtimeType
或者使用關(guān)鍵字is
進(jìn)行類(lèi)型檢測(cè);
另一個(gè)是變量的值的檢查
。
變量類(lèi)型檢查
// runtimeType是用于查看變量類(lèi)型的。
// 可以使用runtimeType或is查看變量是什么類(lèi)型
String QiShare = 'QiShare';
if (QiShare.runtimeType == String) {
print(QiShare);
print('name:${QiShare}');
}
/**
QiShare
name:QiShare
*/
// 使用is 查看變量的類(lèi)型
String QiShare = 'QiShare';
if (QiShare is String) {
print('是String類(lèi)型 :');
print(QiShare);
} else {
print('非String類(lèi)型');
}
/* 輸出結(jié)果:
是String類(lèi)型 : QiShare
*/
變量的值的檢查
。
// Check for an empty string.
var fullName = '';
if (fullName.isEmpty) {
print('空字符串');
}
// Check for zero.
var hitPoints = 0;
assert(hitPoints <= 0);
if(hitPoints <= 0) {
print('hitPoints小于等于0');
}
// Check for null.
var unicorn;
if (unicorn == null) {
print(null);
}
// Check for NaN. The global NaN property is a value representing Not-A-Number.
var iMeantToDoThis = 0 / 0;
if (iMeantToDoThis.isNaN) {
print('Not a number');
}
-
5. 類(lèi)型推導(dǎo)
使用var 聲明的變量,通過(guò)輸出變量的runtimeType
,可以發(fā)現(xiàn)變量的類(lèi)型可以通過(guò)賦給變量的值,自動(dòng)進(jìn)行類(lèi)型推導(dǎo)。
var name = 'QiShare';
if (name == null) {
print('null');
} else {
print(name);
print(name.runtimeType);
}
/**
QiShare
String
*/
var name = 10.0;
if (name == null) {
print('null');
} else {
print(name);
print(name.runtimeType);
}
name = 10.1;
if (name == null) {
print('null');
} else {
print(name);
print(name.runtimeType);
}
/**
10
int
10.1
double
*/
/*
上邊的例子很有意思,推導(dǎo)出的10.0的類(lèi)型為int;
推導(dǎo)出的10.1的類(lèi)型為double。
筆者認(rèn)為是編譯器做了優(yōu)化,具體怎么做的,筆者尚不清楚。
*/
當(dāng)然除了類(lèi)型推導(dǎo)知道變量的類(lèi)型外,對(duì)于我們自己聲明的變量,在已經(jīng)確定變量類(lèi)型的情況下,直接直觀地聲明變量類(lèi)型即可。
那么對(duì)于var 這種變量的使用場(chǎng)景,筆者想到的有如下2種情況。
1.接收服務(wù)端返回?cái)?shù)據(jù)的時(shí)候,避免返回的數(shù)據(jù)類(lèi)型和預(yù)期的有差異的情況,可以使用var 變量接收,然后通過(guò)類(lèi)型檢測(cè)后,再進(jìn)一步進(jìn)行數(shù)據(jù)地處理;
2.對(duì)于某些函數(shù)接收的參數(shù)可能是多種類(lèi)型的情況下,使用var 來(lái)修飾參數(shù)類(lèi)型。
- 6. Final and const
final 聲明的變量只能賦值一次
final name = 'QiShare';
// name = 'QiShareQiShare';
// 報(bào)錯(cuò):
const 是編譯時(shí)常量
const name = 'QiShare'
final 或const修飾的變量只能賦值一次;
const 變量是編譯時(shí)常量,在編譯的時(shí)候,我們就已經(jīng)知道了const 變量的值。
頂級(jí)的final 變量或類(lèi)中的final變量在第一次使用的時(shí)候初始化。
這里舉一個(gè)類(lèi)中final變量初始化的例子:
class QiShareMember {
final String memberID;
final String memberName;
QiShareMember(this.memberID, this.memberName);
}
// QiShareMember初始化實(shí)例
QiShareMember member = QiShareMember('id', 'name');
- 7. List和Map
var list = ['a', 'b', 1];
// 遍歷list
list.forEach( (object){
print('類(lèi)型 ${object.runtimeType}');
print('值${object}');
}
);
// list 中的數(shù)據(jù)
print(list.length);
/**
CONSOLE
類(lèi)型 String
值a
類(lèi)型 String
值b
類(lèi)型 int
值1
*/
void main() {
var gifts = {
// Keys Values
'first' : 'partridge',
'second': 'turtledoves',
'fifth' : 'golden rings'
};
print(gifts);
// 獲取Map中的鍵值對(duì)數(shù)目
print(gifts.length);
// 遍歷字典
gifts.forEach(
(key, value){
print('key:${key}');
print('value:${value}');
}
);
/**
CONSOLE
{first: partridge, second: turtledoves, fifth: golden rings}
key:first
value:partridge
key:second
value:turtledoves
key:fifth
value:golden rings
*/
List相當(dāng)于是Swift的數(shù)組;List的使用場(chǎng)景有:用于放置UI層面的列表數(shù)據(jù)寬泛內(nèi)容;
Map相當(dāng)于Swift的字典;Map的使用場(chǎng)景有:用于放置UI層面的列表數(shù)據(jù)中更具體內(nèi)容;
舉個(gè)例子:
比如說(shuō) 如下的數(shù)據(jù),根據(jù)List中的字典的個(gè)數(shù)可以確定,UI層面上,需要展示5個(gè)人的信息;
進(jìn)一步根據(jù)List中,每一個(gè)字典中的name,和avatarUrl 可以確定更加細(xì)致的UI層面,每個(gè)人的個(gè)人信息的名字(name的值)和頭像(avatarUrl 對(duì)應(yīng)的圖片)應(yīng)該顯示什么。
[
{'name':'QiShare1',
'avatarUrl':'https://www.so.com....jpg'
},
{
'name':'QiShare2',
'avatarUrl':'https://www.so.com....jpg'
},
{
'name':'QiShare3',
'avatarUrl':'https://www.so.com....jpg'
},
{
'name':'QiShare4',
'avatarUrl':'https://www.so.com....jpg'
},
{
'name':'QiShare5',
'avatarUrl':'https://www.so.com....jpg'
}
];
- 8. 數(shù)據(jù)類(lèi)型轉(zhuǎn)換
下邊是字符串和整數(shù),浮點(diǎn)數(shù)之間的類(lèi)型轉(zhuǎn)換。
// String -> int String 類(lèi)型轉(zhuǎn)換為int 類(lèi)型
var one = int.parse('1');
print(one.runtimeType);
// String -> double String 類(lèi)型轉(zhuǎn)為double類(lèi)型
var onePointOne = double.parse('1.1');
print(onePointOne.runtimeType);
// int -> String int 類(lèi)型轉(zhuǎn)換為String
String oneAsString = 1.toString();
print(oneAsString.runtimeType);
// double -> String double類(lèi)型轉(zhuǎn)換為String類(lèi)型
String piAsString = 3.14159.toStringAsFixed(2);
print(piAsString.runtimeType);
/**
int
double
String
String
*/
// List類(lèi)型轉(zhuǎn)換 把子類(lèi)型為dynamic的List轉(zhuǎn)換為更為具體的子類(lèi)型為String的List
List<dynamic> dynmicList = ['QiShare', 'QiShare'];
print(dynmicList.runtimeType);
List<String>strList = List<String>.from(dynmicList);
print(strList);
print(strList.runtimeType);
/**
JSArray
[1, 2]
JSArray<String>
*/
- 9.方法
下邊筆者舉了一個(gè)說(shuō)出QiShare 年齡的方法。
int qiAgeNum = qiAgeNumber();
qiSay('${words()} ${qiAgeNum}');
// 返回值為String類(lèi)型,參數(shù)為空,名為words方法。
String words(){
return 'QiShare Age:';
}
// 返回值為空類(lèi)型,參數(shù)為String,名為qiSay的方法。
void qiSay(String words) {
print(words);
}
// 返回值為空,參數(shù)為空的,名為qiSay方法。
void qiAge() {
print(qiAgeNumber());
}
// 返回值為int,參數(shù)為空,名為qiAgeNumber 的方法。
int qiAgeNumber (){
return 1;
}
/**
// 輸出結(jié)果
QiShare Age: 1
*/
參考學(xué)習(xí)資料
推薦文章:
iOS 短信驗(yàn)證碼倒計(jì)時(shí)按鈕
iOS 環(huán)境變量配置
iOS 中處理定時(shí)任務(wù)的常用方法
算法小專(zhuān)欄:貪心算法
iOS 快速實(shí)現(xiàn)分頁(yè)界面的搭建
iOS 中的界面旋轉(zhuǎn)