Flow(二)—— 簡單語法使用

目錄

  • Flow類型推斷
  • Flow類型註解使用的地方
  • Flow Type Annotationscss

    • 類型參考網址
    • 原始類型
    • 數組類型node

      • 元組 —— Tuple Types
    • 對象類型git

      • 通用寫法
      • 添加可選屬性
      • Map類
      • 混合使用
    • 函數類型github

      • 函數參數
      • 可選函數參數
      • Rest參數
      • 函數返回
    • 特殊類型segmentfault

      • 字面量類型
      • maybe類型
    • Mixed 與 Any數組

      • Mixed
      • Any
      • 二者的區別
  • Flow運行環境API
以前寫了 Flow的相關介紹,若是想回顧的參考 Flow(一)—— JavaScript靜態類型檢查器 ,這裏簡單的介紹 Flow的語法,瞭解 Flow的意義是在第三方源碼中能夠看到 Flow的使用狀況,能夠幫助咱們更好的瞭解源碼。

Flow類型推斷

沒有執行變量類型,可是能夠根據代碼的使用狀況推斷類型,就叫類型推斷瀏覽器

// @flow
// 由於字符串不能進行乘法運算,因此也會報錯
 function square (n) {
   return n * n
 }

 square('100')

不過雖然有類型推斷,可是建議開發者每一個都添加類型,這樣有可讀性。安全

Flow類型註解使用的地方

絕大多數flow均可以推斷出變量類型,可是並不意味着咱們不須要給每一個變量添加類型註解。添加類型註解能夠明確去限制類型,並且對咱們以後理解這裏的代碼頗有幫助,建議儘量的去使用類型註解app

  • 類型能夠標註的地方dom

    • 函數參數
    • 變量
    • 函數返回值
// @flow
// 函數參數標註類型註解
function square (n: number) {
   return n * n
}

// 變量標註類型註解
let num: number = 100

// 函數返回值標註類型註解
function foo (): number {
   return 100
}
// 上面那種狀況,若是沒有返回值,默認返回undefind,上面也會報錯
// 因此若是沒有返回值,須要將返回類型標記爲void
function foo1 (): void {
   
}

Flow Type Annotations

類型參考網址

原始類型

// @flow

 // 字符串
 const a: string = 'foobar'

 // 數字
 const b1: number = 100
 const b2: number = NaN
 const b3: number = Infinity // 無窮大

 // 布爾
 const c1: boolean = true
 const c2: boolean = false

 // null
 const d: null = null

 // undefined
 const e: void = undefined

 // symbol
 const f: symbol = Symbol()

數組類型

// @flow
// 寫法一:Array後面要添加泛型參數,number指定所有由數字組成的數組,若是有其餘類型就會報錯
 const arr1: Array<number> = [1, 2, 3]
 const arr2: Array<mixed> = [1, true, "three",{a:'1',b:2}]
// 寫法二:
 const arr3: number[] = [1, 2, 3]

除了這種數組寫法,還有一種特殊的固定長度的數組,咱們稱爲 —— 元組

元組 —— Tuple Types
  • 固定長度數組,若是改變長度會報錯
  • 下標對應的元素必須是規定類型,設置新值得時候也必須匹配
  • 元組不匹配Array類型,由於數組類型長度不肯定
  • 不能再元組上使用變異數組的方法,例如:copyWithinfillpoppushreverseshiftsortspliceunshift
// @flow
// 元組 —— 固定長度的數組
 // 下面的數組規定了兩個元素,若是改變長度就會報錯,並且下標對應的元素必須是規定的類型
 const arr4: [string, number] = ['foo', 100]
 arr4[2] = 1 // Cannot assign `1` to `arr3[2]` because  tuple type [1] only has 2 elements, so index 2 is out of bounds.
 const item0: string = arr4[0] // Works!
 const item1: number = arr4[0] // Cannot assign `arr3[0]` to `item1` because  string [1] is incompatible with  number [2]

對象類型

通用寫法

肯定一個對象中鍵值有哪些,而且每一個是什麼類型

// @flow
 const obj1: { foo: string, bar: number} = { foo: 'string', bar: 100}
 
// 若是訪問了obj1中沒有的屬性,原來會返回undefined,如今直接當作類型報錯
 obj1.baz // Cannot get `obj1.baz` because property `baz` (did you mean `bar`?) is missing in  object type [1]
添加可選屬性

可選屬性能夠是undefined或者省略,可是不能是null

// foo若是無關緊要,那麼在foo後面加一個問號
 // 可選屬性能夠是undefined或者省略,可是不能是null
 const obj2: { foo?: string, bar: number} = { bar: 100}
 obj2.foo = undefined // Works!
 obj2.foo = null // Cannot assign `null` to `obj2.foo` because  null [1] is incompatible with  string [2]
