關於函數,你知多少?

来源:http://www.cnblogs.com/Beck-Z/archive/2017/10/20/7698706.html
-Advertisement-
Play Games

我們都知道,JS 中沒有的類的概念。 而 函數 則是 JS 中 很重要,很重要,很重要的一點。 理解 函數 也是非常有必要的。 先來看看 函數的定義。 如下: 上面講到了“函數的定義”,但是要怎麼理解“函數聲明”與“函數表達式”的不同呢? 讓我們看看什麼是“函數提升”?。 “函數提升”,會把當前作用 ...


我們都知道,JS 中沒有的類的概念。

而 函數 則是 JS 中 很重要,很重要,很重要的一點。

理解 函數 也是非常有必要的。

先來看看 函數的定義。

如下:

 1 // 函數聲明
 2 // 函數聲明不會立即調用,可以在你需要的時候調用它
 3 function demo(){
 4 
 5 }
 6 
 7 // 函數表達式, 該函數也可稱為匿名函數(無函數名)
 8 // 該函數保存在一個變數中,可通過變數名調用該函數
 9 var demo = funciton(){
10 
11 };
12 
13 // 構造函數(不推薦)
14 // 該方法會造成兩次解析代碼,且js中 很多都避免使用 new 關鍵字
15 var demo = new function(){
16 
17 }

上面講到了“函數的定義”,但是要怎麼理解“函數聲明”與“函數表達式”的不同呢?

讓我們看看什麼是“函數提升”?。

函數提升”,會把當前作用域(作用域的問題,後面會講到)提升到前面的行為。這又代表著什麼好處呢。

舉個例子:

 1 // 調用函數 
 2    test();
 3 
 4 // 函數聲明
 5 function test(){
 6     alert('調用成功');
 7 }
 8 
 9 // 調用函數
10    test();  // 報錯
11 
12 // 函數表達式
13 var  test = function(){
14    alert('調用成功');
15 }

我們知道代碼是從上而下的執行,一個變數若沒有聲明,則會拋出該變數未聲明的報錯信息。然後如上,為何可以如此呢?

這就是“函數提升”乾坤大羅移的時間了,由於“函數提升”的關係,因此調用函數,可以在函數聲明之前。

但是,但是,但是,使用函數表達式不能被提升。

說了這麼多,區別找到了嗎 ? 除了“函數提升”,在寫法上也有不同,這個細心的問題,就交給擁有慧眼的你了。

到這,我們已經瞭解了,函數的定義。也知曉了常用 調用函數的 方法。 接下來,我們聊聊 函數的參數

說到函數的參數,先看段代碼吧!

1  demo(2,3); // 2,3 實參 
2 
3  function demo(sum1,sum2){ // sum1,sum2 虛參
4    return sum1 + sum2;    
5  }

函數參數分為:

  1.  顯示參數:在函數定義時列出(也稱虛參) 
  2.  隱藏參數(arguments):在函數調用時傳遞給函數真正的值(也稱實參)

js 函數有個內置對象 arguments 對象,該對象包含了函數調用的參數數組。

參數規則:

  1.  函數定義時沒有對參數指定數據類型,也就是說,參數可以為任何類型
  2.  函數對隱藏參數(arguments)的個數沒有檢測,也就是說可以傳入比定義時參數的多
  3.  預設參數的值為 “undefined

再,再接下來聊聊 函數的調用 

也順帶著瞭解下 this 。

this 是什麼? this 是指向當前調用的對象。

 1 // 作為一個函數調用
 2    test();
 3 
 4 //當函數沒有被自身的對象調用時,this的值則會變成全局對象
 5 function test(){
 6     alert(this);   //  若在瀏覽器中打開,全局對象則是 window對象
 7 }
 8 
 9 // 作為一個對象的方法調用
10 var obj = {
11      sum1 : 10,
12      sum2 : 10,
13      sum   : function(){
14          console.log( sum1+sum2 );
15          console.log( this );
16      }  
17 }
18 // obj對象調用該函數 ,this的值指向當前對象 obj
19      obj.sum(); // 20, obj
20 
21 // 使用構造函數調用函數,
22 function test(name,age){
23     this.name = name;
24     this.age    = age;
25 }
26 // this 無任何值,this的值在調用實例化對象時(new object)創建
27 var obj = new test('Beck',21);
28       obj.name   // Beck
29 
30 // 自調用函數  
31 (function(){
32    console.log('自調用函數');
33 })

