JavaScript--我發現,原來你是這樣的JS(四)(看看變數,作用域,垃圾回收機制是啥)

来源:http://www.cnblogs.com/Ry-yuan/archive/2017/10/17/7675894.html
-Advertisement-
Play Games

一、介紹 這是紅寶書(JavaScript高級程式設計 3版)的讀書筆記第四篇,是紅寶書第四章內容(主要是變數和作用域問題),當然其中還有我個人的理解。紅寶書這本書可以說是難啃的,要看完不容易,挺厚的,要看懂更不容易,要熟練js更是難,中間需要不斷的積累與重溫。因此不是讀一兩遍就能把這書吃透,需要多 ...


一、介紹

這是紅寶書(JavaScript高級程式設計 3版)的讀書筆記第四篇,是紅寶書第四章內容(主要是變數和作用域問題),當然其中還有我個人的理解。紅寶書這本書可以說是難啃的,要看完不容易,挺厚的,要看懂更不容易,要熟練js更是難,中間需要不斷的積累與重溫。因此不是讀一兩遍就能把這書吃透,需要多讀,可謂溫故而知新,可以為師矣。

溫馨提示:筆記言辭會有主觀色彩,知識重點記錄。博客內容為基礎,適合初學者。
同系列:
第一篇:JavaScript--我發現,原來你是這樣的JS(一)(初識)
第二篇:JavaScript--我發現,原來你是這樣的JS(二)(基礎概念--軀殼篇,不妨從中文角度看js)
第三篇:JavaScript--我發現,原來你是這樣的JS(三)(基礎概念--靈魂篇)

二、變數

1 .變數介紹:

javascript 中的變數是鬆散型的,既不用去指定改變數的數據類型值,聲明變數時直接使用一個操作符var就行。

//聲明變數
var str = 'string';
var num = 123;
//當不用var時,則為全局變數但不推薦這樣操作
i = 123;

2.變數的兩種值:基本類型和引用類型的值:

js的變數有兩種不同的數據類型的值:基本類型的值和引用類型的值。

  • 基本類型上一篇提到的五種基本類型:null ,undefined,boolean,string,number
  • 引用類型一般是:對象,函數,數組等,都是object類型
//基本類型的值
var num = 123;
var boo = false;
//引用類型的值
var obj = new Object();
var arr = new Array();
var arr2 = {};

3.基本類型的值和引用類型的值的區別

區別一:動態的屬性

動態的屬性怎麼理解:就是可以動態的增加,刪除,改變屬性和方法

  • 對於基本類型的值,不能夠進行這些操作
//基本類型的值
var str = '123';
//添加屬性
str.age = 123;

console.log(str.age); //undefined,說明該值沒被聲明,所以基本類型屬性沒有動態的屬性
  • 對於引用類型的值,能夠進行這些操作,例子沒毛病
//引用類型的值
var person = new Object();
//添加屬性name
person.name = 'ry-yuan';
//添加方法sayHi
person.sayHi = function(){
    console.log('hi');
}

console.log(person.name);   //輸出ry-yuan
person.sayHi();  //輸出hi

區別二:複製變數值不同

  • 對於基本類型變數值之間的複製,會創建一個新值給另一變數,彼此不會相互影響,例子:
var n1 = 100;
//n1複製給n2
var n2 = n1;
console.log(n2); //100
//對n2操作自增
n2++;
console.log(n1); //100,n1不會受n2影響
console.log(n2); //101
  • 對於引用類型之間複製,則不會創建新值,而是 指向同一個對象
//引用變數值
var o1 = new Object();
//複製o1給o2
var o2 = o1;
//為o1添加屬性
o1.name = 'ry-yuan';
//o2也會有這個屬性值
console.log(o2.name); //'ry-yuan'

為什麼引用類型會指向同一個對象?因為o1中存著的值只是一個對象的引用地址,所以o1複製到o2時就把地址複製給o2,兩者的地址相同,所以指向同一個對象。

區別三:傳遞參數

這裡的傳遞參數是對函數傳遞參數。函數參數的按值傳遞的。傳遞參數的兩者的區別和上面複製的一樣。

  • 對於基本數據類型的值,對函數傳遞參數,是將值複製給函數內部的參數,複製另一份獨立的值,所以兩者不影響彼此。
var n = 123;
function add(num){
    num ++;
    console.log(num);
}

