通俗易懂------this指向

来源:http://www.cnblogs.com/beidan/archive/2016/04/09/5371275.html
-Advertisement-
Play Games

因為JavaScript 中this 是在運行期進行綁定的,因此JavaScript 中this 關鍵字具備多重含義。 具體在實際應用中,this的指向大致可以分為下麵4種。 作為對象的方法調用 和 作為普通函數調用 註意,不管x之前是obj.getA,還是其他某個對象的屬性,只要最後是以x(),f ...


因為JavaScript 中this 是在運行期進行綁定的,因此JavaScript 中this 關鍵字具備多重含義。

具體在實際應用中,this的指向大致可以分為下麵4種。

  1. 作為對象的方法調用   obj.a()
  2. 作為普通函數調用    a()
  3. 構造函數調用        var b = new a(); 
  4. function.prototype.call或function.prototype.apply調用

作為對象的方法調用 和 作為普通函數調用

 1 window.a = 2;
 2 var obj = {
 3     a:1,
 4     getA:function(){
 5         console.log(this.a);
 6     }
 7 }
 8 obj.getA();       //輸出1,作為對象的方法調用,this指向當前對象
 9 var x = obj.getA;
10 x();   //輸出2,作為普通函數調用,this全部指向window對象。 

註意,不管x之前是obj.getA,還是其他某個對象的屬性,只要最後是以x(),fun()這種方式調用的,均視為普通函數調用,此時this指向window對象

但是,在ECMAScript5的strict模式下,作為函數調用的 this被規定不會指向全局對象

 1 window.a = 2;
 2 var obj = {
 3     a:1,
 4     getA:function(){
 5         "use strict"
 6         console.log(this.a);
 7     }
 8 }
 9 var x = obj.getA;
10 x();   //underfined

作為構造函數調用

通常情況下,構造函數里的this指向返回的這個對象,但是如果構造器顯示地返回了一個object類型的對象,則this指向這個返回的object對象
 1 var Myclass = function(){
 2     this.name = 'beidan';
 3 }
 4 var obj = new Myclass();  
 5 console.log(obj.name);//beidan
 6  
 7 var Myclass = function(){
 8     this.name = 'beidan';
 9     return{         //顯示的返回一個對象,註意!既要是顯示,即有return,也要是對象{}
10         name:'test'
11     }
12 }
13 var obj = new Myclass();
14 console.log(obj.name);//test

作為function.prototype.call或function.prototype.apply調用

 

  • 理解call,apply

 

call,apply都是為了改變函數體內部 this 的指向。例如,fun1.call()或者fun1.apply() 都是為了改變fun1函數內部的this指向。

二者的作用完全一樣,只是接受參數的方式不太一樣。

func1.call(this, arg1, arg2);        //參數列表arg1,arg2 func1.apply(this, [arg1, arg2]);   //參數數組 [arg1,arg2]   第一個參數指定那個了函數體內this對象的指向,他可以任何一個 JavaScript 對象(JavaScript 中一切皆對象),如果為null,則函數體內的this會指向預設的宿主對象,在瀏覽器中則是window。   第二個參數,call 需要把參數按順序傳遞進去,而 apply 則是把參數放在數組裡。 當你的參數不確定數量時用 apply ,然後把參數 push 進數組傳遞進去。或者也可以通過 arguments來獲取所有的參數。這樣看來,apply的使用率更高。  
  • call,apply的用途

 

1.修正this的指向 比如,在實際開發中,會出現以下這種問題
1 document.getElementById('div1').onclick = function(){
2     console.log(this.id);   //div1
3     var func = function(){
4         console.log(this.id);    
5     }
6     func();   //通過普通函數調用,this指向window,輸出undefined
7 }
這時我們可以用call來修正func 函數內this的指向。
1 document.getElementById('div1').onclick = function(){
2     console.log(this.id);   //div1
3     var func = function(){
4         console.log(this.id);
5     }
6     func.call(this);   //使用call,使func函數內部的this指向當前的函數對象,輸出div1
7 }

