ES6+ 对象的扩展
JavaScript 中对象是非常重要的数据结构,ES6 对对象进行了极大的扩展,使用上也更加简洁。前面我们学习了 和 是对象扩展的其中的一部分,本节和后面几节会对 Object 的扩展进行系统的介绍。后面我们还会学到新的数据结构 Set 和 Map 也是对对象的扩展,另外,还有 Proxy 和 Reflect 也是对象的重大。本节主要学习以下几点
ES6 允许直接写入变量和,作为对象的和
在 ES5 中我们知道,在定义对象时的值是必须要写的,在 ES6 中规定,如果名和定义的变量名是一样的,就可以在对象中直接写这个变量名作为对象中的一项。如下:
var name = 'imooc';
// ES5
var obj1 = {
name: name,
}
// ES6
var obj2 = {
name,
}
上面中的 obj1 和 obj2 是一样的意思。变量 name 可以直接写在大括号中。这时,名就是变量名,值就是变量值。
下面我们来看在中返回对象的实例:
// ES5
function getObj(x, y) {
return {x: x, y: y};
}
// 等同于 ES6
function getObj(x, y) {
return {x, y};
}
getObj(, ) // {x: 1, y: 2}
上面中的可以看出,在我们平常开发中,组装数据时是非常方便、有用的。
除了可以简写,对象中的也是可以简写的,而且更加简洁明了。我们来看下面的例子:
const name = '张三'
// ES5
var person = {
name: name,
getName: function() {
console.log('imooc')
}
};
// ES6
var person = {
name,
getName() {
console.log(this.name)
}
};
console.log(person) // {name: "imooc", getName: ?}
上面的中,ES5 中定义对象上的时需要使用 function 关键字来定义,而 ES6 则直接省略了 冒号和 function 关键字。可以看出使用 ES6 这种简洁的方式更具表达力。
在 Node 中进行模块导出时,这种方式更加方便。我们看下面的例子:
var person = {};
function getName () {
return person.name
}
function setName () {
person.name = '李四'
}
function clear () {
person = {};
}
// ES5 写法
module.exports = {
getName: getName
setName: setName,
clear: clear
};
// ES6写法
module.exports = { getName, setName, clear };
上面的中,我们定义了 person 对象,并向外暴露了若干用来操作 person 对象,在导出的时候可以看出,ES6 不需要重复地去写变量名,从而更简洁地表达了模块所提供的。
在 JavaScript 中定义对象的,一般有两种。如下:
// 一
obj.name = 'imooc';
// 二
obj['a' + 'ge'] = ;
上面的中,一直接使用标识符进行赋值操作,这是我们比较常用的赋值操作,但是如果是表达式时,则可以使用二,把表达式写在中括号中。
但是在 ES5 定义字面量对象时不能使用表达式作为字面量对象的,只能通过第一种方式(标识符)来定义。
var obj = {
name: 'imooc',
age:
}
ES6 对对象的进行了扩展,可以覆盖更多的场景,可以使用变量的形式来定义,如下:
var key = 'name';
var obj = {
[key]: 'imooc',
['a' + 'ge']:
}
上面的中字面量对象中的是可以放在中括号中,中括号中的可以是变量,也可以是表达式。这无疑是扩展了的,使编程更加灵活。
另外,也可以是带空格的字符串,在取值时在中括号中可以直接使用字符串,也可以使用变量。如下:
var str = 'first name';
var obj = {
['I love imooc']: 'ES6 Wiki',
[str]: 'Jack'
}
console.log(obj['I love imooc']) // ES6 Wiki
console.log(obj[str]) // Jack
console.log(obj['first name']) // Jack
表达式还可以用于定义对象上的名。
var person = {
name: 'Jack',
['get' + 'Name']() {
console.log(this.name)
}
};
console.log(person.getName()) // Jack
注意 1: 名表达式与简洁表示,不能同时使用,会报错。
// 报错
var name = 'Jack';
var age = ;
var person = { [name] };
// Uncaught Error: Unexpected token '}'
上面的会有语法,正确的方式应该是:
var name = 'Jack';
var person = { [name]: }; // {Jack: 18}
注意 2: 名必须是字符串类型的,如果表达式是对象,则会先调 toString()
先将对象转为字符串,然后才进行使用。
var key1 = {name: 'imooc'};
var key2 = {age: };
var obj = {
[key1]: 'value content 1',
[key2]: 'value content 2',
}
console.log(obj) // {[object Object]: "value content 2"}
上面中定义了两个变量都是对象类型的,在 toString()
时会变为 [object Object]
相同。所以,后面的把前面的覆盖了。
注意 3: 如果的表达式是数组时,则和对象不一样。数组在 toString()
后会变成字符串,所以对象的表达式就是字符串。
var keys = ['imooc', '7'];
var obj = {
[keys]: 'value content',
}
console.log(key.toString()) // "imooc,7"
console.log(obj) // {imooc,7: "value content"}
console.log(obj[keys]) // "value content"
上面的中可以看出来,数组 keys 在 toString()
得到了 imooc,7
作为 obj 的。另外,我们也可以直接使用 keys obj 对象上的值。
你有没有想过怎么对象上的名字?ES6 了的 name
,直接 name
会返回名。字面量对象上的也是,因此也有 name
。如下实例:
var person = {
name: "Jack",
getName() {
console.log(this.name);
},
};
person.getName.name // "getName"
上面中,getName()
的 name
返回名(即名)
有两种特殊情况:
(new Function()).name // "anonymous"
var doSomething = function() {
// todo
};
doSomething.bind().name // "bound doSomething"
如果对象的是 Symbol 值,那么 name
返回的是带中括号的 Symbol 的描述。
const key1 = Symbol('description content');
const key2 = Symbol();
let obj = {
[key1]() {},
[key2]() {},
};
obj[key1].name // "[description content]"
obj[key2].name // ""
本节介绍了 ES6 的对象扩展,学习了对象中和的简写、的表达式以及注意的。最后学习了的 name
,可以返回名。