//將n傳給函數add
add(n);   //124
console.log(n);  //123,n不會被影響
  • 對於引用數據類型的值,對函數傳遞參數,是將對象在的引用地址值複製給函數內部參數(局部變數),所以操作的是同一個對象。
//引用類型
var p = new Object();
function addName(obj){
    obj.name = 'ry-yuan';
}
console.log(p.name);   //undefined,對象沒有name屬性
//將p傳進函數
addName(p);  
console.log(p.name);   //ry-yuan,對象有了name屬性

區別四:檢測類型

  • 對於基本數據類型,我們使用typeof來確認變數是什麼基本數據類型
var num = 666;
var str = "hello ry";
var boo = false;
var und = undefined;
var n = null;

console.log(typeof num);  //number
console.log(typeof str);  //string
console.log(typeof boo);  //boolean
console.log(typeof und);  //undefined
console.log(typeof n);  //object,特別的null返回的是object
  • 對於引用類型的值,我們使用instanceof操作符,判斷它是什麼類型的對象。不用typeof的原因是typeof檢測引用類型都會返回object,這不是我們想要的,我們想知道它是什麼類型的object
//這裡想知道arr是不是數組類型,如果是返回true,不是返回false
console.log(arr instanceof Array);
//這裡想知道arr是不是正則類型,如果是返回true,不是返回false
console.log(arr instanceof RegExp);
  • 特別的:用instanceof去判斷基本類型值都會返回false,因為基本類型數據都不是object,就更不用判斷是什麼類型的object了。

三、作用域

執行環境即作用域:是變數與函數的可訪問範圍,即作用域控制著變數與函數的可見性和生命周期。在JavaScript中,變數的作用域有全局作用域和局部作用域兩種。

1.全局執行環境:

最外圍的一個執行環境,在web瀏覽器中,全局執行環境被認為是window對象,因此所有的全局變數和函數都是作為window對象的屬性和方法創建的。

2.局部執行環境:

局部執行環境是指在函數內部,函數被創建,就會有一個函數作用域,在函數內定義的變數和方法,函數外面不能訪問,但函數內可以訪問外面的變數和方法。

//聲明一個全局變數,當前最外圍是全局作用域
var g = 1;
//聲明函數fn1
function fn1(){
//局部作用域
    //聲明一個變數
    var i = 10;    
    //可以訪問g
    console.log(g);  //1
    //再聲明一個函數fn2
    function fn2(){
    //局部作用域
        var j = 100;
        //可以訪問g和i
        console.log(g);  //1
        console.log(i);  //100
    }
    
//fn1不能訪問到fn2裡面的變數和方法
console.log(j);    //報錯,j沒被定義
}

//全局作用域中不能訪問i,j
console.log(i);   //報錯,i沒有被定義
console.log(j);   //報錯,j沒有被定義

上圖:

全局作用域中只能訪問紅顏色中有的變數和函數,有g和fn1
局部作用域fn1中能訪問紅色+藍色中的變數和函數,有g,i,fn1,fn2
局部作用域fn2中能訪問整個所有的變數和函數g,i,j,fn1,fn2
綜上越裡面的作用域訪問的就越多。有種不能滲透到內部,只能向外拓展的感覺。

3.沒有塊級作用域

什麼是塊級作用域:用大括弧括起來的區域{ coding.... }

js中沒有塊級作用域,所以有一下這種情況:

for(var i =0 ; i<10 ; i++){
    console.log(i);
}
console.log(i);   //10 ,這裡會有結果,i沒有被銷毀

查詢標記符:

查詢標記符怎麼操作?
來個例子:

var a = 1;
function getNum(){
    return a ;
}

console.log(getNum());  //1

我們來分析一下變數a 的查找過程:
1.首先在getNum函數作用域中找,發現沒有a變數
2.於是向外拓展,到了全局作用域,發現,哎,有a,var了個a,沒錯就是你了。然後獲得這個a。

再來一個例子:

var b = 1;
function get(){
    var b = 2;
    return b;
}
console.log(get());  //2

這次又是怎麼操作:
1.在執行函數get時,我們聲明瞭一個b變數,return時需要用到b,這時我們在局部作用域中找,哎,有了,有個b變數,就是你了,然後就返回了。不用再到外面找了。

4、垃圾回收問題:

1.什麼是js的垃圾回收機制?

