typescript基本使用筆記
安裝typescript
npm install -g typescript
全局安裝ts
tsc *.ts
編譯ts文件編譯成js文件,如果ts有語法錯(cuò)誤,則會(huì)編譯報(bào)錯(cuò)碑幅,但是仍然會(huì)創(chuàng)建編譯好的js文件并且編譯執(zhí)行
基礎(chǔ)類型
定義變量或者參數(shù)的時(shí)候通過 :
號(hào)指定類型
-
boolean 布爾型
-
number 數(shù)字型:包括各種進(jìn)制的數(shù)值型质蕉,浮點(diǎn)型
-
string 字符串類型:可以使用模板字符串
-
number[]/Array<number> 數(shù)組類型:寫法有兩種一種是number后面加
[]
废士,一種是通過數(shù)組Array 泛型
-
tuple :一個(gè)已知元素長(zhǎng)度和類型的數(shù)組灶搜,且類型不能重復(fù)沧侥,
屬于聯(lián)合類型
-
enum 枚舉類型:使用枚舉類型可以為一組數(shù)值賦予友好的名字善玫,一種類似數(shù)組的引用類型形式水援,可以通過下標(biāo)訪問和賦值,也可以指定下標(biāo)
-
any :任意類型茅郎,不會(huì)進(jìn)行類型檢查蜗元,任意類型都可以通過,可以組和系冗,比如
any[]
表示任意元素類型的數(shù)組 -
void : 空類型奕扣,通常用來表示無返回值,
只能夠賦值為:undefined和null
-
null和undefined :默認(rèn)是所有類型的子集掌敬,意思是所有其他類型都可以賦值成null和undefined類型
-
never :不應(yīng)該運(yùn)行到此處的類型惯豆,
-
object :非原始類型,除了
string,number,boolean,null,undefined,symbol
這幾個(gè)js的基本類型 類型斷言(類型轉(zhuǎn)換):語法為 let someValue :any = 'Word' 可以強(qiáng)行將右邊轉(zhuǎn)為左邊 ;另一個(gè)方法是'as'語法奔害,let strLength: number = (someValue as string).length;
變量聲明
-
let和var的區(qū)別(略)
-
解構(gòu) --快速的變量賦值
//---------------數(shù)組解構(gòu)---------------------
// 數(shù)組解構(gòu)
let input = [1, 2];
let [first, second] = input;
console.log(first); // outputs 1
console.log(second); // outputs 2
//剩余變量的數(shù)組解構(gòu)
let [first, ...rest] = [1, 2, 3, 4];
console.log(first); // outputs 1
console.log(rest); // outputs [ 2, 3, 4 ]
//對(duì)應(yīng)下標(biāo)的數(shù)組解構(gòu)
let [, second, , fourth] = [1, 2, 3, 4];
//------------------對(duì)象解構(gòu)---------------
let o = {
a: "foo",
b: 12,
c: "bar"
};
let { a, b } = o;
//快速的將o對(duì)應(yīng)的鍵值賦給a,b
let { a, ...passthrough } = o;
let total = passthrough.b + passthrough.c.length;
//剩余變量的對(duì)象解構(gòu)
let { a: newName1, b: newName2 } = o;
//變量重命名楷兽,此處相當(dāng)于{a,b}=0 newName1 = a,newName2 = b;
//此處的:相當(dāng)于賦值符號(hào)
//為什么這里的:不是類型聲明符號(hào)?
//因?yàn)椋航鈽?gòu)時(shí)如果需要類型聲明需要完整的寫類型模式
//例如:let {a, b}: {a: string, b: number} = o;
function keepWholeObject(wholeObject: { a: string, b?: number }) {
let { a, b = 1001 } = wholeObject;
//解構(gòu)時(shí)的默認(rèn)值,如果不存在b這個(gè)鍵值時(shí)华临,b=1001
}
//--------------函數(shù)聲明-----------------------
type C = { a: string, b?: number }
function f({ a, b }: C): void {
// ...
}
//將解構(gòu)元素當(dāng)作參數(shù)傳遞
function f({ a="", b=0 } = {}): void {
// ...
}
f();
//解構(gòu)傳參帶默認(rèn)值
function f({ a, b = 0 } = { a: "" }): void {
// ...
}
f({ a: "yes" }); // ok, default b = 0
f(); // ok, default to {a: ""}, which then defaults b = 0
f({}); // error, 'a' is required if you supply an argument
//解構(gòu)+默認(rèn)賦值芯杀,默認(rèn)傳入{a:""}如果啥也不傳,默認(rèn)參數(shù)為{a:''},那么a='',b=0
-
展開 --與解構(gòu)相反將數(shù)組展開或者將對(duì)象展開
//所有的展開都是淺拷貝!揭厚!
//將數(shù)組展開并且插入新數(shù)組
let first = [1, 2];
let second = [3, 4];
let bothPlus = [0, ...first, ...second, 5];
//將對(duì)象展開
let defaults = { food: "spicy", price: "$$", ambiance: "noisy" };
let search = { ...defaults, food: "rich" };
//對(duì)象展開會(huì)丟失對(duì)象方法
class C {
p = 12;
m() {
}
}
let c = new C();
let clone = { ...c };
clone.p; // ok
clone.m(); // error!
接口
接口的作用就是為這些類型命名和代碼進(jìn)行綁定却特,接口一般用來做函數(shù)參數(shù)的預(yù)定義
-
關(guān)鍵字 interface
interface LabelledValue {
//定義一個(gè)接口
label: string;
//接口中定義了label這個(gè)字段必須是字符串類型
}
function printLabel(labelledObj: LabelledValue) {
//參數(shù)labelledObj 套用這個(gè)接口,所以參數(shù)必須有l(wèi)abel字段并且為string類型
console.log(labelledObj.label);
}
let myObj = {size: 10, label: "Size 10 Object"};
printLabel(myObj);
-
可選參數(shù)接口
interface SquareConfig {
color?: string; //只是在類型聲明符前面增加了一個(gè)問號(hào)
width?: number;
}
-
只讀屬性
只能在對(duì)象剛創(chuàng)建的時(shí)候?qū)ζ渲颠M(jìn)行修改筛圆,可以在屬性名前面增加
readonly
來指定只讀屬性 -
額外的屬性檢查
interface SquareConfig {
color?: string;
width?: number;
[propName: string]: any;
//使用propName內(nèi)置屬性獲取接口的其他參數(shù)傳值核偿,并且對(duì)其進(jìn)行單獨(dú)的檢查
}
-
函數(shù)類型 接口也能用來描述函數(shù)類型
interface SearchFunc {
(source: string, subString: string): boolean;
//定義了一個(gè)函數(shù)接口,參數(shù)為source和substring類型為string類型顽染,返回值為boolean類型
}
//以下兩種調(diào)用方式都符合邏輯
let mySearch: SearchFunc;
mySearch = function(source: string, subString: string) {
let result = source.search(subString);
return result > -1;
}
let mySearch: SearchFunc;
mySearch = function(src: string, sub: string): boolean {
let result = src.search(sub);
return result > -1;
}
-
可索引的類型 可以自定義接口用來限定可索引類型的類型解構(gòu)
//基礎(chǔ)的引用類型接口
interface StringArray {
[index: number]: string;
//定義一個(gè)索引類型的接口:
//":"左邊表示索引的類型定義漾岳,右邊表示值的類型定義
//所以上面的意思是定義了一個(gè)索引類型的接口,index必須是number類型粉寞,值必須是string類型
//嵌套設(shè)計(jì)
interface NumberDictionary {
[index: string]: number;
//定義了該索引類型的index是string類型尼荆,值是number類型
length: number; // 可以,length是number類型
//legth字段定義成number類型唧垦,length也屬于該索引類型的index捅儒,其值也要是number類型
name: string // 錯(cuò)誤,`name`的類型與索引類型返回值的類型不匹配
//同理振亮,name也是index巧还,該值也必須是number類型
}
}
let myArray: StringArray;
myArray = ["Bob", "Fred"];
let myStr: string = myArray[0];
//只讀索引的接口設(shè)計(jì)
interface ReadonlyStringArray {
readonly [index: number]: string;
//設(shè)定index的類型為只讀類型,值為string類型
}
let myArray: ReadonlyStringArray = ["Alice", "Bob"];
//由于設(shè)置了index的只讀類型坊秸,所以無法進(jìn)行修改
myArray[2] = "Mallory"; // error!
-
類類型 與C#或Java里接口的基本作用一樣麸祷,TypeScript也能夠用它來明確的強(qiáng)制一個(gè)類去符合某種契約。
interface ClockInterface {
currentTime: Date;
//定義了一個(gè)類型型的接口褒搔,其currentTime屬性必須是一個(gè)Date類型
}
class Clock implements ClockInterface {
currentTime: Date;
constructor(h: number, m: number) { }
}
//類類型使用方法如下
interface ClockInterface {
currentTime: Date;
setTime(d: Date);
}
class Clock implements ClockInterface {
//implements為關(guān)鍵字阶牍,表示該類使用ClockInterface這個(gè)接口
currentTime: Date;
setTime(d: Date) {
this.currentTime = d;
}
constructor(h: number, m: number) { }
}
//類靜態(tài)部分和實(shí)例部分的區(qū)別
interface ClockConstructor {
new (hour: number, minute: number);
}
class Clock implements ClockConstructor {
currentTime: Date;
constructor(h: number, m: number) { }
//constructor構(gòu)造函數(shù)里面的參數(shù)為類的靜態(tài)屬性所以不會(huì)適用上面那個(gè)接口的檢測(cè)方法
}
//--------------------復(fù)雜的類類型例子--------------------------------------
interface ClockConstructor {
new (hour: number, minute: number): ClockInterface;
}
interface ClockInterface {
tick();
}
function createClock(ctor: ClockConstructor, hour: number, minute: number):
//聲明一個(gè)函數(shù)
//函數(shù)的參數(shù)接口定義是 ctor的接口是ClockConstructor,hour是number類型星瘾,minute是number
//ClockConstructor又是一個(gè)函數(shù)接口走孽,表示構(gòu)造函數(shù)參數(shù)hour和minute的類型都是number,且必須具有屬性ClockInterface接口琳状,也就是必須有這個(gè)tick屬性或者方法
//通過這樣嵌套磕瓷,達(dá)到對(duì)構(gòu)造函數(shù)靜態(tài)參數(shù)的接口定義
ClockInterface {
//函數(shù)的返回值是ClockInterface這個(gè)接口定義的,必須有tick這個(gè)屬性或者方法
return new ctor(hour, minute);
}
class DigitalClock implements ClockInterface {
constructor(h: number, m: number) { }
tick() {
console.log("beep beep");
}
}
class AnalogClock implements ClockInterface {
constructor(h: number, m: number) { }
tick() {
console.log("tick tock");
}
}
let digital = createClock(DigitalClock, 12, 17);
let analog = createClock(AnalogClock, 7, 32);
-
接口的繼承 和類一樣念逞,接口也可以相互繼承困食。 這讓我們能夠從一個(gè)接口里復(fù)制成員到另一個(gè)接口里,可以更靈活地將接口分割到可重用的模塊里肮柜。
interface Shape {
color: string;
}
interface Square extends Shape {
//關(guān)鍵字extend Square繼承自Shape
sideLength: number;
}
let square = <Square>{};
square.color = "blue";
square.sideLength = 10;
// 一個(gè)接口可以繼承多個(gè)接口陷舅,創(chuàng)建出多個(gè)接口的合成接口。
interface Shape {
color: string;
}
interface PenStroke {
penWidth: number;
}
interface Square extends Shape, PenStroke {
sideLength: number;
}
let square = <Square>{};
square.color = "blue";
square.sideLength = 10;
square.penWidth = 5.0;
-
混合類型 一個(gè)接口可以同時(shí)擁有多種類型接口的特性审洞,實(shí)現(xiàn)該接口的多類型
interface Counter {
//定義一個(gè)接口Counter
(start: number): string;
//擁有函數(shù)接口類型的特性莱睁,定義了參數(shù)和返回值的類型
interval: number;
//同時(shí)定義了對(duì)象類型的特性待讳,可以擁有屬性
reset(): void;
}
function getCounter(): Counter {
let counter = <Counter>function (start: number) { };
counter.interval = 123;
counter.reset = function () { };
return counter;
}
let c = getCounter();
c(10);
c.reset();
c.interval = 5.0;
-
接口繼承類 當(dāng)一個(gè)接口繼承一個(gè)類,會(huì)繼承其類的成員仰剿,但是不包括其實(shí)現(xiàn)创淡,
class Control {
private state: any;
}
interface SelectableControl extends Control {
//該接口繼承自類Control,所以也會(huì)繼承其屬性南吮,包括私有屬性
//所以再次使用該接口的時(shí)候琳彩,會(huì)繼承該私有屬性的定義
select(): void;
}
class Button extends Control implements SelectableControl {
select() { }
}
class TextBox extends Control {
select() { }
}
// 錯(cuò)誤:“Image”類型缺少“state”屬性。
class Image implements SelectableControl {
select() { }
}
class Location {
}
//在上面的例子里部凑,SelectableControl包含了Control的所有成員露乏,包括私有成員state。 因?yàn)?state是私有成員涂邀,所以只能夠是Control的子類們才能實(shí)現(xiàn)SelectableControl接口瘟仿。 因?yàn)橹挥?Control的子類才能夠擁有一個(gè)聲明于Control的私有成員state,這對(duì)私有成員的兼容性是必需的比勉。
//在Control類內(nèi)部劳较,是允許通過SelectableControl的實(shí)例來訪問私有成員state的。 實(shí)際上浩聋, SelectableControl接口和擁有select方法的Control類是一樣的观蜗。 Button和TextBox類是SelectableControl的子類(因?yàn)樗鼈兌祭^承自Control并有select方法),但I(xiàn)mage和Location類并不是這樣的衣洁。