首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >类型记录:类型守卫在enum联合上失败

类型记录:类型守卫在enum联合上失败
EN

Stack Overflow用户
提问于 2020-12-02 15:30:19
回答 2查看 197关注 0票数 0

只需阅读Type GuardsTypescript的章节

但是为什么我下面的简单类型的守卫不能区分出一个枚举的结合呢?

代码语言:javascript
复制
enum A {
  COMMA = ',',
  PLUS = '+'
}

enum B {
  REAL = 'REAL',
  STRING = 'STRING'
}

function notWork<T extends A | B>(val: T) {
  if(isA(val)) {
    // mark 1:
    console.log('isA:', useA(val))
  } else  {
    // mark 2: 
    // val should be in type B here !!!
    console.log('isB:', useB(val))
  }
}


function isA(token : A | B): token is A {
  return Object.values(A).includes(token as A)
}

function useA(v: A) {
  console.log("we're using A:", v)
  return v
}

function useB(v: B) {
  console.log("we're using B:", v)
  return v
}

据我理解:

  1. 在标记1中,val实际上是类型:(T & A.COMMA) | (T & A.PLUS)。这很有效,但是为什么它不是一个简单的A
  2. 在马克2,瓦尔仍然是A | B,为什么我的类型警卫失败?

TS游乐场

EN

回答 2

Stack Overflow用户

发布于 2020-12-02 15:37:16

这是因为isA(x) === false并不意味着x是一个B,只是它不是一个A

代码语言:javascript
复制
+ 

enum C {
  FOO = 'FOO',
  BAR = 'BAR'
}

+

function notWork<T extends A | B>(val: T) { // yes, not A | B | C

+

function isA(token : A | B | C): token is A {

+

结果相同类型的错误,但现在很清楚为什么isA并不意味着它是一个B,不能是一个C

您的isA方法可以将任何类型的联合作为参数。它不同于T in notWork

现在,如果您突然之间传递这两种类型,编译器就会知道,任何不是TA都必须是B

代码语言:javascript
复制
+

type T = A | B

+

function notWork(val: T) {

+

function isA(token : T): token is A {

+

这是我的第一个操场。 还有第二个。

票数 0
EN

Stack Overflow用户

发布于 2020-12-02 15:51:48

更改签名:

代码语言:javascript
复制
function notWork<T extends A | B>(val: T) { // ...

至:

代码语言:javascript
复制
function notWork(val: A | B) { // ...

它会像你预期的那样起作用。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/65111136

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档