2.模擬繼承(借用其他對象的方法)

  • 例子一:其他對象(banana)借用apple中的say方法
1 function fruits() {}
2 fruits.prototype = {
3     color: "red",
4     say: function() {
5         console.log("My color is "+ this.color);
6     }
7 }
8 var apple = new fruits;
9 apple.say();    //My color is red
但是,如果我們還有其它 2個對象 banana= {color : "yellow"} ,orange = {color:‘orange’},想使用say方法,但是又不想對它們重新定義say方法。 那麼,我們可以用apply或者call 借用 fruit裡面的say方法
1 banana = {
2     color: "yellow"
3 };
4 orange = {color:‘orange’};
5 apple.say.call(banana);     //My color is yellow
6 apple.say.apply(orange );    //My color is orange
也就是說,當一個 object 沒有某個方法(本例子中banana沒有say方法),但是其他的有(本例子中apple有say方法),我們可以藉助call或apply用其它對象的方法來操作。 再看幾個例子鞏固記憶
  • 例子二:獲取數組中的最大值和最小值
1 var numbers = [5, 458 , 120 , -215 ];
2 var maxInNumbers = Math.max.apply(Math, numbers),   //458
3     maxNumbers = Math.max.call(Math,5, 458 , 120 , -215, 666); //666
number 本身沒有 max 方法,但是 Math 有,我們就可以藉助 call 或者 apply 使用其方法。

 

以上就是this在JavaScript中不同情況下的指向。

周末來了,博主又要出去浪了o(∩_∩)o 

 


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 大型網站優化-memcache技術 memory+cache 記憶體緩存 memcache簡介 memcache是一套分散式的高速緩存系統,由LiveJournal的Brad Fitzpatrick開發,目前被許多網站使用以提升網站的訪問速度,尤其對於一些大型的、需要頻繁訪問資料庫的網站訪問速度提升效 ...
  • Queue簡介 queue是隊列容器,是一種“先進先出”的容器。 queue是簡單地裝飾deque容器而成為另外的一種容器。 #include <queue> 1.queue對象的預設構造 2.queue的push()與pop()方法 queue.push(elem); //往隊尾添加元素 queu ...
  • 在Java程式設計中經常會見到this的使用,this使得程式設計變得規範、簡單、靈活。但是在使用過程中,在不同場 合它的含義並不完全相同,使用不當還會出現錯誤, 本文對this的幾種用法和出現的問題進行了分析詳解。 關鍵詞:類;對象;this;成員變數;方法;構造方法 中,Java語言提供了豐富的 ...
  • 這個簡單的web伺服器包含三個類 HttpServer Request Response 在應用程式的入口點,也就是靜態main函數中,創建一個HttpServer實例,然後調用其await()方法。顧名思義,await方法會在制定的埠上等待http請求,並對其進行處理,然後發送相應的消息回客戶端 ...
  • 清明假期後到新公司報到 公司主要業務搞進存銷系統,涉及方面非常多,軟體都是D7開發的。之前沒有接觸過相關係統,可以算是完全的新人。進公司第一天,大家忙著新功能升級,主管也沒顧上我。與是 自己看公司技術部文檔。 首先是代碼規範, 局部變數定義:Integer的變數以i開頭,byte的以b開頭等等 全局 ...
  • 闡述問題前,先來看一下下麵這張圖片左側iframe中的亂碼頁面; 這個就是讓我糾結好一陣子的亂碼截圖: 這個亂碼頁面中是使用了<jsp:include>引用標簽後出現了這個問題; 源碼截圖: 起初以為是文件編碼的問題,所以各種解決各種可能的找; 有說當jsp include動態文件時(jsp文件)可 ...
  • 寫在最前面:轉載請註明出處 目錄置頂: 關於項目 基於DDD領域驅動設計的WCF+EF+WPF分層框架(1) 架構搭建 基於DDD領域驅動設計的WCF+EF+WPF分層框架(2) WCF服務端具體實現 基於DDD領域驅動設計的WCF+EF+WPF分層框架(3) WCF客戶端配置以及代理 基於DDD領 ...
  • 測試 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...