答:javascript中垃圾收集機制是自動回收的,不用人工操作,這讓我們更專註於編輯代碼上。 回收垃圾機制是定時執行的,具有周期性。

2.什麼時候會有垃圾?

答:在作用域中當整個作用域中的代碼執行完後,作用域中的變數和方法都會沒用,此時就是被當做垃圾了。比如局部作用域,一個函數執行完,裡面的變數就可以被銷毀,其占用記憶體被釋放。

3.垃圾回收方式?

答:常用的是標記清除:這樣操作:一個變數-->進入環境(被標記,有此標記為不能被清除)-->執行-->離開環境(被標記,這個標記告訴機制能被清除)-->回收機制一段周期後,變數被清除。

4.為什麼還要管理記憶體?

答:分配給web瀏覽器的記憶體比桌面的應用的記憶體少,這是出於安全考慮,為了防止運行js的網頁耗盡系統記憶體導致系統崩潰。所以,開發者發現一旦數據不再用時,就將其值設為null來釋放其引用(解除引用),這做法適用於全局變數和全局對象屬性。

五、說說

博文好久沒更新啦,墮落了,啊啊啊啊,努力努力,積極向上。最近挺多事。不能擋我學習,通通閃開。

本文出自博客園:http://www.cnblogs.com/Ry-yuan/
作者:Ry
如有不足,歡迎指出,覺得寫得好就關註或點贊吧,謝謝。
歡迎轉載,轉載請標明出處


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

-Advertisement-
Play Games
更多相關文章
  • 除了nodejs之外,後端技術(php/java等)及環境搭建一直都是大多數web前端開發人員的弱項,而且每當公司里進來一個新的前端開發人員,第一件事情要做的就是搭建開發環境,需要在新的電腦上安裝IDE、nodejs、npm以及團隊裡面需要用到的技術所需要的依賴,一般需要花費一兩天時間;另外,如果團 ...
  • 背景 公司業務由數以百計的分散式服務溝通,每一個請求路由過來後,會經過多個業務系統並留下足跡,並產生對各種緩存或者DB的訪問,但是這些分散的數據對於問題排查,或者流程優化比較有限。對於一個跨進程的場景,彙總收集並分析海量日誌就顯得尤為重要。在這種架構下,跨進程的業務流會經過很多個微服務的處理和傳遞, ...
  • 背景 隨著公司業務的高速發展以及數據爆炸式的增長,當前公司各產線都有關於搜索方面的需求,但是以前的搜索服務系統由於架構與業務上的設計,不能很好的滿足各個業務線的期望,主要體現下麵三個問題: 1. 不能支持對語句級別的搜索,大量業務相關的屬性根本無法實現 2. 沒有任何搜索相關的指標評價體系 3. 擴 ...
  • 銜接上文[解讀REST] 4.基於網路應用的架構風格,上文總結了一些適用於基於網路應用的架構風格,以及其評估結果。在前文的基礎上,本文介紹一下Web架構的需求,以及在對Web的關鍵協議進行設計和改進的過程中遇到的問題;以及在對基於網路應用的架構風格進行評估的過程中的領悟;結合Web的需求進而推導出R ...
  • 本文純屬自己研究所寫筆記,如果有錯誤還請多多指教提出 版心(container) 版心:class名為.container的容器,其版心的寬度在各個屏幕設備下是不一樣的值,版心兩邊就是留白。 各尺寸下版心寬度如下表: 屏幕設備版心寬度 max-width:768px xs 繼承父元素寬度(即widt ...
  • ...
  • 模態框嵌套 在開發中,遇到需要通過點擊事件觸發第一個模態框,觸發後通過事件喚起第二個模態框,並且通過事件觸發第三個模態框;即模態框嵌套。 模態框嵌套需要用一個模態框包裹所涉及嵌套的模態框,從而點擊觸發模態框不會亂掉。 HTML代碼如下: tabindex 模態框中tabindex屬性w3c的解釋是: ...
  • 前言 晚上逛論壇看到一篇對從事HTML5前端開發的文章寫的非常不錯,和目前的市場形勢差不多,然後我在其基礎上給大家進行加工總結一下分享給大家.今天我們談論的話題是<<為什麼從事HTML5前端開發越來越火,工資高,並且還漲的快>>,針對這個問題進行分析分析. 俗話說的好:”沒有調查,就沒有發言權”,同 ...
一周排行
    -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.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...