這次的分享,主要還是想跟大家聊聊Javascript語言中很重要的概念之一,對象。為什麼說之一呢?因為Javascript其他重要概念還包括:作用域 作用域鏈 繼承 閉包 函數 繼承 數組 ...... 有機會會跟大家分享這些概念的。以下的介紹會分為如下:1:前言2:概述 2.1:對象創建 2.2: ...
這次的分享,主要還是想跟大家聊聊Javascript語言中很重要的概念之一,對象。為什麼說之一呢?因為Javascript其他重要概念還包括:作用域 作用域鏈 繼承 閉包 函數 繼承 數組 ...... 有機會會跟大家分享這些概念的。
以下的介紹會分為如下:
1:前言
2:概述
2.1:對象創建
2.2:對象鍵名與鍵值
2.3:對象屬性
2.4:對象引用
3:對象屬性
3.1:讀取屬性
3.2:屬性賦值
3.3:查看所有屬性
3.4:刪除屬性
3.5:遍歷屬性
1:前言
Javascript擁有七種數據類型,其中分為兩類。原始數據和複雜數據類型。原始數據類型:包括 字元串,數組,數字,布爾值,Null,Undefined。複雜數據類型:包括 對象。
對象是Javascript的核心概念,也是最重要的數據類型。Javascript所有數據都可以視為對象。都可以使用內置的方法。但是除了兩個例外,就是Null和Undefined。
代碼如下:
1 [1,2,3].toString() // "1,2,3" 2 "ha".toString() // "ha" 3 false.toString() // 'false'
一個對象就是一系列屬性的集合,一個屬性包含一個名字和一個值。一個屬性也可以是函數,這種情況下這個屬性被稱為方法,可以拿汽車來做一個形象化的對比。
汽車是一個對象,擁有屬性顏色,重量,車型,方法便是可以開上馬路了。
寫在代碼中,就是:
1 var car = { 2 "color": "red", 3 "weight": "1.4噸", 4 "module": "SUV" 5 "use": function() { 6 return "drive"; 7 } 8 };
2:概述
2.1:對象創建
1 var o = { 2 "p": "Hello World", 3 "name": "Keith Chou" 4 };
上面的代碼中,大括弧就定義了一個對象,它被賦值給全局變數o。這個對象(對象的名字隨便定義)內部包含一個鍵值對,p是鍵名,字元串Hello World是鍵值。鍵名和鍵值用":"分離,不同鍵值對之前通過","分離,最後一個鍵值可不用逗號。但是我建議最後都不要加上。右花括弧" } "後邊要加上分號";"。
對象創建有三種方法:
1 var o1 = {}; 2 var o2 = new Object(); 3 var o3 = Object.crete(null);
上面三行語句都是等價的。第一種使用花括弧來創建一個對象,這是最簡便的方法。第二種採用構造函數的寫法清晰的表明瞭意圖。第三種寫法多用於對象繼承的場合。
2.2 鍵名與鍵值
1 var o = { 2 "say": "Hello World", 3 "name": "Keith Chou", 4 "height": "180", 5 "age": 21 6 };
以上用第一種方法創建對象,並賦值給全局變數o。鍵名即如下值:"say","name","height","weight"。鍵值即如下值:"Hello World","Keith Chou" ...
對象的所有鍵名都是字元串,加不加雙引號都可以。對象的鍵值如果是英文,則必須加引號,否則會當成變數處理。如果是數字,加了引號則當成字元串處理,不加引號當成數字類型處理。
1 var o = { 2 o1: 180, 3 o2: "180" 4 }; 5 o.o1 // 180,數字類型 6 o.o2 // "180" ,字元串類型
註意,Javascript的保留字可以不加引號當作鍵名。
1 var o = { 2 for: 1, 3 class: 2 4 }; 5 6 o.for //1 7 o.class //2
2.3 對象屬性
對象的每一個“鍵名”又稱為“屬性”(property),它的“鍵值”又稱為屬性值,可以是任何數據類型。如果一個屬性值為函數,通常把這個屬性稱為“方法”,它可以像函數那樣調用。
1 var o = { 2 p: function(x) { 3 return 2 * x; 4 } 5 }; 6 o.p(2) //4
上面對象申明瞭一個方法p,它就是一個函數。這裡簡單說一下,函數聲明的三個步驟:function,函數名,函數參數,函數體。其中函數名和函數參數都是可選的,即也可以不使用。不使用的情況下稱為匿名函數。
屬性可以動態創建,不必在對象聲明的時候就指定。
1 var obj = {}; 2 obj.keith = 123; 3 obj.rascal = false; 4 obj.keith; // 123
因為對象的方法就是函數,所以也有name屬性。
1 var obj = { 2 m1: function f() {}, 3 m2: function() {} 4 }; 5 obj.m1.name // "f" 6 obj.m2.name // " " , 空字元串
2.4 對象引用
對於複雜數據類型,如果不同的變數名指向同一個對象,那麼它們都是這個對象的引用,也就是說指向同一個記憶體地址。修改其中一個變數,會影響到其他所有變數。也就是 傳址傳遞。
var o1 = { a : 1}; var o2 = o1; o1.a; // 1 o2.a; // 1 o2.a = 11; o1.a // 11
上面o1和o2都指向了同一個對象,當o2修改了o1的屬性a時,訪問o1的屬性a變成11。複雜數據類型的傳址傳遞的特點就是當修改其中一個變數,會影響到其他對象對該變數的訪問。
此時,如果取消某一個變數對於原對象的引用,不會影響到另一個變數。
1 var o1 = {}; 2 var o2 = o1; 3 var o1 = 1; 4 o2 // { }
上面代碼中,o1和o2指向同一個對象,然後o1的值變為1,這時不會對o2產生影響,o2還是指向原來的那個對象。
但是,對於原始數據類型的值,則是傳值傳遞。傳值傳遞的特點就是修改其中一個變數,不會影響到其他變數。也就是只是對該變數copy一份而已。
1 var x = 1; 2 var y = x; 3 x = 2; 4 y; // 1
上面的代碼中,全局變數x發生變化,y的值並不變。也就是上面所說的copy了x的值,沒有指向同一個記憶體地址。
3 :對象屬性
3.1:讀取屬性
1 var o = { 2 name: "Keith Chou", 3 born: "1995" 4 };
訪問屬性有兩種方法。
1 o.name // "Keith Chou" 2 o["name"] // "Keith Chou"
第二種方法訪問屬性的時候必須加上引號,單引號雙引號都可以。
3.2:屬性的賦值
點運算符和方括弧運算符,不僅可以用來讀取值,還可以用來賦值。
1 var o = {}; 2 o.p = "abc"; 3 o["p"] = "abc";
3.3:查看所有屬性
查看一個對象本身的所有屬性,可以使用Object.keys 方法。
1 var o = { 2 "say": "Hello World", 3 "name": "Keith Chou", 4 "height": "180", 5 "weight": "120" 6 }; 7 Object.keys(o); 8 // ["say","name","height","weight"]
可以看出,js返回一個數組對象。
3.4:刪除屬性
Javascript使用delete來刪除屬性。delete操作符只能用來刪除對象本身的屬性,而不能用於刪除繼承自原型的屬性。
1 var o = { p: 1 }; 2 Object.keys(o); 3 // ["p"] 4 delete o.p; 5 o.p; 6 // undefined; 7 Object.keys(o); 8 // [ ]
delete刪除了o對象的p屬性。刪除後,再次訪問屬性就會返回undefined。而且使用Object.keys訪問對象屬性時,o對象也不再包括任何屬性。
toString()方法是對象o繼承自原型Object.prototype的一個方法,雖然delete命令返回true,但該屬性並沒有被刪除。
1 var o = {}; 2 delete o.toString(); // true 3 o.toString();
註意,delele也可以用於刪除一個不存在的屬性,不過也不會報錯,會返回true。不過這個看起來好像沒有什麼用處阿。
1 var o = {}; 2 delete o.p // true
最後,delete操作符也不能用於刪除var命令聲明的變數,只能用來刪除對象本身的屬性。
1 var o = 1; 2 delete o; // false 3 delete window.o // false
上面代碼中,o是在全局作用域下聲明的一個全局變數,全局變數預設是window對象的屬性,預設情況下delete不得刪除。
3.5:遍歷屬性
for...in迴圈用來遍歷一個對象的所有屬性。
1 var o = { 2 a: 1, 3 b: 2, 4 c: 3 5 }; 6 for (var i in o) { 7 console.log(i); 8 } // a , b , c
上面代碼中,定義了一個對象o,使用for..in迴圈來在控制台輸出o對象中的每一個屬性。 var i in o 是指 聲明一個變數i,用於遍歷o對象中的所有屬性。
for...in迴圈有兩個使用註意點:
- 它遍歷的是所有對象可遍歷的屬性,會跳過不可遍歷的屬性。
- 它不僅會遍歷對象自身的屬性,還會遍歷繼承的屬性。