在Web工作者之间共享变量? [全局变量?]

时间:2010-02-14 20:42:16

标签: javascript html5 global-variables local-storage web-worker

我有什么方法可以在两个网络工作者之间共享一个变量? (Web worker基本上是Javascript中的线程)

在像c#这样的语言中你有:

public static string message = "";
static void Main()
{
 message = "asdf";
 new Thread(mythread).Run();
}
public static void mythread()
{
 Console.WriteLine(message); //outputs "asdf"
}

我知道这是一个糟糕的例子,但在我的Javascript应用程序中,我有一个线程正在进行大量计算,可以分布在多个线程中[因为我有一大块数据以数组的形式存在。数组的所有元素都是相互独立的。换句话说,我的工作线程不必关心锁定或类似的东西]

我发现在两个线程之间“共享”变量的唯一方法是创建一个Getter / setter [通过原型设计],然后使用postMessage / onmessage ...虽然这看起来效率很低[特别是对于对象,我必须使用JSON进行AFAIK]

LocalStorage / Database已经从HTML5规范中删除,因为它可能导致死锁,所以这不是一个选项[遗憾] ......

我发现的另一种可能性是使用PHP实际上有一个getVariable.php和setVariable.php页面,它们使用localstorage来存储整数/字符串...再一次,Objects [包括arrays / null]必须转换为JSON ...然后,转换为JSON.parse()'d。

据我所知,Javascript工作线程与主页面线程完全隔离[这就是Javascript工作线程无法访问DOM元素的原因

尽管postMessage有效,但速度很慢。

谢谢!

4 个答案:

答案 0 :(得分:10)

Web工作者是故意共享的 - 没有 - 工作者中的所有内容都完全隐藏在其他工作者和浏览器中的页面之外。如果有任何方法可以在工作者之间共享非“原子”值,那么这些值的语义几乎不可能与可预测的结果一起使用。现在,一个可以引入锁作为一种使用这些值的方式,在某种程度上 - 你获得锁,检查并修改值,然后释放锁 - 但锁是非常棘手的使用,并且由于通常的故障模式是死锁,你可以很容易地“破坏”浏览器。这对开发人员或用户来说是没有好处的(尤其是,当你认为Web环境非常适合那些从未听过线程,锁定或消息传递的非程序员进行实验时),所以另一种方法是在浏览器中的工作者或页面之间不共享状态。您可以将消息(可以认为是通过网络“序列化”传递给工作人员,然后工作人员根据序列化信息创建自己的原始值副本),而不必解决任何这些问题。

实际上,消息传递是支持并行性的正确方法,而不会让并发问题完全失控。正确地协调您的消息切换,您应该拥有与共享状态一样多的能力。你真的不想要你想要的替代品。

答案 1 :(得分:5)

不,但您可以向网络工作人员发送消息,这些消息可以是数组,对象,数字,字符串,布尔值和ImageData,也可以是这些的任意组合。 Web工作者也可以发回消息。

答案 2 :(得分:4)

在专职工作人员之间共享数据有两种选择:

<强> 1。 Shared Workers

  

SharedWorker接口代表一种特定类型的工作者   可以从多个浏览上下文中访问,例如几个   窗户,iframe甚至工人。

Spawning a Shared Worker in a Dedicated Worker

<强> 2。 Channel Messaging API

  

Channel Messaging API允许运行两个单独的脚本   附加到同一文档的不同浏览上下文(例如,两个   IFrame,或主文档和IFrame,两个文件通过   SharedWorker,或两个工人)直接沟通,传递   通过双向通道(或管道)彼此之间的消息   每端都有一个端口。

How to call shared worker from the web worker?

答案 3 :(得分:2)

我最近读过(但尚未使用过)shared workers。根据{{​​3}},支持仅适用于最新的浏览器(Opera 10.6,Chrome 5,Safari 5)。