前端架构师入门之 javascript是单线程语言? ajax怎么解释

什么是单线程

同一时间只能做一件事情.

其实语言的特性都是和其应用场景相互结合的;
javascript 主要是操作dom,如果多线程,同时去添加和删除dom节点
那不就乱套了么

顺便了解:在网页渲染的时候,js的加载和ui的渲染是共享线程的,是互斥的,不会同时加载,这也是为什么我们说把script放在body上面可能会导致页面发生阻塞(也就是肉眼看到页面会晚).

了解javascript堆栈

看到堆栈,我们就会想到

  • 栈是保存变量引用和简单变量的
  • 堆是保存对象的

所以函数的引用是在栈中,函数执行的过程其实就是内存的数据操作的过程,所以函数在执行的时候,堆和栈内存是都会有变化.

function changeVal(val){
    val=2;
}
function changeObj(obj){
    obj.name="changed name"
}
var val = 1;
var obj = {name:"my name"};

changeVal(val);
changeObj(obj)

// 你们觉得下面输出分别是什么呢,自己执行以下
console.log(val);
console.log(obj)
复制代码

通过上面简单说说js的执行阶段

  • EC (Execution Context) 执行上下文,也就是执行环境

    javascript 解析器解析创建的过程,比如变量声明,变量提升等(只是声明)

    例如:上面会构建
    ECobj={
        variableObject:{
         changeVal:Function, 
         changeObj:Function,
         val:1,
         obj:Object
        }
    }
    
    复制代码
  • ECS (执行环境栈)

    声明的代码入栈

上面为什么val=1,而obj={name:"changed name"}
因为函数运行时,changeVal只是执行环境中,只是在栈中声明了name然后赋值,执行完就销毁了
而changeObj 传入的是对象的引用,改变的是堆内存中的数据(需要注意的是,在函数中对对象引用的指向修改是无效的)

例如: changeVal(obj)
console.log(obj) => {name:"changed name"};
复制代码

为什么javascript是单线程的,ajax算什么

javascript是单线程的,是由它的执行机制决定的.下面说说过程,是什么机制?

  • javasript 代码执行会开启线程,线程的运行是要在内存中运行的,此时,javascript的主线程会开辟自己的堆栈.
  • javascript引擎解析后会在执行栈中执行.用代码说话
function a();
setTimeout();
function b();
ajax;


复制代码

入栈过程
1.a 入栈执行
2.setTimeout (浏览器)会开启一个异步任务,会托管给事件计数器去计数
3.b入栈执行
4.ajax (浏览器会开启一个异步网络任务去请求),也会托管给事件计数器计数

这里你会想,不是说javascript是单线程的么,它开启异步任务,不就是开启线程去执行么.(你说的对,这些线程都是浏览器提供的) 但是(下面很重要)

上面的setTimeout 和ajax执行完返回的结果会进行排队,会放在事件队列中,等待执行栈中执行完,也就是主线程执行完毕之后再来一个个的执行.

综上所述:js执行过程是没有在一个时间点同时执行的,是在一个时间点执行一件事,下一件事要执行,不好意思,排队执行.
所以,像你感觉到的setTimeout和ajax异步线程,是浏览器环境提供开启的,针对javascript语言的执行机制来看,它确实是单线程的

怎么去理解上图?


1.首先看任务栈
Math sin()
qux() 这里有一些异步操作,浏览器会开启相关线程去操作,下面的baz()会执行
baz()
...

这些除了qux()的事件会先执行完.


2.异步任务根据执行完的先后把结果放在队列中,然后通过event loop 循环去一个个的取. 这个取的前提是在执行栈中事件已经清空,也就是都执行完之后.


通过上面的讲解,大家应该清楚javascript为什么被称为是单线程语言了吧.

你可能感兴趣的:(javascript,前端,ui,ViewUI)