重新學習了一遍js對象,但方法的靈活使用需要代到案例中學習,共勉 ...
—————————————————————————————————————————————————————————
對象有哪些(導圖)
-
內建對象
-
數據封裝對象
- Object對象
- Object.prototype
- Array對象
- Function對象
基本包裝類型
- Number對象
- Boolean對象
- String對象
-
工具類對象
- Math對象
- Date對象
- RegExp對象
-
全局對象
- Global對象
-
錯誤對象
- Error對象
-
數據封裝對象
- 自定義對象
註解:基本包裝類型
因為有了基本包裝類型,所以js中的基本類型值可以被當做對象來訪問。
共同特征:
- 每個包裝類型都映射到同名的基本類型
- 在讀取模式下訪問基本類型值時,就會創建對應的基本包裝類型的一個對象,從而方便了數據操作
- 操作基本類型值的語句已經執行完畢,就會立即銷毀新創建的包裝對象
—————————————————————————————————————————————————————————
Object對象
-
Object對象是Js中所有對象的父級對象,我們創建的所有對象都繼承於此
方法:
未歸類:
Object.create(): |
指定原型對象和屬性創建一個對象 |
Object.defineProperty(): |
給對象添加/修改一個屬性並指定該屬性的配置 |
Object.defineProperties(): |
在一個對象上添加或修改一個或者多個自有屬性,並返回該對象 |
Object.keys(): |
方法會返回一個由給定對象的所有可枚舉自身屬性的屬性名組成的數組,數組中屬性名的排列順序和使用for-in迴圈遍歷該對象時返回的順序一致(兩者的主要區別是for-in還會遍歷除一個對象從其原型鏈上繼承到得可枚舉的屬性) |
Object.getOwnPropertyNames(): |
返回一個由指定對象的所有自身屬性的屬性名(包括不可枚舉屬性)組成的數組 |
Object.getOwnPropertyDescriptor(): |
返回指定對象上一個自有屬性對應的屬性描述符。(自有屬性指的是直接賦予該對象的屬性,不需要從原型鏈上進行查找的屬性)) |
Object.getPrototypeOf(): |
返回指定對象的原型(也就是該對象內部屬性[[Prototype]]的值) |
可擴展性方法:
內建對象和自定義對象是顯示可擴展的,宿主對象的可擴展性由JavaScript引擎定義。可擴展性的目的是為了將對象鎖定,防止外界干擾,通常和對象的屬性的可配置的行與可寫性配合使用
Object.freeze(): |
凍結一個對象。凍結對象是指那些不能添加新的屬性,不能修改已有屬性的值,不能刪除已有屬性,以及不能修改已有屬性的可枚舉性、可配置性、可寫性的對象。也就是說這個對象永遠不能改變的 p.s. 隻影響對象本身,不影響從其原型繼承來的屬性。 |
Object.isFrozen(): |
判斷對象是否已經被凍結 |
Object.preventExtensions(): |
阻止對象擴展 |
Object.isExtensible(): |
檢測一個對象是否可擴展(是否可以在它上面添加新的屬性) |
Object.seal(): |
可以讓一個對象密封,並返回被密封之後的對象。密封對象是指那些不能添加新的屬性、不能刪除已有屬性,以及不能修改已有屬性的可枚舉性、可配置性、可寫性,但可能可以修改已有屬性的值的對象 p.s. 如果對象的存儲器屬性具有setter方法,存取器屬性將不受影響,仍可以通過屬性賦值調用它們 |
Object.isSealed(): |
檢測一個對象是否被密封sealed |
var obj = {}; // 檢測是否可擴展 console.log(Object.isExtensible(obj)); // 內建對象Date var oTest = new Date(); console.log(Object.isExtensible(oTest)); oTest.x = 1; console.log(oTest.x); // 對象鎖定 oTest2 = Object.preventExtensions(oTest); // 證明oTest2與oTest是同一對象,已經不可擴展 console.log(oTest2 === oTest); console.log(Object.isExtensible(oTest2)); // 此時顯示y為undefined未定義的 oTest2.y = 1; console.log(oTest2.y); // defineProperty方法會報錯,提示不可擴展 // Object.defineProperty(oTest2,'z',{value:1}); // ******************************************************************* // 封閉對象seal() var oTest3 = { x: 1, y: 2 }; var oTest4 = Object.seal(oTest3); // false不可擴展 console.log(Object.isExtensible(oTest3)); // true已經被封閉了 console.log(Object.isSealed(oTest3)); // 自身已有的屬性不受影響 oTest3.y = 55; console.log(oTest3.y); // 提示不能將新屬性定義為訪問器屬性 // Object.defineProperty(object,'username',{ // get:function(){ // return 'this is a test'; // } // }); oTest3.z = 111; console.log(oTest3.z); // 已有屬性也不會被刪除 delete oTest3.x; console.log(oTest3.x); // 檢測屬性 configurable:false,不可配置 console.log(Object.getOwnPropertyDescriptor(oTest3, 'x')); // ******************************************************************* // 凍結對象freeze() console.log('freeze:'); var oTest5 = { x: 1, y: 2, z: 3 }; oTest6 = Object.freeze(oTest5); // 凍結後檢測對象 writable:false,變成了只讀屬性 console.log(Object.getOwnPropertyDescriptor(oTest6, 'x')); // 檢測是否已經被凍結 console.log(Object.isFrozen(oTest6)); // ******************************************************************* // 淺凍結 // 在對象中添加子對象,向子對象添加屬性 console.log('Shallow frozen:'); var oTest7 = { internal: {} }; Object.freeze(oTest7); oTest7.internal.x = 1; console.log(oTest7.internal.x); // 在這裡只凍結了oTest7的internal,internal對象沒有被凍結 console.log(Object.getOwnPropertyDescriptor(oTest7, 'internal')); console.log(Object.getOwnPropertyDescriptor(oTest7.internal, 'x')); // ******************************************************************* // 遞歸凍結,包括子對象全部凍結 console.log('Deep frozen:'); function deepFreeze(obj) { var prop, propKey; Object.freeze(obj); // 通過for迴圈來檢測是否為子對象,並遞歸調用 for (propKey in obj) { prop = obj[propKey]; // 如果這個對象沒有私有屬性||類型不等於Object||已凍結 // 則跳過 - 進入下一迴圈 if (!obj.hasOwnProperty(propKey) || !(typeof prop === 'object') || Object.isFrozen(prop)) { continue; } deepFreeze(prop); } } var oTest8 = { internal: { x: 1 } } deepFreeze(oTest8); oTest8.internal.y = 2; console.log(oTest8.internal.y); console.log(Object.getOwnPropertyDescriptor(oTest8, 'internal')); console.log(Object.getOwnPropertyDescriptor(oTest8.internal, 'x')); console.log(Object.getOwnPropertyDescriptor(oTest8.internal, 'y')); // ******************************************************************* // 凍結規則: // 1.如果一個對象是可擴展的,那則是非凍結的, // 2.一個不可擴展的對象同時也是一個凍結的對象 var oTest9 = {}; Object.preventExtensions(oTest9); console.log(Object.isFrozen(oTest9)); // 3.空對象和非空對象對比,預設都是不被凍結的,可擴展的 var oTest10 = {}; var oTest11 = { x: 1 }; // 4.空對象禁止擴展後,是被凍結的 Object.preventExtensions(oTest10); console.log('3:' + Object.isFrozen(oTest10)); // 5.非空對象禁止擴展後,不凍結 Object.preventExtensions(oTest11); console.log('4:' + Object.isFrozen(oTest11)); // 6.非空對象刪除已有屬性後,凍結 delete oTest11.x; console.log('5:' + Object.isFrozen(oTest11)); // 7.如果一個不可擴展的對象擁有一個可寫但不可配置的屬性,非凍結 // 8.如果一個不可擴展的對象擁有一個不可配置但可寫的屬性,非凍結 // 9.如果一個不可擴展的對象擁有一個訪問器屬性,非凍結 // 10.被凍結的對象同樣也是被密封的和不可擴展的
檢測對象已有屬性方法:
- in:包括原型上的
- hasOwnProperty():僅檢測對象自己有的屬性
function foo() {} foo.prototype.z = 5; var obj1 = new foo(); obj1.x = 1; obj1.y = 2; console.log('x' in obj1); console.log('y' in obj1); console.log('toString' in obj1); console.log('nonono' in obj1); console.log(obj1.hasOwnProperty('x')); console.log(obj1.hasOwnProperty('z'));
—————————————————————————————————————————————————————————
Object.prototype
-
屬性:Object.prototype.constructor:返回一個指向創建了該對象原型的函數引用
方法:
Object.prototype.isPrototypeOf(): |
檢測一個對象是否存在於另一個對象的原型鏈上 |
Object.prototype.propertyIsEnumerable(): |
檢測指定的屬性名是否是當前對象可枚舉的自身屬性 |
Object.prototype.toString(): |
返回一個代表該對象的字元串 |
Object.prototype.valueOf(): |
返回的詩this值,即對象本身 |
—————————————————————————————————————————————————————————
Array對象
Array對象圖解
- JavaScript的數組由索引和值組成
- 索引即可以是正整數,也可以是其他類型,但其他類型索引不算在數組長度內
- 當數組索引不連續時,又稱為稀疏數組,但相比較連續數組來說,稀疏數組查找元素的速度較慢,未定義部分為undefined
方法:
檢測數組方法:
Array.isArray(value) |
檢測value是否為數組 |
轉換方法:
toString() |
把數組轉換為字元串,並返回結果。 |
toLocaleString() |
把數組轉換為本地數組,並返回結果。 |
valueOf() |
返回數組對象的原始值。 |
join() |
把數組的所有元素放入一個字元串。元素通過指定的分隔符進行分隔。 |
棧方法:
pop() |
刪除並返回數組的最後一個元素 |
push() |
向數組的末尾添加一個或更多元素,並返回新的長度。 |
隊列方法:
shift() |
刪除並返回數組的第一個元素 |
unshift() |
向數組的開頭添加一個或更多元素,並返回新的長度。 |
重排序方法:
reverse() |
顛倒數組中元素的順序。 |
sort() |
對數組的元素進行排序 |
操作方法:
concat() |
連接兩個或更多的數組,並返回結果。 |
slice() |
從某個已有的數組返回選定的元素 |
splice() |
刪除元素,並向數組添加新元素。 |
迭代方法:
every() |
如果該函數對每一項都返回true,則true |
filter() |
該函數返回true的項組成數組 |
forEach() |
這個方法沒有返回值 |
map() |
返回每次函數調用的結果組成的數組 |
some() |
如果該函數的任一項返回true,則返回true |
位置方法:
Array.indexOf() |
從數組開頭向後查找 |
Array.lastIndexOf() |
從數組末尾向前查找 |
其他方法:
toSource() |
返回該對象的源代碼。 |
歸併方法:
迭代數組的所有項,構建一個最終返回的值
Array.reduce() |
從數組第一項開始,逐個遍歷到最後 |
Array.reduceRight() |
從數組最後一項開始遍歷 |
以下是手冊中沒有的為prototype中定義的方法
- Array.map()
- Array.filter()
- Array.reduce()
- Array.reduceRight()
- Array.some()
- Array.every()
- Array.indexOf()
- Array.lastIndexOf()
- Array.isArray()
數組基本操作及常用方法
// Array對象 - 數組 // 創建數組 var colors1 = new Array(); var colors2 = new Array(20); // 指定數組長度,預設為undefined*20,長度20 console.log(colors1.length); console.log(colors2.length); var colors3 = new Array(3); // 如果傳參為1個數字則預設為指定長度 console.log(colors3); var colors4 = new Array("1"); // 傳入非數值則為數組內容 console.log(colors4); var colors5 = ['1', 'aaa', 21, 3.33]; console.log(colors5); var colors6 = []; // 空數組 console.log(colors6); // p.s.不要使用以下形式創建數組,容易出現歧義,數組項數不確定 // var arr = [1,2,]; // 2或3項 // var arr = [,,,,,]; // 5或6項 // ***************************************************************** // 利用length屬性也方便為數組添加元素 console.log(colors5.length); colors5[colors5.length] = "new1"; colors5[colors5.length] = "new2"; console.log(colors5); colors5.length = 2; // 指定長度後如果比之前小,則會移除多餘的部分 console.log(colors5); colors5.length = 10; // 擴大length,則填補undefined console.log(colors5); // 數組項的上限是4294967295 var colors7 = new Array(4294967295); // var colors7 = new Array(4294967296); // RangeError: Invalid array length console.log(colors7); // ***************************************************************** // 數組中可以存放所有的變數形式 var arr2 = [1, 2.3, null, true, false, undefined, [1, 2, 3, 4], { x: 1, y: 2, z: 3 }]; console.log(arr2); console.log(arr2[6][1]); console.log(arr2[7].y); // 列印數組長度 console.log(arr2.length); // 引用內容來創建數組 var num = 1; var arr3 = [num, num + 1, num * 2]; console.log(arr3); // 通過構造函數的方式 var arr5 = new Array; // 多個參數時定義的是數組的內容 var arr6 = new Array(1, 2, 3); console.log(arr6); // 任何變數都可以作為索引值,但只有非負整數作為索引時長度才會變化 var arr8 = new Array(); arr8[2.3] = 'a'; arr8[-2333] = 'b'; arr8['c'] = 'b'; // ***************************************************************** // 通過for in取出元素以及元素的索引 for (var i in arr8) { console.log(i + ":" + arr8[i]); } console.log(arr8); console.log(arr8.length); arr8[2] = 'd'; console.log(arr8); console.log(arr8.length); // 壓棧彈棧操作 var arr9 = new Array(1, 2, 3); arr9.push(4, 5, 6, 7); console.log(arr9); console.log(arr9.length); arr9.pop(); arr9.pop(); console.log(arr9); console.log(arr9.length); // 在首部加入元素 arr9.unshift(9, 10, 11, 12); console.log(arr9); // 首部彈出元素 arr9.shift(); console.log(arr9); // 刪除元素,但刪除後長度不變 delete arr9[3]; console.log(arr9); console.log(arr9.length); // 稀疏數組遍歷 var arr10 = [1, 2, 3]; arr10[100] = 99; // for-in遍歷集成下來的屬性 for (var i in arr10) { console.log(i); } // 在forEach()中定義函數體, arr10.forEach(Test); function Test(element, index, array) { console.log("array:" + array + " index:" + index + " element:" + element); } // ***************************************************************** // 檢測數組 // instanceof // 缺點:假定只有一個全局執行環境,如果網頁包含多個框架,實際存在兩個以上不同的全局執行環境時,就有兩個以上不同版本的Array構造函數,如果從一個框架向另一個框架傳入一個數組,那麼傳入的數組與第二個框架中原生創建的數組分別具有各自不同的構造函數 console.log(colors5 instanceof Array); // isArray()方法 console.log(Array.isArray(colors2)); // ***************************************************************** // 轉換方法 // toString() console.log(colors5.toString()); // valueOf() console.log(colors5.valueOf()); alert(colors5.valueOf()); // alert使用valueOf方法時會在後臺調用toString() alert(colors5); // toLocaleString() // 與toString()和valueOf()一樣可以返回值 // 調用的同時會創建一個數組值的以逗號分隔的字元串,不同之處在於為了取得每一項的值,調用的是每一項的toLoaclString() var person1 = { toLocaleString: function() { return "111"; }, toString: function() { return "222"; } }; var person2 = { toLocaleString: function() { return "333"; }, toString: function() { return "444"; } }; var people = [person1, person2]; alert(people); // 預設調用的是toString()方法 alert(people.toString()); alert(people.toLocaleString()); // join() 使用不同的分隔符來構建字元串 console.log(colors5.join('||')) // ***************************************************************** // 棧方法 colors5.push('aaa', 'bbb'); // 壓棧 console.log(colors5); var item1 = colors5.pop(); // 彈棧 console.log(item1); console.log(colors5); // 隊列方法 var len = colors5.push('ccc', 'ddd'); // 壓棧 console.log(len); var item2 = colors5.shift(); // 定位到首部並移除,返回移除的元素 console.log(item2); console.log(colors5); colors5.unshift('new'); // 在隊列頭部推入元素,可以unshift(),pop()聯用模擬反向隊列 console.log(colors5);
// 通過.map方法返回新函數,在map方法中調用Trans函數,對數組中的每一個元素進行替換操作 var arr = ['abc', 'bcd', 'cde']; res = arr.map(Trans); function Trans(x) { return x.replace(/c/g, '!').toUpperCase(); } console.log(res); // filter var arr = [1, 3, 4, 5, 6, 6, 123, 6547, null, undefined, ""]; res = arr.filter(function(x) { return (x <= 10) && (x != null) && (x != ""); }) console.log(res); // reduce作為累加器,從左到右依次進行返回運算 var arr = [1, 2, 3, 4, 5, 6, 7, 8]; res = arr.reduce(function(a, b) { return a - b; }) console.log(res); res = arr.reduce(function(a, b) { return a * b; }) console.log(res); // reduceRight從右往左 res = arr.reduceRight(function(a, b) { return a - b; }) console.log(res); // every函數檢測是否所有的元素都符合要求,有不符合的則返回false var age = [12, 34, 55, 4]; res = age.every(function(x) { return x >= 18; }) console.log(res); // some檢測的是否有符合的,有符合的則返回true var age = [12, 34, 55, 4]; res = age.some(function(x) { return x >= 18; }) console.log(res); // 索引 var arr = ['a','b','c','b','d','b','e']; // 第一個索引位 res = arr.indexOf('b'); console.log(res); // 最後一個索引位 res = arr.lastIndexOf('b'); console.log(res); // 索引開始位置 res = arr.indexOf('b',3); console.log(res);
—————————————————————————————————————————————————————————
Date對象
方法
創建日期
Date.parse() |
解析一個字元串,返回所經過的毫秒數 |
Date.UTC() |
解析一個字元串,返回所經過的毫秒數 |
獲取當前時間
Date.now() |
返回當前時間的毫秒數 |
繼承的方法
toString() |
把時間轉換為字元串,並返回結果。不同瀏覽器結果不同 |
toLocaleString() |
把時間轉換為字元串,並返回結果。不同瀏覽器結果不同 |
valueOf() |
不返回字元串,返回日期的毫秒錶示,可以通過比較操作符來比較日期值 |
日期格式轉換