摘要:在腳本中,默認指向一個空對象,并不是指向,也不是指向。舉個栗子,在函數執行后,覆蓋原先的值我們在外部定義了一個名為的全局變量,它會被默認添加到全局的屬性上。總結在不同的執行環境中的默認指代通過省略聲明變量導致變量提升現象的發生及預防
侃侃JavaScript中的this
this為何如此多變?
this總是跟它的執行上下文有關,而在JavaScript總會有開辟新的執行上下文的東西,比如函數,所以,this才如此的變化。
執行環境對JavaScript中的this有影響嗎?
JavaScript是一門解釋型語言,需要有一個執行環境去執行它,通常的執行環境是瀏覽器,還有node腳本,還有`REPL`(“讀取-求值-輸出”循環(Read-Eval-Print Loop,簡稱REPL))。 如果對REPL有興趣的話,博客中的另一篇文章介紹了`REPL`
this默認指代誰?
在不同的執行環境中,會指代不同的對象
瀏覽器中:
> this // Window {top: Window, window: Window,... > this === window //true > var a = 1; //在全局中,用var聲明變量,會默認給window添加 > this.a // 1 > window.a // 1 > b = 1; //不使用var聲明變量,會默認給全局的this添加屬性 > this.b // 1 > window.b // 1
在node腳本中
console.log(this); //{} console.log(this === global); //false console.log(this === window); //ReferenceError: window is not defined var a = 1; //在全局中,使用var聲明變量,未給global添加屬性 console.log(this.a); //undefined console.log(global.a); //undefined console.log(window.a); //ReferenceError: window is not defined b = 1; //不使用var聲明變量,會默認給全局的global添加屬性。 console.log(this.b); //undefined console.log(global.b); // 1 在node腳本中,this默認指向一個空對象,并不是指向global,也不是指向window。
在REPL中
> this { DTRACE_NET_SERVER_CONNECTION: [Function], DTRACE_NET_STREAM_END: [Function], ... > global === this //true > var a = 1; //在全局中,使用var聲明變量,會默認給全局的global添加屬性 > this.a // 1 > global.a // 1 > b = 1; //不使用var聲明變量,會默認給全局的this添加屬性 > this.b // 1 > global.b // 1實例擴展
我們對于省略var的變量聲明方式,我們總說它是不安全的,但是是合法的。
為什么不安全?
如上文所述:不使用var聲明變量,會讓變量默認的添加到了全局的this中,這有時候會莫名的給變量提升它的作用域,從而影響其他全局變量。
舉個栗子:
var position = "outer"; //this.position = "outer" function test(){ position = "inner"; //this.position = "inner",在函數執行后,覆蓋原先的值 console.log(this.position); } test();
我們在外部定義了一個名為position的全局變量,它會被默認添加到全局this的屬性上。
然后在我們的test函數中,又定義了一個同名的變量,但是注意,函數中的變量聲明沒有用var。
因為我們并沒有對函數實例化,所以this.position的this會默認指代全局。
而當我們調用函數test時,函數會生成一個執行上下文,而內部position會將作用域從函數內部提升到全局,從而覆蓋(污染)了外部全局定義的position變量。
所以,在JavaScript的嚴格模式中,是不允許省略var來聲明變量的。故在聲明變量的時候,就順手加上var吧。
總結this在不同的執行環境中的默認指代
通過省略var聲明變量導致“變量提升”現象的發生及預防
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/91498.html
摘要:構造函數對于被實例化的,我們稱之為構造函數,及使用關鍵字調用的,對于它們來說,會被改變,指向實例。上栗子全局賦上屬性通過關鍵字創建實例,改變函數內部指向注解通過這個栗子,我們可以看出,通過創建構造函數的實例,使得的指向改變,指向了實例本身。 用栗子說this Bug年年有,今年特別多 對于JavaScript這么靈活的語言來說,少了this怎么活! function ...
摘要:閉包執行上下文決定了變量作用域而閉包,它其實是一種決策,是一種模式,讓我們可以靈活的改變變量作用域。所以,在本質上,閉包就是將函數內部和函數外部連接起來的一座橋梁。只要咱們弄明白閉包,其中的自然跑不掉。 閉包 this 執行上下文決定了變量作用域 而閉包,它其實是一種決策,是一種模式,讓我們可以靈活的改變變量作用域。 按慣例,上栗子 var global = glo...
摘要:而在中是迭代器生成器,被創造性的拿來做異步流程控制了。當執行的時候,并不執行函數體,而是返回一個迭代器。行代碼再看看文章開頭的行代碼首先生成一個迭代器,然后執行一遍,得到的是一個對象,里面再執行。 廣告招人:阿里巴巴招前端,在這里你可以享受大公司的福利和技術體系,也有小團隊的挑戰和成長空間。聯系: qingguang.meiqg at alibaba-inc.com 首先請原諒我的標題...
摘要:寫在前面在一款應用的整個生命周期,我們都會談及該應用的數據安全問題。用戶的合法性與數據的可見性是數據安全中非常重要的一部分。 寫在前面 在一款應用的整個生命周期,我們都會談及該應用的數據安全問題。用戶的合法性與數據的可見性是數據安全中非常重要的一部分。但是,一方面,不同的應用對于數據的合法性和可見性要求的維度與粒度都有所區別;另一方面,以當前微服務、多服務的架構方式,如何共享Sessi...
摘要:橋接模式的核心在于將抽象部分和它的實現部分分離,使它們都可以獨立的變化。看起來這個版本已經很完美了不,它仍然有可以優化的空間,即題目提到的橋接模式。使用橋接模式的實現版本這個實現包含了三個函數。這個例子體現了橋接模式的作用。 我寫的程序員面試系列文章 Java面試系列-webapp文件夾和WebContent文件夾的區別? 程序員面試系列:Spring MVC能響應HTTP請求的原因?...
閱讀 3999·2021-09-24 10:24
閱讀 1397·2021-09-22 16:01
閱讀 2718·2021-09-06 15:02
閱讀 1020·2019-08-30 13:01
閱讀 1008·2019-08-30 10:52
閱讀 636·2019-08-29 16:36
閱讀 2237·2019-08-29 12:51
閱讀 2338·2019-08-28 18:29