角度应用程序(对象中的数组未填充在实例化期间传递的值)



在我的 Angular 应用程序的一个组件中,我订阅了一个 Observable,它从我的一个服务中的函数返回一个 json 数组。 该响应将正确返回到组件。

在 .subscribe 中,我使用嵌套的 for 循环将每个 JSON 对象的字段映射到新类实例(对象)的属性中,然后将每个实例/对象添加/推送到该类类型的数组中。

当我在Chrome控制台中查看来自console.log(this.contractsList)的结果时,所有字段都正确填充,除了显示为:

列表办公室: 数组(0)

此字符串数组应始终具有 1 或 2 个元素。

我意识到我可能应该在我的服务而不是组件中执行这种反序列化/映射,但我认为这不会导致这个问题。我计划在工作后进行重构。相反,我认为它与关闭有关,这仍然让我感到困惑。 我假设是这样,因为当我在尝试将其值分配给对象之前随时尝试 console.log(officeval) 时,我在控制台中看到正确的值。

这是我的组件中调用订阅的方法:

getContracts() {
this.contractService.getContracts().subscribe(
(res) => {
let officeval = new Array<string>();
for (var x = 0; x < res.length; x++) {
for (var z = 0; z < res[x].length; z++) {
if (res[x][z].resources.office !== undefined){
for (var a = 0; a < res[x][z].resources.office.values.length; a++) {
officeval.push(res[x][z].resources.office.values[a]);
}
}
else {
officeval.push("Not a Hive Policy");
}
this.createContract(res[x][z].id, res[x][z].name,"placeholder for type",res[x][z].isEnabled, res[x][z].service,
officeval, ["q", "w"], ["q", "w"],["q", "w"], ["q", "w"],["q","r"]);
} console.log(this.contractsList);       
}
},
(err) => console.log(err))
console.log("logging contracts");
}
createContract(id:number, contractName:string, type:string, isEnabled:boolean,
service:string, listOffices:string[], listRooms:string[],
listSeats:string[], contractItemsEntries:string[], contractItemsOwners:string[], contractItemsSessions:string[]) {
this.contractsList.push (new Contract (id, contractName, type, isEnabled,
service, listOffices, listRooms,
listSeats, contractItemsEntries, contractItemsOwners, contractItemsSessions ));
}
}

以下是 Chrome 控制台中的输出示例:

[Contract, Contract, Contract...] x6 
-opened Contract Array:
0:Contact
1:Contract
2:Contract
...
-opened Contract:
listOffices: Array(0) -- ???
listRooms: Array(2) --contain correct values
listSeats: Array(2) --contain correct values
id:1
isEnabled: true
service: contractService
type: "placeholder for type"

既然我们对你的 res 对象一无所知,你确定

res[x][z].resources.office.values.length > 0

这是您的办公室瓦尔没有被填满的唯一情况。(因为它没有明显循环)

所以我敢打赌。

从查看代码来看,office.values的长度必须为 0,这意味着没有添加任何内容,因此是一个 Array(0)。如果您可以发布从getContracts返回的JSON,则可以确认这一点。

此外,一旦你让它将项目放入 officeval 数组中,你可能会注意到它有比它应该更多的项目,因为它在循环的每次迭代中都没有出现你的清除 officeval。这可能是故意的,但我的猜测是不是。

问题的根本原因与以下方面有关:

  1. 没有意识到javascript通过引用传递复杂的数据类型 (见这篇文章)(这些帖子是我如何按值而不是按引用完成传递的指南:一,二)
  2. 每次内部 for 循环迭代后不将办公室数组重置回 0

要修复,我:

  1. 将 officeval 数组的声明移到了我的外部函数之外,以便可以使用 this 关键字在我的内部函数中引用它
  2. 使用 slice 方法创建 officeval 的按值副本,然后将其传递到我的内部函数中,用于创建新合约并将它们添加到 contractsList 数组中。
  3. 每次将新合约推送到合约列表后,立即重置 officeval 的值。

这是我代码的最终版本:

officeval: string[] = []
getContracts() {
this.contractService.getContracts().subscribe(
(res) => {
//let officeval = new Array<string>();
for (var x = 0; x < res.length; x++) {
for (var z = 0; z < res[x].length; z++) {
if (res[x][z].resources.office !== undefined){
for (var a = 0; a < res[x][z].resources.office.values.length; a++) {
officeval.push(res[x][z].resources.office.values[a]);
}
}
else {
officeval.push("Not a Hive Policy");
}
var testArray = this.officeval.slice(0);
this.createContract(res[x][z].id, res[x][z].name,"placeholder for type",res[x][z].isEnabled, res[x][z].service,
testArray, ["q", "w"], ["q", "w"],["q", "w"], ["q", "w"],["q","r"]);
} console.log(this.contractsList);       
}
},
(err) => console.log(err))
console.log("logging contracts");
}
createContract(id:number, contractName:string, type:string, isEnabled:boolean,
service:string, listOffices:string[], listRooms:string[],
listSeats:string[], contractItemsEntries:string[], contractItemsOwners:string[], contractItemsSessions:string[]) {
this.contractsList.push (new Contract (id, contractName, type, isEnabled,
service, listOffices, listRooms,
listSeats, contractItemsEntries, contractItemsOwners, contractItemsSessions ));
this.offiveval.length = 0;
}
}

最新更新