百科问答小站 logo
百科问答小站 font logo



JavaScript 如果拥有多线程能力会怎样? 第1页

  

user avatar   Ivony 网友的相关建议: 
      

其实这样的选择是对的,从如今的情况来看,所谓的共享资源和互斥锁的多线程模型,带来的好处有限,麻烦却一大堆,实在不能说是一个很好的设计。是值得检讨而不是发扬光大的模型。


user avatar   liu-jin-wei 网友的相关建议: 
      

首先,webworker 不是伪多线程,一般我们说 js 中的伪多线程是指使用像 setTimeout setInterval 这样的 api 来实现类似并行的效果,而 webworker 是真正起了一个新线程的,所以它是真多线程。

这里的多线程并不是像web worker一样的伪多线程,而是类似java一样的真多线程,该线程,和其他线程共享全局变量,需要对共享变量用锁保护。

根据题主这句话,我猜测题主说 webworker 是伪多线程是因为 webworker 不能和主线程或其他子线程共享全局变量,也自然谈不上什么对共享变量的锁保护。可事实上,是不是多线程,和线程之间能不能共享全局变量并没有什么直接关系。可以参看维基百科上面关于线程的描述:

zh.wikipedia.org/wiki/%
1. 会对开发者有什么影响(好处or坏处更多一点)?
2. 对js语言本身有什么影响?(会限制某些功能,某些场景?)
3. 和异步的api怎么兼容?

关于题主的这三个问题,我觉得其实不太好回答。因为一旦引入题主所说的可共享变量的多线程机制,整个 javascript 开发模型可能都得一起改变,这么大的变化,已经没法估量它带来的好处多还是坏处多了。

我们都知道 javascript 运行时,不管是 Chrome 的 V8 还是 Edge 的查克拉,都是基于 EventLoop 的。这意味着,每时每刻都只有一段用户代码可能修改环境中的变量,这个看似限制颇多的运行时模型使得 javascript 的开发模型大为简化。一旦引入可共享变量的多线程机制,就算传统的 EventLoop 机制仍然保留,也仍然可能会出现有两段代码同时修改某个变量,这无疑使得代码的编写和调试难度大大增加。

还有一些问题,比如,引入题主所谓的真多线程之后,原来的用户事件、setTimeout、setInterval 这些api的回调,是仍然放入 EventLoop 还是在新线程并行执行?浏览器的渲染线程会被 javascript 的执行线程阻塞,引入可共享变量的子线程后,子线程的执行要不要也阻塞浏览器渲染?

总的来说,目前浏览器上 javascript 已有的这些运行时模型基本满足了绝大部分的业务需求,同时又使编程模型复杂度保持在了很低的水平,已经是很好的权衡,并不太需要引入可共享变量的多线程这个新技术。

------------ 2016-09-23 13:57:18 更新-------------------

针对题主补充的内容,做一点补充

但另一个方面settimeout,以及异步(promise async/await),都是通过类似event loop的原理实现的,都运行在同一个线程里,当这个线程任务比较繁重,可能导致timeout不够准确,异步任务等待得比较久等缺点,能否通过vm层的多线程支持而有更好的体验呢(这样timeout和async/await运行在另一个线程,timeout更准确,异步任务也更及时)?比如类似C#一样,异步就新开一个线程,在里面干活,干完数据送回主线程,主线程可能阻塞,也可能做自己的事情,这样是不是一种比js真多线程更好的解决方案?

题主说到了setTimeout不准时的问题,我猜题主对这个不准时的原因理解可能有偏差。从我之前看过的一些资料来看,setTimeout不准时并不是因为定时器没有在指定的时间被触发,而是触发之后回调函数没有被立刻执行,这是两个完全不同的概念。比如 setTimeout(fn, 500) 这句代码会让 javascript 引擎在 500ms 后准时地将 fn 加入 EventLoop ,但是 EventLoop 是不是会立刻执行 fn 的内容就不好说了,这要看 fn 前面是不是还有别的什么任务。

而C#里面一般定时器的回调都是在单独线程里面执行的,其执行上下文和主线程是相对独立的,自然也就不存在要看前面是不是有其他任务要运行的问题,所以看上去执行时机更准确。

但是 C# 的多线程也没这么简单。如何更新 UI ?题主如果用 C# 写过客户端程序应该记得,子线程是没有办法直接操作界面的,需要用委托 delegate,其实也可以说就是一种消息,在子线程触发计时器之后,给 UI 线程发消息(调用delegate),让 UI 线程更新用户界面。

C# 这种做法,你用现有的 webworker 一样可以实现,在 worker 里面开计时器,到时间之后给主线程 postMessage ,主线程收到指定消息之后操作UI。可是,你怎么保证主线程收到消息的时候不忙碌可以立即处理消息更新 UI ?是不是感觉弄了半天还是绕回来了?呵呵




  

相关话题

  win7笔记本,外接扩展显示器,如何在不缩小外接显示器像素的同时去除外接显示器的桌面背景黑边? 
  开发web前端为什么用后端node(npm安装模块和webpack打包方式)? 
  感觉自己学会了JavaScript所有基础知识,为什么老师留一个日历的作业我还是写不出来? 
  为什么 Vue 的更新记录没有中文,中文文档也一直滞后? 
  既然有 HTTP 请求,为什么还要用 RPC 调用? 
  C、C++、Java、JavaScript、PHP、Python、Ruby 这些语言分别主要用来开发什么? 
  前端做的页面为什么总是跟设计稿差很多? 
  为什么java返回json时用code=0表示成功, 而我观察的php和nodejs都是用1表示成功? 
  Java如何打好牢固的基础? 
  JavaScript 如果拥有多线程能力会怎样? 

前一个讨论
为什么有人说 Java 的跨平台很鸡肋?
下一个讨论
JavaScript 关于 if…else if…else 的疑问?





© 2024-05-20 - tinynew.org. All Rights Reserved.
© 2024-05-20 - tinynew.org. 保留所有权利