TS初學筆記

整理之前學習ts時的一些筆記。


安裝
npm install -g typescript // 報無權限 
sudo npm install -g typescript 
tsc -v // tsc,ts編譯器,查看版本
// hello.ts 
const hello = (name:string)=>{ return `hello ${name}` } 
hello('yuki')
tsc hello.ts  //編譯 ===> 生成 hello.js
tsc -w hello.ts //監(jiān)聽hello.ts 的變化
node hello.js //運行 js 文件

或者安裝 ts-node ,將以上兩步合并為一步 ts-node hello.ts

編譯后,函數(shù)會出現(xiàn)(2393)函數(shù)實現(xiàn)重復,猜測可能是vscode的bug(不確定)
在項目根目錄添加配置文件 tsconfig.json即可(空文件也可)


基礎類型
let isDone: boolean = false;
let age: number = 18; 
let firstName: string = "yuki"; 
let message: string = `Hello,${firstName},age is ${age}`; 
let u: undefined = undefined; 
let n: null = null; 
let num: number = undefined;
any 和 聯(lián)合類型
let notSure: any = 4; 
notSure = "a string"; 
notSure = true; 
notSure.getName(); 

let numberOrString: number | string; 
numberOrString = "hhh"; 
numberOrString = 1;
數(shù)組Array 和 元祖Tuple
// 數(shù)組 Array 
let arrOfNumbers: number[]=[1,2,3] 
arrOfNumbers.push(5) 

// 元祖 Tuple
let user:[string,number]=['1',3]
interface 接口

對象的形狀(shape)進行描述
類(class)進行抽象

interface Person { 
  readonly id:number, // readonly 用于對象屬性,不允許修改該值 
  name: string; 
  age?: number; // ? 表示 非必須 
} 
let yuki: Person = { 
  id:1111, 
  name: "yuki",
  age: 20, // 此處允許不加age 
};
 yuki.id = 2222 // error , id readonly,不允許修改
函數(shù) 和 類型推斷

如下,
z 為可選參數(shù)。需要注意,必選參數(shù) 必須放在 可選參數(shù) 之前,否則報錯
或者用es6的寫法, z:number = 0 ,不傳的話默認為0

// function add ():number{} 此處的number 規(guī)定了輸出的類型為number
function add(x:number,y:number,z?:number):number{ 
  if(typeof z ==='number'){ 
    return x+y+z 
  } 
  return x+y 
} 
let result1 = add(1,2,3) 
let result2 = add(1,2)

注意,下圖中,不是es6中的箭頭函數(shù)。而是tsc(ts編譯器)的 類型推斷

image.png
let str= 'str' 
str= 123 // error , 因為ts推斷出 str 是string類型
Class 類

默認是public,允許外部和子類訪問
private 不允許外部和子類訪問
protected 不允許外部訪問,允許子類訪問
readonly 可訪問,不可修改

class Animal { 
  private name:string 
  constructor(name:string){ 
    this.name=name
  }
} 
const snake = new Animal('lili') 
console.log(snake.name) // error,外部不允許訪問 
snake.name='lucy' // error,外部不允許訪問 

class Dog extends Animal { 
  break() { 
    return `${this.name} is barking`; // error 子類同樣無法訪問
  }
 }

子類繼承父類,復雜場景時可能無法滿足需求,故,可用接口interface提供公共部分
類可以同時繼承多個接口,implements (類繼承接口就必須實現(xiàn)這個接口里面寫的方法)
接口可以繼承接口,extends

interface Radio { 
  switchRadio():void // void 什么都不返回
} 
interface Battery{ 
  checkBatteryStatus() 
} 

// 方法一:CellPhone 同時implements Radio,Battery 
class Car implements Radio { 
  switchRadio(){ } 
} 
class CellPhone implements Radio,Battery{ 
  switchRadio(){ } 
  checkBatteryStatus(){ } 
} 

// 方法二:RadioWithBattery 繼承 Radio, CellPhone implements RadioWithBattery 
interface RadioWithBattery extends Radio{ 
  checkBatteryStatus(){ } // 繼承了Radio的switchRadio(){ } ,并添加checkBatteryStatus(){ } 
}
class CellPhone implements RadioWithBattery{ 
  switchRadio(){ } 
  checkBatteryStatus(){ } 
}
Enum 枚舉

默認從0開始賦值,每個值自動遞增
也可以自行賦值,numberstring 等均可

enum Direction { 
  Up, // 若 賦值 Up=10,則Down為11, Direction[10]為Up 
  Down,
  Left,
  Right
} 
console.log(Direction.Up) // 0 
console.log(Direction[0]) // 'Up'   雙向

