TypeScript 如何做索引签名

你有没有过这样的经历?用 JavaScript 写代码时,想声明一个对象,它的键和值都是不确定的——比如一个用户的动态属性,可能是姓名、年龄、地址,也可能是手机号、邮箱,提前写好固定属性总觉得不够灵活,可没了类型约束,又很容易写错键名、传错值。这时候 TypeScript 的索引签名,就能帮你解决这个“灵活与约束难兼顾”的小麻烦。

先搞懂:什么是索引签名?

咱们用生活化的例子来拆解:假设你开了个小卖部的“商品库存本”,这个本子没有固定要写的条目——今天可能记“矿泉水:20瓶”,明天可能加“冰棒:15根”“辣条:30袋”,后天还能加“充电宝:5个”。你不用提前把所有商品都列出来,只要约定好:所有写在本子上的商品(键),都是字符串;对应的数量(值),都是数字。

TypeScript 如何做索引签名

放到 TypeScript 里,这个“约定”就是索引签名。它允许你声明一个对象,这个对象的键的类型是统一的,值的类型也是统一的,不需要提前把所有键都写死,兼顾了灵活性和类型安全,不会出现“把冰棒的数量写成字符串”这类低级错误。

怎么写索引签名?两步就能上手

索引签名的写法非常直白,就像给对象的键和值定规矩,而且语法也很好记。还是用刚才的小卖部例子,咱们来一步步写:

先定义键和值的类型

第一步,确定你要给对象的键、值定的类型。键一般是字符串(对应生活里的文本条目),也可以是数字(比如用序号当键),值的话根据需求来,比如数字、字符串甚至布尔值都可以。

比如小卖部的例子,键是商品名(字符串),值是库存数(数字),咱们就先定好这俩类型。

用语法写索引签名

TypeScript 里用 [键名: 类型]: 值类型 来写索引签名,把它放在对象类型的声明里就行。完整的小卖部库存类型就是这样:

`typescript

type Inventory = {

// 索引签名:键是字符串,值是数字

[itemName: string]: number;

};

`

你看,itemName 其实就是个占位的名字,你可以换成任何你喜欢的,比如 product 也行,只要后面跟着的类型是键的类型就行。

日常用的小细节,别踩这些坑

索引签名虽然简单,但用的时候有两个小细节要注意,不然容易出错,结合生活例子一看就懂。

第一个细节:如果对象里有固定属性,要和索引签名兼容。

还是小卖部的例子,你想加一个固定属性“总库存”,值是数字,这时候就可以直接写在类型里:

`typescript

type Inventory = {

totalStock: number; // 固定属性

[itemName: string]: number; // 索引签名

};

`

这个时候,你就能用这个类型声明对象了,既可以写固定的 totalStock,也可以加任意的商品键,比如:

`typescript

const myShop: Inventory = {

totalStock: 70, // 固定属性

矿泉水: 20, // 商品条目

冰棒: 15,

辣条: 30,

};

`

这里有个小规则:固定属性的类型,必须能被索引签名的类型兼容。比如如果固定属性 totalStock 是字符串,而索引签名的值是数字,就会报错,就像你给库存本写“总库存:七十”(字符串),又约定所有条目值都是数字,就矛盾了。

第二个细节:索引签名的键只能是 string、number、symbol 这几种。

刚才的例子用的是字符串键,如果你想按序号存商品,比如 1: "矿泉水",那键类型就可以写 number,对应索引签名:

`typescript

type NumberInventory = {

[itemId: number]: string; // 键是数字,值是商品名

};

`

但不能用 boolean 当键,就像你不能给库存本写“true:矿泉水”,这样没实际意义,TypeScript 也不允许这种写法。

举个实用的小场景,加深理解

假设你做了一个简易的通讯录工具,要存朋友的联系方式,每个朋友的联系方式可能是手机号、微信、邮箱,没有固定顺序,也可能随时加新的。用索引签名来做,就能写出类型安全的代码:

`typescript

type ContactBook = {

name: string; // 固定的名字属性

[contactType: string]: string; // 任意联系方式,键是类型(手机号/微信等),值是号码

};

// 符合类型的对象

const myContacts: ContactBook = {

name: "小明",

phone: "138xxxx1234",

wechat: "xiaoming123",

};

`

如果不小心写错,比如把手机号的值写成数字 phone: 138xxxx1234,TypeScript 会直接报错,提醒你值的类型不对,不用等到运行时才发现 bug,这就是索引签名的好处。

是不是不难?核心就是记住:索引签名是给对象的“动态键和值”定统一类型的规则,既不用提前写死所有属性,又能避免类型错误,日常做动态对象的时候用它,就能兼顾灵活和靠谱啦。

上一篇 揭秘Swift编程语言的核心优势与实用开发场景