Open9

isで遊ぶ

ishizakitishizakit

isはタイプAをBに変換できる程度の理解だったのでいろいろ遊んで理解を深めたい
ドキュメント読めば分かる話だと思うけど遊びたい!

ishizakitishizakit

このコードをベースにちょこちょこいじって遊ぶ

type A = {
  hoge: string
}

type B = {
  hoge: string
}

const AisB = (v: A): v is B => {
  if (typeof v.hoge === 'string') return true
  return false
}

const convert = (v: A): B => {
  if (AisB(v)) return v
  throw new Error()
}
ishizakitishizakit

名前も型も同じプロパティのタイプに変換できるか

参考のコードそのまま。

IDEでvのreturn時のタイプを見てみたらBになっているので変換できていそう。

ishizakitishizakit

名前が同じで型が異なるプロパティのタイプに変換できるか

参考のコードのAのhogeをnumber型に変更。

type A = {
  hoge: number
}

エラーが発生して変換できない。

ishizakitishizakit

任意のプロパティを必須のプロパティに変換することはできるか

参考のコードのAのhogeを任意に変更。

type A = {
  hoge?: string
}

変換できる。

必須のプロパティを任意のプロパティに変換することはできるか

先ほどとは逆にAは必須のままでBを任意に変更。

type B = {
  hoge?: string
}

エラーが発生して変換できない。

ishizakitishizakit

プロパティを削ったタイプに変換できるのか

参考コードのAにfugaというプロパティを追加。

type A = {
  hoge: string
  fuga: number
}

エラーが発生して変換できない。

プロパティを追加したタイプに変換できるのか

参考コードのBにfugaというプロパティを追加。

type B = {
  hoge: string
  fuga: number
}

変換できる。

ishizakitishizakit

参考コードを変える
AisB()をisB()という引数の型がanyのメソッドに変えたものですすめる

type A = {
  hoge: string
}

type B = {
  hoge: string
}

const isB = (v: any): v is B => {
  if (typeof v.hoge === 'string') return true
  return false
}

const convert = (v: A): B => {
  if (isB(v)) return v
  throw new Error()
}
ishizakitishizakit

参考のコードそのまま。
前の参考コードと同様に名前も型も同じプロパティのタイプに変換できる。

ishizakitishizakit

必須のプロパティを任意のプロパティに変換することはできるか

参考のコードのBのhogeを任意に変更。

type B = {
  hoge?: string
}

変換できない。
前の参考コードのようにエラーは発生しないが、IDEでタイプを見てみるとAのまま。
先程エラーが発生していたのはAisB関数内で互換性の無いAとBを変換しようとしていたのが原因。
AisBの引数をanyにしたisBでは互換性が生まれてエラーは発生しなくなった。