Map類

鍵的類型用方括號

// 初始化爲空,能夠本身添加鍵值對,規定鍵是string類型,值也是string類型
 const obj3: { [string] : string } = {}

 obj3.key1 = 'value1'
 obj3.key2 = 100 // annot assign `100` to `obj3.key2` because  number [1] is incompatible with  string [2]
混合使用

Map類和普通能夠混合使用

// @flow
var obj: {
  size: number,
  [id: number]: string
} = {
  size: 0
};

function add(id: number, name: string) {
  obj[id] = name;
  obj.size++;
}

函數類型

通常是指參數類型和返回值類型進行類型註解

函數參數
// @flow

// 參數輸入肯定類型
 function square (n: number) {
   return n * n
 }
可選函數參數
function func1 (num?: number) {
    const n = num ? num : 1
    console.log(n)
 }

 func1()  // 1  能夠接受undefined,不能接受null
 func1(2) // 2
 func1(null) // Error!
Rest參數
// @flow
function method(...args: Array<number>) {
  // ...
}

method();        // Works.
method(1);       // Works.
method(1, 2);    // Works.
method(1, 2, 3); // Works.
函數返回
// 返回值肯定類型
 // 有返回值
 function foo (): number {
   return 100
 }
 // 無返回值
 function foo1 (): void {
   
 }

// 回調函數參數和返回值類型 
 function func (callback: (string, number) => void) {
   callback('string', 100)
 }

 func(function (str, n) {
   // str => string
   // n => number
   // 無返回值
 })

特殊類型

字面量類型

與傳統類型不一樣,這種字面量類型必須限制變量必須是某個值,通常不會單獨使用,會配合 聯合類型 去組合幾個特性的值

// @flow
// 下面定義了n字面量,值只能是存放foo字符串,不能換成別的字符串和別的類型
const n: 'foo' = 'foo'
// 只能是下面三個字符串類型中的一種(下面的就是聯合類型,也成或類型)
const type : 'success' | 'warning' | 'danger' = 'success'
// b變量既能夠是string也能夠是number,能夠是字符串也能夠是數字
const b: string | number = 'string' // 100 


// 也能夠本身定義一個類型,StringOrNumber是一個類型的別名
type StringOrNumber = string | number
const test: StringOrNumber = 'string' // 100
maybe類型

有可能,在基本類型的基礎上擴展了nullundefined的類型

// @flow
// 添加?能夠使用null和undefined
const gender: ?number = null
const gender1: ?number = undefined
const gender2: ?number = 100

// 相等於下面的number或null或undefined
const gender: number | null | void = undefined

Mixed 與 Any

Mixed

Mixed能夠接收任意類型的值,是全部類型的聯合類型string | number | boolean | ...

// 參數是mixed類型
function passMixed (value: mixed) {
  console.log(value)
}

passMixed('string') // string
passMixed(100) // 100
Any

Mixed同樣,能夠接收任意類型的值

function passAny (value: any) {
    console.log(value)
}

passAny('string') // string

passAny(100) // 100
二者的區別
  • Mixed是一個強類型,若是有使用隱患的話就會報錯,只能用typeof進行類型判斷
  • Any是一個弱類型,若是有使用隱患,語法上不會報錯。
  • Mixed是安全的(推薦使用),Any是不安全的,存在的意義是爲了兼容老代碼
// Mixed
// 若是沒有明確這個變量是字符串仍是數字,那麼不能直接進行使用的,會報錯
function passMixed (value: mixed) {
  console.log(value)
  value = value ** 2 // Cannot perform arithmetic operation because  mixed [1] is not a number.
}

// 若是想要 解決上面的問題,須要使用typeof進行類型判斷
function passMixed (value: mixed) {
  if (typeof value === 'string') {
    value.substr(1)
  }
  if (typeof value === 'number') {
    value ** 2
  }
}
// Any
// 下面語法上是不會報錯的, 運行階段不肯定
function passAny ( value: any) {
  value = value ** 2
}

Flow運行環境API

JavaScript須要運行在某個環境中,例如:瀏覽器環境或者node環境。
他們有自己本身的API,如瀏覽器中的DOMBOMnode中的path等,咱們在flow中也會使用到這些對象。

那麼這些有特殊的類型限制,例如:

document.getElementById() //裏面參數傳字符串,數字會報錯
// 這是瀏覽器環境內置的API的一些限制
document.getElementById('app') //返回對應的類型是HTMLElement
// 若是沒有找到對應元素,也返回null類型,那麼接收的時候能夠這麼寫
const element: HTMLElement | null = document.getElementById('app')

右鍵跳到定義能夠看到,原生裏面有定義

官網倉庫給出了一些類型聲明,開發的時候能夠參考使用

相關文章
相關標籤/搜索