首页 > 为什么从dom中把script标签移除了,还可以执行下面的代码?

为什么从dom中把script标签移除了,还可以执行下面的代码?

<!DOCTYPE html>
<html>
    <head>
        <meta charset="UTF-8">
        <title></title>
    </head>
    <body>
        <script type="text/javascript">
            var src=document.querySelector("script");
            document.body.removeChild(src);
            alert(1);
        </script>
    </body>
</html>

如上代码,dom中已经没了这个script标签 ,为什么下面代码alert(1)还在执行?


楼主这个题目提得非常好,我刚花了一段时间google一下才搞懂,之前还误会了楼主的意思真是抱歉。
原因其实也就是js的按块执行、非阻塞I/O以及Event loop机制。JavaScript代码块被执行,创造出自己的执行环境后,就完全和dom中的script标签脱离了。事件队列中的事件全都执行完毕后执行环境才被销毁。
Removed JavaScript is still executable
The JavaScript Event Loop: Explained
Concurrency model and Event Loop


代码已经在列队中了,所以删除了还是会执行完


我在JavaScript高级程序设计那本书上看到这个知识点,在删除带有事件处理程序或引用了其他JavaScript对象子树时,就有可能导致内存占用问题。假设某个元素有一个事件处理程序(或者引用了一个JavaScript对象作为属性),在使用前述某个属性将该元素从文档树中删除后,元素与事件处理程序(或JavaScript对象)之间的绑定关系在内存中并没有一并删除。如果频繁出现这种情况,页面占用的内存数也会明显增加。


细节需要深入到浏览器的处理机制才可以。
不过我猜测是在处理js的时候会有个预处理的过程,在这个过程已经知道要运行的js了,也许这个script已经存在了某个地方,你删掉了script只是对dom影响,也没有用。


<script type="text/javascript">
    var src=document.querySelector("script");
    document.body.removeChild(src);
    function a(){
         alert(1);
    }
    a();
</script>

换一种写法,可以看到方法a()已经被浏览器解析了,所以就会执行了。


會不會是你已經運行過正確的,然後緩存了


JavaScript解释器在执行脚本时,是按块来执行的,简单来说,浏览器在解析HTML文档流时,如果遇到一个script标签时,javascript解释器会等待这个代码块都加载完了,才进行预编译,然后才执行。

所以,当开始执行这个代码块的代码时,这个代码段已经被解析完了。这时再从DOM中删去也就不影响代码的执行了。

【热门文章】
【热门文章】