ES6中对象的扩展

1. 属性的简洁表示法

可以直接写入变量和函数作为对象的属性和方法。在对象中只写属性名,不写属性值,代表属性值等于和属性名相同的的变量的值。

属性的简写


let foo = 'bar';
let baz = {foo}; // { foo: 'bar' }
// 等同于
let baz = { foo: foo}

方法的简写

let o = {method: function() {return 'hello';}
}let o = {method() {return 'hello';}
}

好处:

  • 函数返回会很方便
  • 书写很方法
  • CommonJS输出变量会很方便

如果某个方法的值是一个Generator函数,则前面需要加上星号。

const obj = {* m() {yield 'hello world';	}
}

2. 属性名表达式

在js之前对象定义属性名可以使用标识符或者表达式。但是如果使用字面量定义对象(大括号),只能使用标识符定义,不能使用表达式。

之前写法

// 标识符定义
obj.foo = true;
// 表达式定义
obj['a'+ 'b'] = 123;

在ES6中在定义对象时表达式可以定义属性名、方法名。

但是属性名表达式不能与简洁表示法一起使用,否则会报错。

// 定义在对象中
let propKey = 'foo';
let obj = {[propKey]: true,['a' + 'b']: 123,
}// 定义在方法
let a = {'first word': 'hello',['a'+'b'](){return 'hi';	}
}// 不能与简洁表示法一块使用
let foo = 'bar';
let baz = { [foo] }; // 会报错
// 可以这样写
let baz = { [foo]: foo }

注意:如果属性表达式是一个对象,默认情况下会自动转为字符串[object Object],这样就要特别注意!

const keyA = { a: 1};
const keyB = { b: 2};
const myObject = {[keyA]: 'valueA',[keyB]: 'valueB',
}
console.log(myObject);  // [object Object]: 'valueB'

这是因为这两个属性名都是对象,都转成同一个属性名[object Object],所以就把上面的属性自动覆盖掉了,不能有相同名称的属性名。

3. 方法的name属性

函数的name属性返回函数名,方法也是函数,也有name属性并返回函数名即方法名。

const person = {sayName() {console.log('hello');	}
}
person.sayName.name // 'sayName'

对于方法使用了get、set函数,则name属性不在该方法上。则在方法属性的描述对象的get和set属性上,返回值会在方法名前加上get和set。

如何操作获取含有get、set的方法名?

  1. 首先可以使用Object.getOwnPropertyDescriptor()方法,获取该属性的描述对象。
  2. 然后在使用`name`属性获取方法名。
const obj = {get foo() {},set foo(x) {}
}
obj.foo.name; // 会报错const descriptor = Object.getOwnPropertyDescriptor(obj, 'foo');
descriptor.get.name; // 'get foo'
descriptor.set.name; // 'get foo'

特殊情况!bind方法创造的函数,name属性返回值会在函数名的前面加上bound;Function构造函数创造的函数,name属性返回anonymous

(new Function()).name // 'anonymous'const doSomething = function(){}
doSomething.bind().name // 'bound doSomething'

如果对象的方法是一个Symbol值,那么属性返回的是这个Symbol值的描述。

4. Object.is()

用来比较两个值是否严格相等,与严格相等运算符(===)的行为一致。返回布尔类型

两个不同的是,+0不等于-0,NaN等于自身

Object.is('foo', 'foo'); // trueObject.is(NaN, NaN); // true
Object.is(+0, -0); // false

为什么ES6要提供Object.is方法?

因为在ES5中比较两个值是否相等,只有相等运算符()和严格相等运算符(=)两种,但他们有个缺点,前者在比较时会自动转换数据类型,后者在比较时,NaN不等于自身,+0等于-0,造成js中缺少一种运算,就是在所有环境中,只要两个值是一样的,它们就应该相等。所有在ES6中提出了Same-value equality(同值相等)算法来解决这个问题。

如何在ES5中模拟Object.is

