首页 > 解决方案 > 使用枚举索引对象

问题描述

我有以下结构;

import data from "../data.min.json";

export enum TileType {
  tree = 'tree',
  rock = 'rock'
}

interface MapTile {
  walkable: boolean;
  positions: number[][];
}

export type MapTiles =  {
  [key in TileType]: MapTile
}

export interface Level1 {
  mapTiles: MapTiles;
}

export interface RootObject {
  level_1: Level1;
}

export default data as RootObject;

这工作正常。但是,当我尝试这样使用它时;

const entries = Object.entries(data.level_1.mapTiles);
entries.forEach(([tileType, data]) => {
  
})

tileType 的值是一个字符串,而不是一个 Enum。我怎样才能得到枚举值呢?

数据结构:

{
  "level_1": {
    "mapTiles": {
      "tree": {
        "walkable": false,
        "positions": [
          [ 0, 0 ], [ 0, 40 ], [ 0, 80 ]]
      },
      "rock": {
        "walkable": false,
        "positions": [
          [2, 4], [5, 7]
        ]
      },
    }
  }
}

标签: javascriptjsontypescript

解决方案


这与Object.entriesin 的类型有关lib.esXXX.object.d.ts例如lib.es2017.object.d.ts打字看起来像这样:

entries<T>(o: { [s: string]: T } | ArrayLike<T>): [string, T][];

如您所见,key假定为字符串。如果您改为这样更改它,事情将按您的预期工作:

entries<T, U extends keyof T>(o: T): [U, T[U]][];

现在您显然不想更新标准库上的类型 - 因此您可以创建自己的类型化函数,如下所示:

const objectEntries = <T, U extends keyof T>(inputObject: T) => {
  return Object.entries(inputObject) as [U, T[U]][]
}

使用它你应该得到你正在寻找的类型,并且

objectEntries(data.level_1.mapTiles).forEach(([
  tileType, // correctly inferred as "tree" | "rock"
  data
]) => {})

在此处输入图像描述


推荐阅读