为了账号安全,请及时绑定邮箱和手机立即绑定

markForCheck()和detectChanges()有什么区别

markForCheck()和detectChanges()有什么区别

扬帆大鱼 2019-10-15 10:52:45
ChangeDetectorRef.markForCheck()和之间有什么区别ChangeDetectorRef.detectChanges()?我只找到了关于SO的信息NgZone.run(),但没有找到这两个功能之间的区别。对于仅参考文档的答案,请举例说明一些实际情况,以供选择。
查看完整描述

3 回答

?
交互式爱情

TA贡献1712条经验 获得超3个赞

两者之间的最大区别是detectChanges()实际上触发变更检测,而markForCheck()不会触发变更检测。


detectChanges

该代码用于从触发您的组件开始对组件树进行更改检测detectChanges()。因此,更改检测将针对当前组件及其所有子组件运行。Angular在中保留对根组件树的引用ApplicationRef,当发生任何异步操作时,它会通过包装方法触发对该根组件的更改检测tick():


@Injectable()

export class ApplicationRef_ extends ApplicationRef {

  ...

  tick(): void {

    if (this._runningTick) {

      throw new Error('ApplicationRef.tick is called recursively');

    }


    const scope = ApplicationRef_._tickScope();

    try {

      this._runningTick = true;

      this._views.forEach((view) => view.detectChanges()); <------------------

view这是根组件视图。正如我在引导多个组件的含义中所描述的那样,可能有许多根组件。


@milad描述了您可能需要手动触发更改检测的原因。


markForCheck

就像我说的,这个家伙根本不会触发变更检测。它只是从当前组件向上扩展到根组件,并将其视图状态更新为ChecksEnabled。这是源代码:


export function markParentViewsForCheck(view: ViewData) {

  let currView: ViewData|null = view;

  while (currView) {

    if (currView.def.flags & ViewFlags.OnPush) {

      currView.state |= ViewState.ChecksEnabled;  <-----------------

    }

    currView = currView.viewContainerParent || currView.parent;

  }

}

组件的实际更改检测未计划,但将来会发生时(作为当前或下一个CD周期的一部分),即使父组件视图已脱离更改检测器,也将对其进行检查。可以通过使用cd.detach()或指定OnPush更改检测策略来分离更改检测器。所有本机事件处理程序都将所有父组件视图标记为要检查。


这种方法通常在ngDoCheck生命周期挂钩中使用。如果您认为这ngDoCheck意味着正在检查您的组件。



查看完整回答
反对 回复 2019-10-15
?
当年话下

TA贡献1890条经验 获得超9个赞

商店更新主要是由于获取或设置isFetching before导致的。并在获取后..但是我们不能总是使用,async pipe因为在订阅内部,我们通常有一些事情要做call setFromValues do some comparison..如果async本身调用markForCheck它,那么如果我们自己调用它会带来什么问题呢?但是同样,在ngOnInit获取不同数据时,我们通常会有2-3个或更多选择器……而我们markForCheck都将它们都调用了。

查看完整回答
反对 回复 2019-10-15
  • 3 回答
  • 0 关注
  • 2659 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信