1.對象初始化器或對象字面量:{[nameValuePair1[, nameValuePair2[, ...nameValuePairN]]]}數組
參數:nameValuePair1, nameValuePair2, ... nameValuePairNdom
成對的名稱(字符串)與值(任何值),其中名稱經過冒號與值分隔函數
es2015以後簡化了字面量寫法性能
let a = "foo", b = 42, c = {}; let object1 = { a: a, b: b, c: c }; //es2015寫法 let object2 = { a, b, c }; console.log(object1.a === object2.a); //true
2.以構造函數形式來調用:new Object([value])
參數:value 任何值測試
let object = new Object({'foo': 123}); console.log(object.foo); //123
對象屬性能夠用下標小圓點標記或者方括號標記訪問this
let object = new Object({"b": 42}); console.log(object["b"]); // 42 object.b = "baz"; console.log(object.b); //'baz'
從ECMAScript 2015開始,對象初始化語法開始支持計算屬性名,容許在[]中放入表達式,計算結果能夠當作屬性名prototype
let i = 0; let object1 = { ["foo" + ++i]: i, ["foo" + ++i]: i, ["foo" + ++i]: i }; console.log(object1.foo1); // 1 console.log(object1.foo2); // 2 console.log(object1.foo3); // 3 let param = 'size'; let object2 = { [param]: 12, ["mobile" + param.charAt(0).toUpperCase() + param.slice(1)]: 4 }; console.log(object2); // { size: 12, mobileSize: 4 }
語法:Object.defineProperty(obj, prop, descriptor)code
參數:對象
obj 要在其上定義屬性的對象
prop 要定義或修改的屬性的名稱
descriptor 將被定義或修改的屬性描述符
configurable t當且僅當該屬性的 configurable 爲 true 時,該屬性描述符纔可以被改變,同時該屬性也能從對應的對象上被刪除。默認爲 false
enumerable 當且僅當該屬性的enumerable爲true時,該屬性纔可以出如今對象的枚舉屬性中。默認爲 false
value 與屬性關聯的值。能夠是任何有效的JavaScript值(數字,對象,函數等)。默認爲 undefined.
writable 當且僅當該屬性的writable爲true時,value才能被賦值運算符改變。默認爲 false
get 做爲該屬性的 getter 函數,若是沒有 getter 則爲undefined。當訪問該屬性時,該方法會被執行,方法執行時沒有參數傳入,可是會傳入this對象。默認爲 undefined繼承
set 做爲屬性的 setter 函數,若是沒有 setter 則爲undefined。當屬性值修改時,觸發執行該方法,該方法將接受惟一參數,即該屬性新的參數值。默認爲 undefined
返回值:傳遞給函數的對象
(1)writable決定一個屬性可否被賦值
let object = {}; Object.defineProperty(object,"a",{ value: 30, writable: true }); console.log(object.a); //30 object.a = 15; console.log(object.a); //15 Object.defineProperty(object,"b",{ value: 30, writable: false }); console.log(object.b); //30 object.b = 15; //TypeError: Cannot assign to read only property 'b' of object '#<Object>'
(2)enumerable決定該屬性是否能被枚舉
let object = {}; Object.defineProperty(object,"a",{ value: 15, writable: true, enumerable: true }); Object.defineProperty(object,"b",{ value: 16, writable: true, enumerable: false }); Object.defineProperty(object,"c",{ value: 17, writable: true, enumerable: true }); for (let i in object) { console.log(i+"=",object[i]); //a=15 c=17 } console.log(Object.keys(object)); //["a", "c"] console.log(object.propertyIsEnumerable('a')); // true console.log(object.propertyIsEnumerable('b')); // false console.log(object.propertyIsEnumerable('c')); // true
(3)configurable
let object = {}; Object.defineProperty(object,"a",{ get: () => { return 10; }, configurable: false }); Object.defineProperty(object,"a",{ value: 15 }); //TypeError: Cannot redefine property: a console.log(object.a); //10 object.b = 5; //等同於 Object.defineProperty(object,'b',{ value: 5, writable: true, configurable: true, enumerable: true }); Object.defineProperty(object,'d',{ value: 5 }); //等同於 Object.defineProperty(object,'b',{ value: 5, writable: false, configurable: false, enumerable: false });
(4)set/get
function Test() { let x = null; let arr = []; Object.defineProperty(this,'x',{ get: () => { console.log('get'); return x; }, set: (value) => { console.log('set'); x = value; arr.push(x); } }); this.getTest = function () { return arr; } } let test = new Test(); test.x; //get test.x = 25; //set test.x = 30; //set console.log(test.getTest()); //[25, 30]
語法:Object.defineProperties(obj, props)
參數:
obj 要在其上定義屬性的對象
props 要定義其可枚舉屬性或修改的屬性描述符的對象
返回值:被傳遞給函數的對象
let object = {}; Object.defineProperties(object, { 'property1': { value: true, writable: true }, 'property2': { value: 'Hello', writable: false } });
語法:Object.getOwnPropertyDescriptor(obj, prop)
參數:
obj 須要查找的目標對象
prop 目標對象內屬性名稱(String類型)
返回值:若是指定的屬性存在於對象上,則返回其屬性描述符對象(property descriptor),不然返回 undefined
let object = { bar: 42, get foo() { return 17; } }; let foo = Object.getOwnPropertyDescriptor(object, "foo"); // { // configurable: true, // enumerable: true, // get: /*the getter function*/, // set: undefined // } let bar = Object.getOwnPropertyDescriptor(object, "bar"); // { // configurable: true, // enumerable: true, // value: 42, // writable: true // } Object.defineProperty(object, "baz", { value: 8675309, writable: false, enumerable: false }); let baz = Object.getOwnPropertyDescriptor(object, "baz"); // { // configurable: false, // enumerable: false, // value: 8675309, // writable: false // }
語法:Object.getOwnPropertyDescriptors(obj)###
參數:
obj 任意對象
返回值:所指定對象的全部自身屬性的描述符,若是沒有任何自身屬性,則返回空對象
let object = { bar: 42, get foo() { return 17; } }; Object.getOwnPropertyDescriptors(object); //{ // bar: {value: 42, writable: true, enumerable: true, configurable: true}, // foo: {get: ƒ, set: undefined, enumerable: true, configurable: true} // } function SuperClass() {} SuperClass.prototype = { x: 15, y: 20 }; let superClass = new SuperClass(); superClass.a = 50; superClass.b = 100; function SubClass() {} SubClass.prototype = Object.create(SuperClass.prototype, Object.getOwnPropertyDescriptors(superClass)); let subClass = new SubClass(); console.log(subClass.a); //50
語法:Object.getOwnPropertyNames(obj)
參數:
obj 一個對象,其自身的可枚舉和不可枚舉屬性的名稱被返回
返回值:在給定對象上找到的屬性對應的字符串數組
let arr = ["a", "b", "c"]; console.log(Object.getOwnPropertyNames(arr).sort()); // ["0", "1", "2", "length"] // 類數組對象 let object = { 0: "a", 1: "b", 2: "c"}; console.log(Object.getOwnPropertyNames(object).sort()); // ["0", "1", "2"]
語法:Object.getOwnPropertySymbols(obj)
參數:
obj 要返回 Symbol 屬性的對象
返回值:在給定對象自身上找到的全部 Symbol 屬性的數組
let object = {}; let a = Symbol("a"); let b = Symbol.for("b"); object[a] = "localSymbol"; object[b] = "globalSymbol"; let objectSymbols = Object.getOwnPropertySymbols(object); console.log(objectSymbols.length); // 2 console.log(objectSymbols); // [Symbol(a), Symbol(b)] console.log(objectSymbols[0]); // Symbol(a)
語法:Object.create(proto, [propertiesObject])
參數:
proto 新建立對象的原型對象
propertiesObject 可選,這些屬性對應Object.defineProperties()的第二個參數。
返回值:一個新對象,帶着指定的原型對象和屬性
function Father() { this.x = 0; this.y = 0; } Father.prototype.move = function (x,y) { this.x += x; this.y += y; }; function Son() { Father.call(this); //調用父類構造函數 } Son.prototype = Object.create(Father.prototype); Son.prototype.constructor = Son; let son = new Son(); console.log(son instanceof Son); //true console.log(son instanceof Father); //true
語法:Object.getPrototypeOf(object)
obj 要返回其原型的對象
返回值:給定對象的原型,若是沒有繼承屬性,則返回 null
let proto = {}; let object = Object.create(proto); Object.getPrototypeOf(object) === proto; // true let reg = /a/; Object.getPrototypeOf(reg) === RegExp.prototype; // true
語法:Object.assign(target, ...sources)
參數:
target 目標對象
sources 源對象
返回值:目標對象
let obj = { a: 1 }; let copy = Object.assign({}, obj); console.log(copy); // { a: 1 }
此方法是淺拷貝,Object.assign()拷貝的是屬性值,若是源對象的屬性值是一個指向對象的引用,它也只拷貝那個引用值
let obj1 = { a: 0 , b: { c: 0}}; let obj2 = Object.assign({}, obj1); console.log(JSON.stringify(obj2)); // { a: 0, b: { c: 0}} obj1.b.c = 3; console.log(JSON.stringify(obj1)); // { a: 1, b: { c: 3}} console.log(JSON.stringify(obj2)); // { a: 1, b: { c: 3}}
如何實現深拷貝
let obj1 = { a: 0 , b: { c: 0}}; let obj2 = JSON.parse(JSON.stringify(obj1)); obj1.b.c = 4; console.log(JSON.stringify(obj2)); // { a: 0, b: { c: 0}}
合併兩個對象
let obj1 = { a: 1, b: 1, c: 1 }; let obj2 = { b: 2, c: 2 }; let obj3 = { c: 3 }; let newObj = Object.assign({}, obj1, obj2, obj3); console.log(newObj); // { a: 1, b: 2, c: 3 }
語法:Object.is(value1, value2);
參數:
value1 須要比較的第一個值
value2 須要比較的第二個值
返回值:表示兩個參數是否相同的Boolean
如下狀況返回true:
console.log(NaN === NaN); //false console.log(NaN == NaN); //false console.log(Object.is(NaN,NaN)); //true console.log(0 == false); //true console.log(0 === false); //false console.log(Object.is(0,false)); //false console.log(-0 == 0); //true console.log(-0 === 0); //true console.log(Object.is(-0,0)); //false
語法: Object.isExtensible(obj)
參數:
obj 須要檢測的對象
返回值:表示給定對象是否可擴展的一個Boolean
語法:Object.isSealed(obj)
參數:
obj 要被檢查的對象
返回值:表示給定對象是否被密封的一個Boolean
語法:Object.isFrozen(obj)
參數:
obj 被檢測的對象
返回值:表示給定對象是否被凍結的Boolean
語法:Object.preventExtensions(obj)
參數:
obj 將要變得不可擴展的對象
返回值:已經不可擴展的對象
描述:不可擴展對象不能再添加新的屬性,可是原有的屬性仍然可被編輯、刪除
非空對象(其屬性的configurable爲true,writable爲true):
let object = { a:1, b:2 }; console.log(Object.isExtensible(object)); // true Object.preventExtensions(object); console.log(Object.isExtensible(object)); //false console.log(Object.isSealed(object)); // false console.log(Object.isFrozen(object)); // false ob.b = 20; //能夠賦值 console.log(ob.b); //20 delete ob.b; //能夠刪除 console.log(ob); //{a: 1} Object.defineProperty(ob,'c',{ // 不能夠添加屬性 value: 3, writable: true }); //Cannot define property c, object is not extensible
非空對象(其屬性的configurable爲false,writable爲true):
let empty = {}; Object.defineProperty(empty,'foo',{ value: 'baz', writable: true }); Object.preventExtensions(empty); console.log(Object.isExtensible(empty)); // false console.log(Object.isSealed(empty)); // true console.log(Object.isFrozen(empty)); // false
非空對象(其屬性的configurable爲true,writable爲false):
let empty = {}; Object.defineProperty(empty,'foo',{ value: 'baz', writable: false, configurable: true }); Object.preventExtensions(empty); console.log(Object.isExtensible(empty)); // false console.log(Object.isSealed(empty)); // false console.log(Object.isFrozen(empty)); // false
非空對象(其屬性的configurable爲false,writable爲false):
let empty = {}; Object.defineProperty(empty,'foo',{ value: 'baz' }); Object.preventExtensions(empty); console.log(Object.isExtensible(empty)); // false console.log(Object.isSealed(empty)); // true console.log(Object.isFrozen(empty)); // true
空對象:
let empty1 = {}; console.log(Object.isExtensible(empty1)); // true Object.preventExtensions(empty1); console.log(Object.isExtensible(empty1)); //false console.log(Object.isSealed(empty1)); // true console.log(Object.isFrozen(empty1)); // true
語法:Object.seal(obj)
參數:
obj 將要被密封的對象
返回值:被密封的對象
描述:密封一個對象會讓這個對象變的不能添加新屬性,且全部已有屬性會變的不可配置
空對象:
let empty = {}; Object.seal(empt); console.log(Object.isExtensible(empty)); // false console.log(Object.isSealed(empty)); // true console.log(Object.isFrozen(empty)); // true
非空對象:
let object = { foo: 'bar' }; Object.seal(object); object.foo = 'baz'; //可編輯 console.log(object.foo); //baz delete object.foo; //TypeError: Cannot delete property 'foo' of #<Object> console.log(Object.isExtensible(object)); // false console.log(Object.isSealed(object)); // true console.log(Object.isFrozen(object)); // false
語法:Object.freeze(obj)
參數:
obj 要被凍結的對象
返回值:被凍結的對象
描述:被凍結對象自身的全部屬性都不可能以任何方式被修改,若是一個屬性的值是個對象,則這個對象中的屬性是能夠修改的,除非它也是個凍結對象
let object1 = { property1: 42 }; Object.freeze(object1); console.log(Object.isExtensible(object1)); // false console.log(Object.isSealed(object1)); // true console.log(Object.isFrozen(object1)); // true object1.property1 = 33; // TypeError: Cannot assign to read only property 'property1' of object '#<Object>' console.log(object1.property1); //42 let object2 = { internal: {} }; Object.freeze(object2); object2.internal.a = 'aValue'; console.log(object2.internal.a); //aValue
語法:Object.entries(obj)
參數:
obj 能夠返回其可枚舉屬性的鍵值對的對象
返回值:給定對象自身可枚舉屬性的鍵值對數組
const object1 = { foo: 'bar', baz: 42 }; console.log(Object.entries(object1)); // [ ['foo', 'bar'], ['baz', 42] ] // array like object const object2 = { 0: 'a', 1: 'b', 2: 'c' }; console.log(Object.entries(object2)); // [ ['0', 'a'], ['1', 'b'], ['2', 'c'] ] // array like object with random key ordering const object3 = { 100: 'a', 2: 'b', 7: 'c' }; console.log(Object.entries(object3)); // [ ['2', 'b'], ['7', 'c'], ['100', 'a'] ]
語法:Object.keys(obj)
參數:
obj 要返回其枚舉自身屬性的對象
返回值:一個表示給定對象的全部可枚舉屬性的字符串數組
let arr = ['a', 'b', 'c']; console.log(Object.keys(arr)); // ['0', '1', '2'] // array like object let object = { 0: 'a', 1: 'b', 2: 'c' }; console.log(Object.keys(object)); // ['0', '1', '2']
語法:Object.values(obj)
參數:
obj 被返回可枚舉屬性值的對象
返回值:一個包含對象自身的全部可枚舉屬性值的數組
let arr = ['a', 'b', 'c']; console.log(Object.values(arr)); // ['a', 'b', 'c'] // array like object let object = { 0: 'a', 1: 'b', 2: 'c' }; console.log(Object.values(object)); // ['a', 'b', 'c']
語法:obj.hasOwnProperty(prop)
參數:
prop 要檢測的屬性 字符串 名稱或者 Symbol
返回值:用來判斷某個對象是否含有指定的屬性的 Boolean
描述:這個方法能夠用來檢測一個對象是否含有特定的自身屬性;和 in 運算符不一樣,該方法會忽略掉那些從原型鏈上繼承到的屬性
let object = new Object(); object.prop = 'exists'; console.log(object.hasOwnProperty('prop')); // true console.log(object.hasOwnProperty('toString')); // false console.log(object.hasOwnProperty('hasOwnProperty')); // false console.log('toString' in object); // true console.log('prop' in object); // true console.log('hasOwnProperty' in object); // true
語法:prototypeObj.isPrototypeOf(object)
參數:
object 在該對象的原型鏈上搜尋
返回值:Boolean,表示調用對象是否在另外一個對象的原型鏈上
function Foo() {} function Bar() {} function Baz() {} Bar.prototype = Object.create(Foo.prototype); Baz.prototype = Object.create(Bar.prototype); let baz = new Baz(); console.log(Baz.prototype.isPrototypeOf(baz)); // true console.log(Bar.prototype.isPrototypeOf(baz)); // true console.log(Foo.prototype.isPrototypeOf(baz)); // true console.log(Object.prototype.isPrototypeOf(baz)); // true
語法:obj.propertyIsEnumerable(prop)
參數:
prop 須要測試的屬性名
返回值:用來表示指定的屬性名是否可枚舉的Boolean
let o = {}; let a = []; o.prop = 'is enumerable'; a[0] = 'is enumerable'; o.propertyIsEnumerable('prop'); // 返回 true a.propertyIsEnumerable(0); // 返回 true
語法:object.toString()
返回值:表示該對象的字符串
let object = new Object(); console.log(object.toString()); //[object Object] function Animal(name,age,color,sex) { this.name = name; this.age = age; this.color = color; this.sex = sex; } Animal.prototype.toString = function () { let string = this.name + "是一個" + this.age + "歲的" + this.color + "的" + this.sex + "動物"; return string; }; let animal = new Animal("小可愛",1,"灰色","雌性"); console.log(animal.toString()); //小可愛是一個1歲的灰色的雌性動物
語法:object.valueOf()
返回值:返回值爲該對象的原始值
function Animal(name,age,color,sex) { this.name = name; this.age = age; this.color = color; this.sex = sex; } let animal = new Animal("小可愛",1,"灰色","雌性"); console.log(animal.valueOf()); //{name: "小可愛", age: 1, color: "灰色", sex: "雌性"}