gpt4 book ai didi

angular - "Expression has changed after it was checked"当子组件在 ngOnInit 上发出时

转载 作者:太空狗 更新时间:2023-10-29 17:20:19 25 4
gpt4 key购买 nike

我有一个显示验证错误列表并使用 ngFor 呈现子组件列表的父组件。每个子组件在 ngOnInit 期间执行其验证并将结果输出到父组件。父组件监听此输出并更新验证错误列表,结果抛出错误:

检查后表达式发生了变化

现在,我明白了为什么会抛出这个错误 - 在变更检测周期开始时,验证错误处于一种状态,而在结束时它处于另一种状态,这是不允许的。

我不明白的是如何解决这个问题。父组件必须在页面顶部显示一个错误列表,每个子组件都会将它们的验证结果添加到这个列表中。如果这违反了单向数据流,那么请告诉我如何以干净的方式解决这个问题(即,不将验证包装在 setTimeout 中,不从不可变列表更改为可变的,并且在验证后不会再次显式调用更改检测器)。

Plunker 重现问题:https://plnkr.co/edit/q52A1DraNOnxZa0qGFDo?p=preview


编辑

我已经通过使用 isAsync 标志构造 EventEmitter 来“解决”了这个问题:

新的 EventEmitter(true)

这意味着值将异步发出,因此发出的值将在下一个变化检测周期中被拾取。我想结果与将逻辑包装在 setTimeout 中是一样的,但这样至少我们不必在任何可能发出值的地方都将代码包装在超时中。

最佳答案

Angular 不喜欢变化检测本身引起变化并且 ngOnInit 被变化检测调用。

在 devMode 中,更改检测会在每次常规更改检测运行后执行额外的更改检测运行,以检查模型是否稳定。如果模型在变化检测期间发生变化,则会抛出此错误。

您可以延迟更改,直到更改检测完成后使用

  ngOnInit() {
setTimeout(() => {
this.output.emit({value: true});
}
}

Plunker example

更新(见下方 Ghetolay 的评论)

ngOnInit is not called by change detection and you can do bind changes inside it. What you cannot do is making change on a parent from a child's ngOnInit cause this breaks unidirectional data flow.

另见 https://github.com/angular/angular/issues/10131#issuecomment-233369491

关于angular - "Expression has changed after it was checked"当子组件在 ngOnInit 上发出时,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42190290/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com