ts基礎(chǔ)

ts的優(yōu)點(diǎn):靜態(tài)編譯提示錯(cuò)誤,強(qiáng)類型,接口和繼承,是js的超集,需要編譯后執(zhí)行

編譯

1、ts后綴建立文件后通過(guò)tsc進(jìn)行指定文件的編譯,不帶任何輸入文件的情況下調(diào)用tsc,編譯器會(huì)從當(dāng)前目錄開始去查找tsconfig.json文件,逐級(jí)向上搜索父目錄。
2、不帶任何輸入文件的情況下調(diào)用tsc,且使用命令行參數(shù)--project(或-p)指定一個(gè)包含tsconfig.json文件的目錄。
3、當(dāng)命令行上指定了輸入文件時(shí),tsconfig.json文件會(huì)被忽略。
4、直接通過(guò)ts test.ts會(huì)生成對(duì)應(yīng)的js文件
5、通過(guò)sudo npm install ts-node -g --save --unsafe-perm=true --allow-root安裝依賴 可通過(guò)ts-node test.ts直接執(zhí)行
6、通過(guò)配置vscode實(shí)現(xiàn)執(zhí)行tsc --init 生成文件 tsconfig.json,修改路徑和添加watch監(jiān)聽實(shí)現(xiàn)自動(dòng)監(jiān)控ts文件生成js: https://www.cnblogs.com/liangyy/p/12436720.html

tsconfig.json配置文件

配置示例

{
    "extends": "./configs/base",
    "compilerOptions": {
        "module": "commonjs",
        "noImplicitAny": true,
        "removeComments": true,
        "preserveConstEnums": true,
        "sourceMap": true,
        "types" : ["node", "lodash", "express"],
        "typeRoots" : ["./typings"]
    },
    "files": [
        "core.ts",
        "sys.ts",
        "types.ts"
    ],
    "include": [
        "src/**/*"
    ],
    "exclude": [
        "node_modules",
        "**/*.spec.ts"
    ]
}
  • extends 拓展配置文件 引入的會(huì)覆蓋當(dāng)前的源文件配置
  • 默認(rèn)配置下會(huì)編譯當(dāng)前目錄以及子目錄下的所有文件 排除可能是輸出文件 支持拓展名為ts tsx d.ts 當(dāng)allowJs設(shè)置為true則包含js jsx拓展名
  • 當(dāng)配置了files之后只會(huì)引入對(duì)應(yīng)的配置下的文件,優(yōu)先于exclude指定的排除文件
  • include和exclude指定匹配模式,支持(匹配0+多個(gè)字符不包含目錄)? (匹配一個(gè)任意字符)*/ (遞歸匹配任意子目錄)
  • 默認(rèn)所有可見的@types包都會(huì)在編譯時(shí)包含進(jìn)來(lái),node_modules/@types文件夾下以及子文件下所有包都是可見的,當(dāng)被置頂了typeRoots則只有被指定的包會(huì)被包含進(jìn)來(lái),指定了types則node_modules/@types下的這些包會(huì)被引入進(jìn)來(lái),可以通過(guò)指定types:[]來(lái)禁用自動(dòng)引入

基礎(chǔ)語(yǔ)法

1、number boolean string null undefined指定五種基本類型,void指定空值可以賦值為null undefined,反之void不可賦值給任何類型;any代表任意類型的值(類似不寫);類型推論,當(dāng)你定義變量的時(shí)候賦值,ts會(huì)根據(jù)你的賦值推出一個(gè)類型,不進(jìn)行賦值則會(huì)默認(rèn)為任意值;聯(lián)合類型:通過(guò)|分隔多個(gè)類型,訪問(wèn)屬性/方法時(shí)只能是共有的,當(dāng)賦值后則會(huì)類型推斷
2、接口:通過(guò)interface關(guān)鍵字進(jìn)行定義,?可選屬性、[propName: type] 自定義屬性(自定義屬性后,其他屬性必須為自定義屬性的子類)、readonly只讀屬性

  • 接口描述了ts種復(fù)雜的類型結(jié)構(gòu),接口繼承自類的時(shí)候繼承了它的成員但是沒有繼承實(shí)現(xiàn),所以接口的功能只能由子類來(lái)實(shí)現(xiàn)。

3、數(shù)組類型number[]或者Array<number>;也可以通過(guò)接口定義(復(fù)雜),其他類數(shù)組類型有自己的類型定義如IArguments NodeList
4、函數(shù)有兩種定義方式,通過(guò)?進(jìn)行可選參數(shù)定義,只能寫在最后,如果是寫了默認(rèn)值的參數(shù),ts認(rèn)為是可選參數(shù),且無(wú)位置要求,通過(guò)解構(gòu)獲取剩余參數(shù),也可進(jìn)行定義
5、斷言 as語(yǔ)法:只要A兼容B或者B兼容A,就可以互相斷言,子類可以被斷言為一個(gè)父類,父類斷言可以為子類,是因?yàn)樽宇惏割惖乃袑傩裕梢栽L問(wèn)到父類的內(nèi)容
6、聲明文件一種是放在源碼里,通過(guò)types指定文件目錄;一種是補(bǔ)充到type庫(kù),最后是自己實(shí)現(xiàn).d.ts文件
7、type指定類型別名,類型約束
8、元組,賦值時(shí)需要匹配,可單獨(dú)賦值,可越界為聯(lián)合類型
9、enum 枚舉類型可以手動(dòng)覆蓋;可以包含計(jì)算值,下一個(gè)加一; 常數(shù)枚舉類型不可計(jì)算,外部枚舉類型 declare
10、類:public private protected abstract,抽象類必須被子類實(shí)現(xiàn)
11、接口繼承類:ts中的類在聲明時(shí)同時(shí)創(chuàng)建了一個(gè)同名的類型,它包含了屬性和方法,沒有constructor和static屬性,接口繼承時(shí)繼承了這部分類型,類似繼承了類生成的實(shí)例