Object.defineProperty(Object, 'is', {value: function(x, y) {if(x === y) {// 针对+0 不等于-0的情况return x !== 0 || 1 / x === 1 /y; }// 针对NaN的情况return x !== x && y !== y;},configurable: true,enumerable: false,writable: true
})

5. Object.assign()

用于将源对象的所有可枚举属性复制到目标对象。

第一个参数:目标对象。后面的参数都是源对象,后面的参数可以为多个。

let target = { a: 1};
let source1 = { b: 2};
let source2 = { c: 3};
Object.assign(target, source1, source2);
target // { a: 1, b: 2, c: 3 }

注意点

  • 如果目标对象中与源对象有同名属性,则后面的属性会覆盖前面的属性。
  • 如果只有一个参数,也就是目标对象,Object.assgin会直接返回该参数。如果不是对象,会先转成对象,然后返回。由于undefined和null无法转成对象,所以会报错
typeof Object.assign(2); // 'object'
Object.assign(undefined); // 报错
  • 如果非对象出现在源对象的位置,会先转对象,无法转的会先跳过,这意味着undefined和null不会报错。
let obj = {a: 1};
Object.assign(obj, undefined) === obj; // true
  • 数值、字符串和布尔值在源对象中,不会报错,字符串会以数组形式复制到目标对象中,其他值直接跳过
const obj = Object.assign({}, 12, true, 'ab'); // {'0': 'a', '1': 'b'}

可以看出转成对象后,它们的原始值都会包装在对象的内部属性[[PrimitiveValue]]上面,这个属性是不会被Object.assign复制的。只有字符串的包装对象会产生可枚举的实义属性,才会被拷贝

  • Object.assign只会对源对象自身属性拷贝,不会复制继承过来的属性,也不会复制不可枚举的属性。
  • 属性名也Symbol值的属性也会被复制
Object.assign({a: 'b'}, {[Symbol('c')]: 'd'});
// { a: 'b', Symbol(c): 'd'}
  • 复制是浅拷贝不是深拷贝

用途

  • 为对象添加属性
  • 为对象添加方法
  • 克隆对象

把一个原始对象复制到一个空对象中

  • 合并多个对象
  • 为属性指定默认值

6. 属性的可枚举性

对象的每一个属性都具有一个描述对象,用来控制属性的行为,使用Object.getOwnPropertyDescriptor方法可以获取该属性的描述对象。

let obj = { foo: 123 };
Object.getOwnPropertyDescriptor(obj);
/**{value: 123,writable: true,enumerable: true,configurable: true}*/

enumerable属性称为可枚举性,若属性值为true,则可以枚举,为false则不能,遍历时会忽略。

会忽略enumerable为false属性的操作,在ES5中有3个,ES6又新增了一个。

  • for…in循环:只遍历对象自身和继承过来的可枚举属性
  • Object.keys():返回对象自身可枚举属性的键名
  • JSON.stringify():只串行化对象自身的可枚举属性
  • Object.assign():遍历对象自身可枚举的属性

7. 属性的遍历

共有5中方法

  • for … in

只遍历对象自身和继承过来的可枚举属性

  • Object.keys(obj)

返回一个数组,包括对象自身可枚举属性的键名

  • Object.getOwnPropertyNames(obj)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/148637.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

Nginx高级 第一部分:扩容

Nginx高级 第一部分:扩容 通过扩容提升整体吞吐量 1.单机垂直扩容:硬件资源增加 云服务资源增加 整机:IBM、浪潮、DELL、HP等 CPU/主板:更新到主流 网卡:10G/40G网卡 磁盘:SAS(SCSI) HDD(机械…

十天学完基础数据结构-第二天(数据结构简介)

什么是数据结构? 在计算机科学中,数据结构是一种组织和存储数据的方式。它定义了数据的布局,以及对这些数据执行的操作。你可以把数据结构看作是计算机内存中的特定组织方式,就像图书馆中书籍的排列一样。 数据结构可以是各种形…

python获取时间戳

使用 datetime 库获取时间。 获取当前时间: import datetime print(datetime.datetime.now()) . 后面的是微秒,也是一个时间单位,1秒1000000微秒。 转为时间戳: import datetimedate datetime.datetime.now() timestamp date…

【数据结构】堆的应用-----TopK问题

目录 一、前言 二、Top-k问题 💦解法一:暴力排序 💦解法二:建立N个数的堆 💦解法三:建立K个数的堆(最优解) 三、完整代码和视图 四、共勉 一、前言 在之前的文章中&#xff…

Springboot场景开发多面手

LinkedBear ,资深 Java 高级工程师,底层技术研究者与分享者,倾心研究 Spring 技术体系多年,对 Spring、Spring Boot 、SpringCloud 等框架有独到的见解,拥有丰富的框架体系实践经验和架构封装经验。善于总结、输出&…

CharacterEncodingFilter的用法

CharacterEncoding是SpringMVC提供的一个一个过滤器,用于设置请求和响应的字符编码,解决乱码问题,他本身是一个过滤器 那么在SpringBoot中,CharacterEncoding就有一个很好的秒用 setEncoding("UTF-8")设置编码 setForceEncoding(true) 设置请求和响应编码 还需要在配…

leetcode做题笔记160. 相交链表

给你两个单链表的头节点 headA 和 headB ,请你找出并返回两个单链表相交的起始节点。如果两个链表不存在相交节点,返回 null 。 图示两个链表在节点 c1 开始相交: 题目数据 保证 整个链式结构中不存在环。 注意,函数返回结果后&…

计算机视觉——飞桨深度学习实战-深度学习网络模型

深度学习网络模型的整体架构主要数据集、模型组网以及学习优化过程三部分,本章主要围绕着深度学习网络模型的算法架构、常见模型展开了详细介绍,从经典的深度学习网络模型以CNN、RNN为代表,到为了解决显存不足、实时性不够等问题的轻量化网络…

Day-05 CentOS7.5 安装docker

参考 : Install Docker Engine on CentOS | Docker DocsLearn how to install Docker Engine on CentOS. These instructions cover the different installation methods, how to uninstall, and next steps.https://docs.docker.com/engine/install/centos/ Doc…

计算机网络 第二章物理层

计算机网络第二章知识点速刷 其中重要的是信源和信宿,以及调制解调器在通信模型当中起到的作用。 单工、半双工和全双工。

【Java 进阶篇】JDBC 数据库连接池详解

数据库连接池是数据库连接的管理和复用工具,它可以有效地降低数据库连接和断开连接的开销,提高了数据库访问的性能和效率。在 Java 中,JDBC 数据库连接池是一个常见的实现方式,本文将详细介绍 JDBC 数据库连接池的使用和原理。 1…

计组——I/O方式

一、程序查询方式 CPU不断轮询检查I/O控制器中“状态寄存器”,检测到状态为“已完成”之后,再从数据寄存器取出输入数据。 过程: 1.CPU执行初始化程序,并预置传送参数;设置计数器、设置数据首地址。 2. 向I/O接口发…

腾讯云服务器选购指南:如何选择一台合适的云服务器配置?

腾讯云服务器配置如何选择?CPU内存、带宽和系统盘怎么选择合适?个人用户可以选择轻量应用服务器,企业用户可以选择云服务器CVM,2核2G3M带宽轻量服务器95元一年、2核4G5M服务器168元一年,企业用户可以选择标准型S5云服务…

1300*C. Rumor(并查集贪心)

解析&#xff1a; 并查集&#xff0c;求每个集合的最小费用。 每次合并集合的时候&#xff0c;根节点保存当前集合最小的费用。 #include<bits/stdc.h> using namespace std; #define int long long const int N1e55; int n,m,a[N],p[N],cnt[N]; int find(int x){retur…

分布式锁:四种方案解决商品超卖的方案

一 分布式锁 1.1 分布式锁的作用 在多线程高并发场景下&#xff0c;为了保证资源的线程安全问题&#xff0c;jdk为我们提供了synchronized关键字和ReentrantLock可重入锁&#xff0c;但是它们只能保证一个工程内的线程安全。在分布式集群、微服务、云原生横行的当下&#xff…

深度学习笔记_4、CNN卷积神经网络+全连接神经网络解决MNIST数据

1、首先&#xff0c;导入所需的库和模块&#xff0c;包括NumPy、PyTorch、MNIST数据集、数据处理工具、模型层、优化器、损失函数、混淆矩阵、绘图工具以及数据处理工具。 import numpy as np import torch from torchvision.datasets import mnist import torchvision.transf…

uniapp 实现下拉筛选框 二次开发定制

前言 最近又收到了一个需求&#xff0c;需要在uniapp 小程序上做一个下拉筛选框&#xff0c;然后找了一下插件市场&#xff0c;确实有找到&#xff0c;但不过他不支持搜索&#xff0c;于是乎&#xff0c;我就自动动手&#xff0c;进行了二开定制&#xff0c;站在巨人的肩膀上&…

归并排序及其非递归实现

个人主页&#xff1a;Lei宝啊 愿所有美好如期而遇 目录 归并排序递归实现 归并排序非递归实现 归并排序递归实现 图示&#xff1a; 代码&#xff1a; 先分再归并&#xff0c;像是后序一般。 //归并排序 void MergeSort(int* arr, int left, int right) {int* temp (int…

tcp滑动窗口原理

18.1 滑动窗口 我们再来看这个比喻&#xff1a; 网络仅仅是保证了整个网络的连通性&#xff0c;我们我们基于整个网络去传输&#xff0c;那么是不是我想发送多少数据就发送多少数据呢&#xff1f;如果是这样的话&#xff0c;是不是就会像我们的从一个池塘抽水去灌到另外一个…

速看:免费领取4台阿里云服务器_申请入口及领取流程

注册阿里云账号&#xff0c;免费领云服务器&#xff0c;最高领取4台云服务器&#xff0c;每月750小时&#xff0c;3个月免费试用时长&#xff0c;可快速搭建网站/小程序&#xff0c;部署开发环境&#xff0c;开发多种企业应用。阿里云服务器网分享阿里云服务器免费领取入口、免…