繁体   English   中英

Javascript闭包:直接访问模型和使用变量之间的区别

[英]Javascript closure: difference between accessing the model directly and using a variable

我注意到该代码无法正常运行。

消息RENDER_IMAGE在有效负载中以不同的图像多次广播,但是下面代码中的self.model.get(“ image”)始终返回最后一个图像。 为什么?

bus.subscribe("RENDER_IMAGE", (message, payload) => {
    const self = this;
    self.model.set(payload);

    self.render().then(function() {
            bus.broadcast("IMAGE_RENDER_COMPLETE", self.model.get("image"));
        });
});

同时,此代码可以正常工作:

bus.subscribe("RENDER_IMAGE", (message, payload) => {
        const self = this;
        self.model.set(payload);
        const image = self.model.get("image"));

        self.render().then(function() {
                bus.broadcast("IMAGE_RENDER_COMPLETE", image;
            });
    });

在第一个示例中,您将在渲染完成从模型中检索image字段。
同时,在第一个渲染完成之前,可能已触发一个或多个RENDER_IMAGE事件。 每次此类事件触发时,您都在更新image字段。

即发生这种情况

RENDER_IMAGE triggered
Set image field            (image = 0)
Start render (0)

RENDER_IMAGE triggered
Set image field            (image = 1)
Start render (1)

Render finished (0)
Get image field (1, because image = 1)

Render finished (1)
Get image field (1, because image = 1)

在第二个示例中,您将在设置后立即检索归档的image 由于JavaScript是单线程的,因此不可能再使用另一个self.model.set(payload); const image = self.model.get("image"));之前被调用const image = self.model.get("image")); 被执行:

RENDER_IMAGE triggered
Set image field            (image = 0)
Get image field (0, because image = 0)
Start render (0)

RENDER_IMAGE triggered
Set image field            (image = 1)
Get image field (1, because image = 1)
Start render (1)

Render finished (0)

Render finished (1)

如果您仍然想知道为什么直接访问模型和使用变量之间有何区别:事件处理程序的每次调用都有其自己的 image变量,但是它们都访问相同的共享模型。

这就是共享数据的特征之一,这就是为什么在处理异步流程时必须谨慎处理共享数据的原因。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM