搜尋

首頁  >  問答  >  主體

一道關於 JavaScript 中 this 的題目的困惑

看到很多資料說,哪個物件呼叫了這個函數,這個函數中的 this 就指向這個物件。
下面這個例子中,foo這個函數,是透過 foo()這個語句呼叫的,為什麼this 會指向全域?並沒有 Window.foo( )這樣由全域物件呼叫呀?
求教,多謝!

var x = 10;
var obj = {
  x: 20,
  f: function () {
     var foo = function (){
         console.log(this.x);
     }
     foo();
  }
};
obj.f(); //10
代言代言2715 天前910

全部回覆(7)我來回復

  • 给我你的怀抱

    给我你的怀抱2017-06-26 10:54:59

    樓上講的有點問題,foo不是全域變量,簡單點來判斷(非嚴格模式)就是:
    1.當一個函數沒有被指定上級對象的時候,this指向window
    2.當一個函數有被指定上級物件的時候,this只指向最靠近的上級(父)物件
    如foo.fn.o() , o裡面的this指向fn

    回覆
    0
  • 高洛峰

    高洛峰2017-06-26 10:54:59

    是這樣子的,我寫在註解裡面

    var x = 10;
    var obj = {
      x: 20,
      f: function () {
         var foo = function (){
             console.log(this.x);//你这是把函数赋值给一个 foo的变量。此时的 foo 是全局的,所以下面调用 foo()这里是10嘛
         }
         foo();
      }
    };
    obj.f(); // 这个调用 f 函数,因为 f(),并没有返回出去什么,所以这里是 undefined

    回覆
    0
  • 代言

    代言2017-06-26 10:54:59

    對於內部函數,即聲明在另一個函數體內的函數,都會綁定到全域物件上,這是JavaScript的設計缺陷,正確的設計方式是內部函數的this應該綁定到其外層函數對應的物件上,所以導致以上問題。

    為了規避這個設計缺陷,可以用變數取代的方法,約定俗成,可以使用selfthat,程式碼如下:

    var x = 10;
    var obj = {
      x: 20,
      f: function () {
         var self = this;
         var foo = function (){
             console.log(self.x);
         }
         foo();
      }
    };
    obj.f();

    回覆
    0
  • PHP中文网

    PHP中文网2017-06-26 10:54:59

    先搞清楚一個道理:
    1: window也是一個對象,它是一個特別的對象,它代表全局。 當你以以下方式呼叫一個函數的時候:
    function foo(){....}
    foo();//
    第二行的這種呼叫方式(函數前面沒有一個你自己定義的object),我們叫做'全域調用'。其實等同於window.foo()。所以你看出來了嗎?在全域呼叫函數,其實是在物件上呼叫函數的一個特例,因為這時候的物件是window.
    2: 那為什麼上面的程式碼是在全域呼叫了foo(),而不是在obj上面呢?我把程式碼改一下,讓他輸出20:

    var x = 10;
    var obj = {
      x: 20,
      f: function () {
         console.log(this.x);
      }
    };
    obj.f();//20
    

    對比一下,兩段程式碼,找找它們的不同。

    回覆
    0
  • 某草草

    某草草2017-06-26 10:54:59

    雷雷 雷雷

    回覆
    0
  • 曾经蜡笔没有小新

    曾经蜡笔没有小新2017-06-26 10:54:59

    你可以把程式碼改寫為這樣子的:

    var x = 10;
    var obj = {
      x: 20,
      f: function () {
         var foo = function (){
             console.log(this.x);
         }
         foo.call(null) // 等价于foo.call(window)
      }
    };
    obj.f.call(obj); //10  结果不变

    透過上面的例子,你可以這樣理解 當呼叫一個函數的時候,JavaScript解析器是按照call或apply這樣的形式去呼叫的。 透過這樣的方式來為函數中的this指定一個值。這兩個方法的第一個參數就是foo方法被呼叫時其內部this的值,如果call方法的第一個參數為null、undefined時,就會預設把全域物件當作第一個參數(你可以試試試foo.call()、foo.call(null)、foo.call(undefined))

    回覆
    0
  • 女神的闺蜜爱上我

    女神的闺蜜爱上我2017-06-26 10:54:59

    函數內套函數,this指標遺失

    回覆
    0
  • 取消回覆