還有一種方式,函數的方法調用。我們知道,函數在js中也是對象, 也有屬性和方法。

舉個例子

1 function test(sum1,sum2){}
2 // 統計的是參數的個數
3 test.length  // 2

接下來,要瞭解的是,函數預定義的兩個方法 “calc()”,“apply()”;

這兩個方法,在於昨天總算明白一點,特此記錄下。

這兩個方法第一個參數,必須是 對象本身,也就是設置 this的值(參數為空時,預設使用全局對象)

而 calc() 與 apply() 的區別在於 第二個參數的不同、

apply() 的第二個參數,則是合成一個數組,而 calc() 的參數,則是全部顯現的定義(從第二個參數開始)

舉個例子

 1 // 定義個對象
 2 var obj = {};
 3 // 聲明一個函數
 4 function test(sum1,sum2){
 5    console.log(sum1+sum2);  
 6 }
 7 //使用apply方法  沒有自身對象調用 this的值提升為全局對象
 8 test.apply(this,[10,10]); // this的值為window ,輸出 20
 9 
10 // 設置 this的值為 obj
11 test.apply(obj,[10,10]); // this的值為 obj. 輸出20
12 
13 // 值的註意是是,即使只有一個參數,也必須使用 數組的方式傳遞
14 eg: test.apply(this,[10]);  //不然會報錯
15 
16 // 使用 calc 方法 同上,只是參數定義的方式不同
17 test.calc(this,10,10);   // this的值為 window. 輸出20
18 test.calc(obj,10,10);   // this的值為 obj ,輸出 20

其實,看到兩個方法差不多,可能到這,又要很多人糾結了,既然差不多,那麼該使用哪個方法好一點呢。

也沒必要糾結,使用哪一個方法,具體看你傳入的參數哪個方便,哪個方便就使用哪個。

記錄就這麼多,後續有更好的理解,會持續維護。如果有錯的地方,也希望你們指出來。

祝大家學習進步,共勉!

 


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

-Advertisement-
Play Games
更多相關文章
  • 對於學習前端的童鞋,css的掌握是必須的。今天就來實現用css畫出一棵聖誕樹。 主要練習的是css裡面border的練習與掌握程度。 在body創建一個主區域<div></div>:我們用border搭建的三角形在主區域內。 改主區域的背景色:可以給設定一個高度 創建第一個三角形: 這裡的每個區域代 ...
  • 前言 本文大概整理下綁定事件的幾種方式,相容IE8- 的方式(如果需要的話),事件委托,阻止傳播,取消預設行為,event對象等。 之前做的多是手機端頁面,監聽事件也一直是 addEventListener ,現代瀏覽器基本都支持addEventListener ,除了萬惡的IE8及更低版本IE。雖 ...
  • 匿名函數: 之前的文章也有講到,指的是 沒有函數名的函數 嵌套函數呢 ? 請看代碼: 如代碼所示,函數內部嵌入函數,稱之為嵌套函數。 那閉包又是什麼呢? 不多說,看代碼 這麼看,感覺像是,只要是嵌套函數,且能訪問上一層作用域的變數就是閉包。 是這樣嗎? 我們知道,js中,分為全局作用域,局部作用域, ...
  • 代碼段 以上代碼段就是閉包。 閉包使得函數可以繼續訪問定義時的詞法作用域。 閉包實質:將內部函數傳遞到所在的詞法作用域以外,內部函數仍然持有對原始定義作用域的引用。 ...
  • 通常在寫HTML5手機端頁面的時候,我們會發現頁面所顯示元素的比例不正確,那此時我們需要添加的就是: <meta name="viewport" content="width=device-width,initial-scale=1"> 或者是 <meta name="viewport" conte ...
  • 創建文本節點 document.createTextNode() 創建新文本節點,該方法接收一個參數,即要插入節點中的文本信息。 文本節點的合併 當往一個節點中添加多個文本節點後,要取出該節點的全部節點內容,第一個想到的方法是用for迴圈拼接。 Node類型里定義了一個normalize() 方法, ...
  • 一、註:一般倒計時的時間都是後臺傳來的然後渲染到頁面,這裡有2個簡單的倒計時方式 二、如何使用 ...
  • vue的實例對象 首先用js的new關鍵字實例化一個vue el: vue組件或對象裝載在頁面的位置,可通過id或class或標簽名 template: 裝載的內容。HTML代碼/包含指令或者其他組件的HTML片段,template將是我們使用的模板 data: 數據通過data引入到組件中 在組件 ...
一周排行
    -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.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...