類 接口 函數(shù)的用法

1、類 跟es6中的類差不多,添加了修飾符:public protected private,以及readonly;如果是抽象類abstract則不能直接實(shí)例化,抽象類中的抽象屬性和方法必須被子類實(shí)現(xiàn),類和接口很像,他們的區(qū)別在于:

  • 類通過(guò)class實(shí)現(xiàn),通過(guò)extends繼承被子類繼承;接口是通過(guò)interface定義,被類所實(shí)現(xiàn)
  • 類的方法可以自己實(shí)現(xiàn),抽象類子類必須實(shí)現(xiàn);接口則是一組規(guī)則的定義
  • 類通常是對(duì)一個(gè)類別的公共部分做抽象,有規(guī)律;接口只是抽象,可能并無(wú)關(guān)聯(lián)

2、接口:接口中可以定義可選屬性,索引屬性,只讀屬性;也支持定義函數(shù)以及構(gòu)造函數(shù)的類型

  • 函數(shù)重載 根據(jù)不同的參數(shù)個(gè)數(shù)指定不同的類型
  • this指向 由于運(yùn)行時(shí)才能確定this指向,在ts中可以進(jìn)行手動(dòng)的this指向

3、泛型 通過(guò)T來(lái)代指當(dāng)運(yùn)行時(shí)才能確認(rèn)的類型,難點(diǎn)在于結(jié)合keyof和T<k>使用
4、兼容 如A=B,協(xié)變是B包含A,逆變是A包含B,雙向協(xié)變是沒有規(guī)則
對(duì)象、函數(shù)返回值、類中采用的是協(xié)變
函數(shù)參數(shù)個(gè)數(shù)的兼容采用的是逆變
函數(shù)參數(shù)的兼容和泛型用的是雙向協(xié)變

function greeter(person:string) {
    return "Hello, " + person;
}

let user = ["Jane User"];

// document.body.innerHTML = greeter();
let u: void
// let num: number = u
let anyThind: any = 'hello'
console.log(anyThind.myName)
let from: string|number
from.toString()
from.length
from = 'z'
from.length

interface Person {
    name: string
    age: number
}

let child:Person = {
   name: 'zz',
   age: 12
}
interface Person {
    readonly id:number
    name: string
    age?:number
    [propName: string]: string|number
}
let child1: Person = {
    id:1,
    name: 'z',
    class: 1
}
child1.id = 2
// 數(shù)組
let list: number[] = [1]
let list2: Array<number> = [2]
interface IList {
    [index:number]: number,
    length:number,
    callee: Function
}
function sum() {
    let args: IList = arguments
}

// 函數(shù)
function myName(x:number,y:number, ...items: any[]): number {
   return x+y  
}
let mySum: (x:number, y:number) => number = function(x:number, y:number):number {return x+y}
// 函數(shù)重載
function reverse(x:number): number
function reverse(x:string): string
function reverse(x: string|number): number| string {
    return x
}
// 斷言和聲明
interface Animal {
    name: string
}
interface Cat {
    name: string,
    voice: string
}
let animal:Animal = {
    name: 'tom'
}
// 斷言只需要有互相包含的關(guān)系
let bai = animal as Cat
// 賦值必須滿足前者兼容后者
let baige2:Cat = {
    name: 'baige',
    voice: 'miao'
}
let baige:Cat = animal //失敗
// 類型別名
type stringName = string
let names: stringName = 'owo'
// 類型約束
type EventNames = 'click' | 'scroll' | 'mousemove'
// 元組
let tom: [string, number]
tom[0]='first'
tom = ['second',0]
tom.push(3)
// 枚舉
enum Days {Sun, Mon, Tue, Wed, Thu, Fri, Sat}
// 類 
abstract class Animals {
    public name;
    public constructor(name) {
        this.name = name
    }
    public abstract voice()
}
class Cats extends Animals {
    public voice() {
        // 必須要實(shí)現(xiàn)抽象類的屬性
    }
}
let miao = new Cats('bai')
// 泛型 后置確定類型 可定義約束
function copyFields<T extends U, U>(target: T, source: U): T {
    for(let id in source) {
        target[id] = (<T>source)[id]
    }
    return target
}
let x = {a:1, b:2}
let y = {b:10}
copyFields(x, y)

最后編輯于
?著作權(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ù)。