繁体   English   中英

如何根据object属性值应用接口

[英]How to apply the interface according to the object property value

我通过总结文章的内容再次写了它。

我想知道如何根据 object 属性值应用接口。

我在下面写了一个简单的示例代码。

一共有三个节点:root、dept、user。

指定每个节点对应的类型。 因此,我们希望根据 object 类型属性指定接口。

但是,您可以看到您正在手动确认类型,因为您还没有找到解决方案。

为了解决这个问题,我认为应该用索引类型而不是条件类型来解决。

原因是条件类型是期望根据泛型类型参数计算返回的,但是当前的问题应该是根据现有类型计算而不是接收类型参数。

但是,即使使用两种方法也无法解决问题。 任何帮助将不胜感激♂️

export enum NodeType {
  root = "root",
  dept = "dept",
  user = "user",
}

interface Node {
  readonly type: NodeType;
  title: string;
}

interface RootNode extends Node {
  type: NodeType.root;
}

interface DeptNode extends Node {
  type: NodeType.dept;
  departmentCode: string;
}

interface UserNode extends Node {
  type: NodeType.user;
  employeeNumber: string;
}

const nodeData: Node[] = [
  {
    type: NodeType.root,
    title: "Company 1",
  } as RootNode,
  {
    type: NodeType.dept,
    title: "Department 1",
    departmentCode: "557",
    // The type is not inferred according to the object property type, so the type must be explicitly asserted.
  } as DeptNode,
  {
    type: NodeType.user,
    title: "User 1",
    employeeNumber: "201911",
  } as UserNode,
];

// I want to be the type of DeptNode interface because the type of object property is NodeType.dept.
const selectDept = nodeData.filter((x) => x.type === NodeType.dept);
selectDept.forEach((x) => {
  console.log({
    type: x.type,
    title: x.title,
    // The type is not affirmed in the node that fits the object property type, so you have to affirm the type yourself.
    departmentCode: (x as DeptNode).departmentCode,
  });
});

我知道如何使用type s,而不是interface s。

您的尝试有两个问题:

  1. 通过使用类型,您可以利用区分联合(注意Node类型作为三种可能情况的联合)。
  2. 对于filterforEach等数组方法,推断算法不够聪明,无法理解请求的类型,因此您必须使用简单forif

这里我们 go:

export enum NodeType {
    root = "root",
    dept = "dept",
    user = "user",
}

type NodeBase = {
    readonly type: NodeType;
    title: string;
}

type RootNode = NodeBase & {
    type: NodeType.root;
}

type DeptNode = NodeBase & {
    type: NodeType.dept;
    departmentCode: string;
}

type UserNode = NodeBase & {
    type: NodeType.user;
    employeeNumber: string;
}

type Node = RootNode | DeptNode | UserNode;

const nodeData: Node[] = [
    {
        type: NodeType.root,
        title: "Company 1",
    },
    {
        type: NodeType.dept,
        title: "Department 1",
        departmentCode: "557",
        // The type is not inferred according to the object property type, so the type must be explicitly asserted.
    },
    {
        type: NodeType.user,
        title: "User 1",
        employeeNumber: "201911",
    },
];

// I want to be the type of DeptNode interface because the type of object property is NodeType.dept.
for (const x of nodeData) {
    if (x.type === NodeType.dept) {
        console.log({
            type: x.type,
            title: x.title,
            // The type is not affirmed in the node that fits the object property type, so you have to affirm the type yourself.
            departmentCode: (x as DeptNode).departmentCode,
        });
    }
}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM