2013-02-28 35 views
6

中測試了一些js代碼Chrome開發者控制檯,我有點困惑。JavaScript'嚴格使用';裏面的函數

我知道,在嚴格模式函數時提到不屬於某個對象的方法這關鍵字應該得到不確定,而不是全局對象。

function test(){ 
    "use strict"; 
    return this===undefined;} 
test(); 

輸出false

"use strict"; 
function test(){ 
    return this===undefined;} 
test(); 

仍然false

(function test(){ 
    "use strict"; 
    return this===undefined;}()); 

輸出真正

只是想澄清。 'm•ᴥ•ʔ我是js的新手。

+2

請閱讀類似的問題http://stackoverflow.com/questions/1335851/what-does-use-strict-do-in-javascript-and-what-is-the-reasoning-behind-it – hexblot 2013-02-28 12:20:40

+4

@hexblot這並不回答這個問題,雖然...... – Christoph 2013-02-28 12:37:00

回答

2

它是Chromium開發人員控制檯中的一個錯誤,它會導致this仍引用全局對象。相同的代碼在位置欄和文檔中的作用與javascript:中指定的相同。

可以測試像這樣(2控制檯輸入):

var global = (function() { return this; }()); 

"use strict"; 
function test() { return this === global; } 
test(); 

和(一個或多個控制檯輸入)

var script = document.createElement("script"); 
script.type = "text/javascript"; 
script.appendChild(document.createTextNode(
    'function test() { "use strict"; return this === undefined; }; console.log(test());' 
)); 
document.body.appendChild(script); 

測試在鉻版25.0.1364.97的Debian 7.0(183676) 。

+0

你的第一個測試是一個破碎的測試。即使你在腳本標記而不是控制檯中運行它,你仍然會得到'true',因爲''use strict''必須是它的作用域中的* first *行。你的例子在'var global ...'之後出現,所以該指令被忽略(按照規範)。 – 2013-03-02 01:52:46

+0

@NathanWall不,請參閱我的說明。我建議你在函數中使用'debugger;'來檢查調用堆棧。 – PointedEars 2013-03-03 12:27:53

2

一切都很好。如果您通過某個HTML頁面(而不是開發控制檯)運行代碼,則結果符合預期(始終爲this===undefined)。

此外,在最新的Firefox(螢火蟲):

function test(){ 
    "use strict"; 
    return this===undefined;} 
test(); 
>> true 

因此,這似乎只是一個瀏覽器的bug(功能?)。感覺就像它通過dev控制檯傳遞的代碼有一個稍微不同的方法。

另外請注意,爲了事項:

<script> 
    console.log('Me First!'); 

    "use strict"; 

    function test(){ 
     console.log(this); 
    } 
    test(); 

</script> 

>>> "Me First!" 
>>> Window {top: Window, window: Window, location: Location, external: Object, chrome: Object…} 

但是:

<script> 
    "use strict"; 

    console.log('Me later!'); 

    function test(){ 
     console.log(this); 
    } 
    test(); 

</script> 

>>> undefined 
>>> "Me later!" 
4

什麼,你已經注意到了根本的辦法副作用的開發者控制檯的作品。當你在那裏輸入代碼,這實際上是發生了什麼(見this answer有詳細介紹):

eval.call(null, "with (window) { \ 
        function test() { \ 
         'use strict'; \ 
         console.log(this); \ 
        } test(); \ 
       }"); 

這是一個間接呼叫eval,這意味着它會一直在全球執行上下文中執行(在瀏覽器,這是window)。

實際上,該功能被綁定到全局對象,因此this持有全局對象的引用,因爲如果你在網頁中(而不是在控制檯)這樣做:

function test(){ 
    "use strict"; 
    return this === undefined; 
} 

test(); // true 
test.call(window); // false 
+1

像'window' *引用的對象是* *不是執行上下文。執行上下文是一個抽象程序實體;它有一個*範圍鏈*,其中有對象。在這種情況下,它將是'with'語句,用於'test()'調用上下文的範圍鏈中插入'window'引用的對象。 – PointedEars 2013-02-28 12:58:30

+0

@PointedEars - 當然可以。我本可以說「窗口對象所屬的詞彙環境的環境記錄」,但我認爲它的方式更簡單,我認爲它仍然是重中之重。而'with'語句在這種情況下沒有什麼區別 - 這就是'eval'被調用的方式,它會影響其參數被評估的上下文。 – 2013-02-28 13:11:48

+0

這裏的'with'語句*可能很重要;當然,如果你認爲(IMO錯誤地)全局對象的'window'主機屬性總是引用全局對象。因爲那麼'test()'調用將等同於'global.window.test()',其中'global'將作爲全局對象的標準引用的替身。 – PointedEars 2013-03-01 00:52:48