Angular 14.2模板中索引表达式隐式any类型问题求助
Angular模板中动态索引的类型错误解决办法
问题背景
环境:Angular 14.2 + TypeScript 4.6.4
TypeScript类型定义:
export class MyInfo { public name = ''; public street = ''; } export class Everyone { public people: { [index: string]: MyInfo } = this.getEveryone(); }
people对象结构示例:
{ '1': { name: 'Homer', street: 'Evergreen Terrace'}, '34': { name: 'Rod', street: 'Maple'} }
数据来自动态数据库,键值无法预先定义。TypeScript代码中通过keyof或类型断言可正常处理,但HTML模板中使用以下代码时触发编译错误:
<div *ngFor='let character of differentPeople'> <p *ngIf="people[character.id]['street'] === character['street']; else alone"> {{ people[character.id]['name'] }} lives on the same street as character['name']; </p> <ng-template #alone><p>You live alone</p></ng-template> </div>
错误信息:Element implicitly has an 'any' type because index expression is not of type 'string'
解决方法
1. 统一索引类型为字符串
如果character.id是数字类型,在模板中显式转为字符串:
<div *ngFor='let character of differentPeople'> <p *ngIf="people[character.id.toString()].street === character.street; else alone"> {{ people[character.id.toString()].name }} lives on the same street as {{ character.name }} </p> <ng-template #alone><p>You live alone</p></ng-template> </div>
更优方案是在组件类中提前处理数据,避免模板重复转换:
// 组件类中定义处理后的数组 get processedPeople() { return this.differentPeople.map(char => ({ ...char, id: char.id.toString() })); }
模板中直接使用处理后的数组:
<div *ngFor='let character of processedPeople'> <p *ngIf="people[character.id].street === character.street; else alone"> {{ people[character.id].name }} lives on the same street as {{ character.name }} </p> <ng-template #alone><p>You live alone</p></ng-template> </div>
2. 封装类型安全的访问方法
在组件或Everyone类中添加方法,统一处理索引转换和属性访问:
// 在Everyone类或组件中添加 getPerson(id: number | string): MyInfo | undefined { const key = typeof id === 'number' ? id.toString() : id; return this.people[key]; }
模板中调用该方法,结合可选链避免空值报错:
<div *ngFor='let character of differentPeople'> <p *ngIf="getPerson(character.id)?.street === character.street; else alone"> {{ getPerson(character.id)?.name }} lives on the same street as {{ character.name }} </p> <ng-template #alone><p>You live alone</p></ng-template> </div>
3. 扩展索引类型支持
修改people的类型定义,同时兼容数字和字符串索引:
export class Everyone { public people: { [index: string | number]: MyInfo } = this.getEveryone(); }
此方法无需修改模板,直接使用character.id即可,但要确保后端返回的键值在类型转换时不会出现不一致问题。
内容的提问来源于stack exchange,提问作者Bob Ramsey
相关产品推荐
相关产品推荐