編譯后,可發(fā)現(xiàn)轉為js后,是一個自執(zhí)行函數(shù)

// js 
var Direction; 
(function (Direction) { 
  Direction[Direction["Up"] = 0] = "Up";
  Direction[Direction["Down"] = 1] = "Down"; 
  Direction[Direction["Left"] = 2] = "Left";
  Direction[Direction["Right"] = 3] = "Right"; 
})(Direction || (Direction = {}));

常量枚舉(加const)

const enum Direction { 
  Up = 'up', 
  Down = 'down' 
} 
const value = 'up' 
console.log(value === Direction.Up) // true

編譯后:

// js 
var value = "up"; 
console.log(value === "up" /* Up */);

常量枚舉成員在使用的地方會被內(nèi)聯(lián)進來,
之所以可以這么做是因為,常量枚舉不允許包含計算成員;
如上,編譯時,并沒有 Direction 變量的,因此常量枚舉會對性能有一定提升。

泛型 (一)

如下,自定義一個泛型T,函數(shù)入?yún)㈩愋蚑,出參同樣T(使入?yún)⒊鰠⒈3忠粯拥念愋停?br> 當入?yún)閟tring,出參同樣是string;入?yún)閚umber,出參同樣number

function echo<T>(arg: T): T {
  return arg;
} 
const res = echo("str"); 

function swap<T, U>(tuple: [T, U]): [U, T] { 
  return [tuple[1], tuple[0]]; 
} 
const res2 = swap(["str", 123]);
泛型(二):約束泛型
interface IwithLength { length: number; } // 入?yún)⒈仨毎?length屬性
function echoWithLength<T extends IwithLength>(arg: T): T {
  console.log(arg.length); 
  return arg; 
} 
const arr = echoWithLength([1, 2]); 
const obj = echoWithLength({ x: 1, length: 1 }); 
const str = echoWithLength('hhh')
泛型(三):類和接口
class Queue<T> { 
  private data = []; 
  push(item: T) { 
    return this.data.push(item);
  } 
  pop(): T { 
    return this.data.shift(); 
  } 
} 

const queue = new Queue<number>(); 
queue.push(1); 
console.log(queue.pop().toFixed()); 

const queue2 =new Queue<string>() 
queue2.push('str') 
console.log(queue2.pop())
interface Iplus<T> { 
  (a: T, b: T): T; // 函數(shù),入?yún)⒁缓腿雲(yún)⒍門,出參為T 
} 
function plus(a: number, b: number): number { 
  return a + b; 
} 
function connect(a: string, b: string): string { 
  return a + b; 
} 
const num: Iplus<number> = plus; 
const str: Iplus<string> = connect;

當我新建另一個ts文件:

let isDone: boolean = false 
//報錯,提示 'isDone' was also declared here.

在默認狀態(tài)下,typescript 將 DOM typings 作為全局的運行環(huán)境,
當我聲明 isDone 時, 與 DOM 中的全局 window 對象下的isDone屬性出現(xiàn)了重名。

解決方法:在腳本文件最后一行,添加 export {}; 將文件聲明為模塊
(在 Typescript 中,只要文件存在 import 或 export 關鍵字,都被視為 module)


類型別名

使用關鍵字type,多用于聯(lián)合

type PlusType = (x: number, y: number) => number; 
function sum(x: number, y: number): number { 
  return x + y; 
} 
const sum2: PlusType = sum; // 代替 const sum2: (x: number, y: number) => number = sum
類型斷言

通過類型斷言這種方式告訴編譯器類型,只在編譯階段起作用

let someVal: any = 'str' 
let strLength: number = (<string>someVal).length // 尖括號 
let strLength2: number = (someVal as string).length // JSX 只可使用as語法斷言
聲明文件

https://www.runoob.com/typescript/ts-ambient.html

目的:為了借用 TypeScript 的各種特性來使用第三方庫文件
(declare 定義的類型只會用于編譯時的檢查,編譯結果中會被刪除。)

如,

declare var jQuery:(selector:string)=>any

把這些聲明單獨放在一個文件,稱為聲明文件,以 .d.ts 為后綴,如 jQuery.d.ts
一般而言,所有ts文件都可獲得這些類型定義,若無法獲取,可在根路徑的tsconfig.json中配置tsc編譯器

{ "include":["**/*"] }

DefinitelyTyped (http://definitelytyped.org/
該組織提供了各類聲明文件,安裝即可,無需自己創(chuàng)建聲明文件

npm install --save-dev @types/jquery
?著作權歸作者所有,轉載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。

相關閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容