invalid number是什么意思_JS 中令人脑壳疼的 == 与 === 区别到底是什么?

c7cd37768c08042dd74f9a8cf0b0ebfa.png

曾经对我来说,等于就是等于,所以第一次接触到 JS 中的三等号时我感到很困惑。大部分编程语言中都有双等号"==",但没有三等号"==="。

下面是一个比较官方的双等号与三等号的差别:

"如果需要判断运算数是否为同一类型并且值相等,则使用严格相等运算符[===]。

否则,使用标准相等运算符[==],它允许你比较两个运算数的值,即使它们类型不同。"

--MDN web docs

在认为理解它的关键就在于了解“类型强制转换”,它是“动态类型语言” Vanilla JavaScript 中的一个奇怪的概念。

之所以会有类型强制转换是因为 JS 想要防御编程错误,比如拿一个数字和一个字符串比较:

“当在 JavaScript 中使用双等号时我们测试的是不严格的相等。双等号还会带来类型强制转换。

强制转换的意思是只有当运算数被转换为相同类型时它们才能被比较。”

换句话说,由于有类型转换,不同类型的值可以通过 == 被比较,但一个字符串和一个数字则永远不会用 === 严格相等。

举个例子:

console.log(Number("7") - 7 == 0); // trueconsole.log(Number("7") - 7 === 0); // trueconsole.log(Number("7") - 7 === Number("0")); // trueconsole.log("7" - 7 == "0"); // trueconsole.log("7" - 7 === "0"); // false

JavaScript 中的真与假

在 JavaScript 中我们有六个代表假的值:false, 0, ""(空字符串),null, undefined 和 NaN(Not A Number),这六个假值互相是什么关系呢?

“将 false,0和""用(==)相比较,结果为真,它们都不严格相等;null 和 undefined 只和自己相等;NaN 不与任何假值相等,包括它自己。”

// All permutations of falsy comparisons in JavaScript by Dr. Derek Austin console.log(false == false); // trueconsole.log(false === false); // trueconsole.log(false == 0); // true -- false, 0, and "" are loosely equalconsole.log(false === 0); // falseconsole.log(false == ""); // true -- false, 0, and "" are loosely equalconsole.log(false === ""); // falseconsole.log(false == null); // falseconsole.log(false === null); // falseconsole.log(false == undefined); // falseconsole.log(false === undefined); // falseconsole.log(false == NaN); // falseconsole.log(false === NaN); // falseconsole.log(0 == 0); // trueconsole.log(0 === 0); // trueconsole.log(0 == ""); // true -- false, 0, and "" are loosely equalconsole.log(0 === ""); // falseconsole.log(0 == null); // falseconsole.log(0 === null); // falseconsole.log(0 == undefined); // falseconsole.log(0 === undefined); // falseconsole.log(0 == NaN); // falseconsole.log(0 === NaN); // falseconsole.log("" == ""); // trueconsole.log("" === ""); // trueconsole.log("" == null); // falseconsole.log("" === null); // falseconsole.log("" == undefined); // falseconsole.log("" === undefined); // falseconsole.log("" == NaN); // falseconsole.log("" === NaN); // falseconsole.log(null == null); // trueconsole.log(null === null); // trueconsole.log(null == undefined); // true -- null loosely equals undefinedconsole.log(null === undefined); // falseconsole.log(null == NaN); // falseconsole.log(null === NaN); // falseconsole.log(undefined == undefined); // trueconsole.log(undefined === undefined); // trueconsole.log(undefined == NaN); // falseconsole.log(undefined === NaN); // falseconsole.log(NaN == NaN); // false -- NaN nothing equals NaN, andconsole.log(NaN === NaN); // false -- NaN doesn't equal itself

虽然 JS 中的假值这么奇葩,但幸好除了这些假值以外所有值都为真:

“在 JavaScript 中,真值就是在布尔类型上下文中所有被认为是"true"的值。所有的值皆为真,除非它被定义为假,比如 false,0,"",null,undefined 和 NaN。”

ECMAScript 中的情况呢?

如果你感兴趣的话,下面是 JavaScript 所使用的具体算法

严格相等运算符

严格相等运算符(=== 与 !==)使用严格相等比较算法来比较两个运算数:

11.9.6 严格相等比较算法当比较 x===y 时,x 与 y 为值,表达式返回 true 或 false,表达式执行方式如下:1. 如果 Type(x) 和 Type(y) 不同, 返回 false.2. 如果 Type(x) 为 Undefined, 返回 true.3. 如果 Type(x) 为 Null, 返回 true.4. 如果 Type(x) 为数字,那么→ a. 如果 x 为 NaN, 返回 false.→ b. 如果 y 为 NaN, 返回 false.→ c. 如果 x 与 y 的数字值相等, 返回 true.→ d. 如果 x 为 +0 而 y 为 −0, 返回 true.→ e. 如果 x 为 −0 而 y 为 +0, 返回 true.→ f. 返回 false.5. 如果 Type(x) 为字符串,如果 x 与 y 中的字符顺序完全相同(长度相同,字符位置相同),则返回 true;否则返回 false.6. 如果 Type(x) 为布尔类型, 如果 x 与 y 皆为真或假,则返回 true;否则,返回 false.7. 如果 x 和 y 引用了同一个对象,返回 true;否则返回 false.NOTE — This algorithm d如果fers from the SameValue Algorithm (9.12) in its treatment of signed zeroes and NaNs.

标准相等运算符

标准相等运算符(== 和 !=)使用抽象相等比较算法来比较两个运算数:

11.9.3 抽象相等比较算法(Abstract Equality Comparison Algorithm)比较 x == y, x 和 y 为值, 表达式返回 true 或 false. 表达式执行如下:1. 如果 Type(x) 与 Type(y) 相同, 那么→ a. 如果 Type(x) 为 Undefined, 返回 true.→ b. 如果 Type(x) 为 Null, 返回 true.→ c. 如果 Type(x) 为数字, 则→ → i. 如果 x 为 NaN, 返回 false.→ → ii. 如果 y 为 NaN, 返回 false.→ → iii. 如果 x 与 y 数字值相等, 返回 true.→ → iv. 如果 x 为 +0 并且 y 为 −0, 返回 true.→ → v. 如果 x 为 −0 并且 y 为 +0, 返回 true.→ → vi. 返回 false.→ d. 如果 Type(x) 是字符串, 如果 x 与 y 中的字符顺序完全相同(长度相同,字符位置相同),则返回 true;否则返回 false.→ e. 如果 Type(x) 为布尔类型, 如果 x 与 y 皆为真或假,则返回true;否则返回 false.→ f. 如果 x 与 y 引用了同一个对象,返回 true;否则返回 false.2. 如果 x 为 null 并且 y 为 undefined, 返回 true.3. 如果 x 为 undefined 并且 y 为 null, 返回 true.4. 如果 Type(x) 为数字并且 Type(y) 为字符串, 返回 x == ToNumber(y) 的结果.5. 如果 Type(x) 为字符串并且 Type(y) 为数字, 返回 ToNumber(x) == y 的结果.6. 如果 Type(x) 为布尔类型, 返回 ToNumber(x) == y 的结果.7. 如果 Type(y) 为布尔类型, 返回 x == ToNumber(y) 的结果.8. 如果 Type(x) 为数字或字符串,并且 Type(y) 为 Object, 返回 x == ToPrimitive(y) 的结果.9. 如果 Type(x) 为 Object 并且 Type(y) 为数字或字符串, 返回 ToPrimitive(x) == y 的结果.10. 返回 false.NOTE 1 — Given the above definition of equality:• String comparison can be forced by: "" + a == "" + b.• Numeric comparison can be forced by: +a == +b.• Boolean comparison can be forced by: !a == !b.NOTE 2 — The equality operators maintain the following invariants:• A != B is equivalent to !(A == B).• A == B is equivalent to B == A, except in the order of evaluation of A and B.NOTE 3 The equality operator is not always transitive. For example, there might be two distinct String objects, each representing the same String value; each String object would be considered equal to the String value by the == operator, but the two String objects would not be equal to each other. For example:• new String("a") == "a" and "a" == new String("a")are both true.• new String("a") == new String("a") is false.NOTE 4 Comparison of Strings uses a simple equality test on sequences of code unit values. There is no attempt to use the more complex, semantically oriented definitions of character or string equality and collating order defined in the Unicode spec如果ication. Therefore Strings values that are canonically equal according to the Unicode standard could test as unequal. In effect this algorithm assumes that both Strings are already in normalized form.

结论

通常来说,我比较喜欢用 === 和 !==,除非碰到了必须使用 == 和 != 的情况,比如检查空值。

另外,在检查空值时,牢记 null 和 undefined 使用双等号比较时是相等的这点很有用。

weixin_39722917
关注 关注
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
写文章

热门文章

  • 怎么把电脑系统做成iso镜像_iso系统镜像文件的安装步骤【图文】-系统城 14780
  • visio软件接口流程图_用Visio画流程图 7084
  • python多元非线性回归模型_Python 非线性回归 - 树懒学堂 6835
  • 怎么用wps做区域分布图_wps演示制作漂亮的组织结构图 5470
  • 复制粘贴之后出现问号怎么办_CAD图形文字复制粘贴以后出现变化该怎么办? 5410

大家在看

  • 信息安全工程师(65)恶意代码防护技术应用
  • 基于ssm+vue花卉网站(开题报告+源码+论文)
  • 敏捷开发过程-需求管理 404
  • 代码练习:打印正六边形
  • 基于ssm+vue化妆品销售网站(开题报告+源码+论文)

最新文章

  • 网易服务器修改权限等级,网易七鱼客服管理_七鱼客服管理人员权限设置_企业服务汇...
  • 使用mvc模式读取服务器上的文件,ASP.NET MVC之读取服务器文件资源的两种方式
  • 华为服务器如何登录修改密码,更改服务器登录密码
2021年166篇
2020年200篇

目录

目录

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值

玻璃钢生产厂家玻璃钢雕塑七星瓢虫鹤壁玻璃钢雕塑厂门头玻璃钢雕塑哪里好玻璃钢动物雕塑规格泡沫玻璃钢彩绘雕塑定制南阳小区玻璃钢雕塑定做天水玻璃钢雕塑厂山西玻璃钢雕塑仿真牛稳定的玻璃钢雕塑卡通江苏室内商场美陈销售企业玻璃钢园林雕塑厂家加工熊出没玻璃钢雕塑图张家口小品系列玻璃钢雕塑制作北京玻璃钢雕塑定制兴化玻璃钢雕塑企业苏州玻璃钢卡通雕塑定制低价玻璃钢雕塑济南动物玻璃钢雕塑无锡镜面玻璃钢雕塑推荐厂家北京特色玻璃钢雕塑订做价格雕像玻璃钢雕塑商场美陈动态安徽环保玻璃钢雕塑图片云南玻璃钢花盆厂家直销花朵玻璃钢卡通雕塑定做江苏玻璃钢广场雕塑厂家梅州玻璃钢动物雕塑服务电话阿拉尔广场玻璃钢雕塑德州广场玻璃钢雕塑定制玻璃钢罗马柱雕塑厂家定制香港通过《维护国家安全条例》两大学生合买彩票中奖一人不认账让美丽中国“从细节出发”19岁小伙救下5人后溺亡 多方发声单亲妈妈陷入热恋 14岁儿子报警汪小菲曝离婚始末遭遇山火的松茸之乡雅江山火三名扑火人员牺牲系谣言何赛飞追着代拍打萧美琴窜访捷克 外交部回应卫健委通报少年有偿捐血浆16次猝死手机成瘾是影响睡眠质量重要因素高校汽车撞人致3死16伤 司机系学生315晚会后胖东来又人满为患了小米汽车超级工厂正式揭幕中国拥有亿元资产的家庭达13.3万户周杰伦一审败诉网易男孩8年未见母亲被告知被遗忘许家印被限制高消费饲养员用铁锨驱打大熊猫被辞退男子被猫抓伤后确诊“猫抓病”特朗普无法缴纳4.54亿美元罚金倪萍分享减重40斤方法联合利华开始重组张家界的山上“长”满了韩国人?张立群任西安交通大学校长杨倩无缘巴黎奥运“重生之我在北大当嫡校长”黑马情侣提车了专访95后高颜值猪保姆考生莫言也上北大硕士复试名单了网友洛杉矶偶遇贾玲专家建议不必谈骨泥色变沉迷短剧的人就像掉进了杀猪盘奥巴马现身唐宁街 黑色着装引猜测七年后宇文玥被薅头发捞上岸事业单位女子向同事水杯投不明物质凯特王妃现身!外出购物视频曝光河南驻马店通报西平中学跳楼事件王树国卸任西安交大校长 师生送别恒大被罚41.75亿到底怎么缴男子被流浪猫绊倒 投喂者赔24万房客欠租失踪 房东直发愁西双版纳热带植物园回应蜉蝣大爆发钱人豪晒法院裁定实锤抄袭外国人感慨凌晨的中国很安全胖东来员工每周单休无小长假白宫:哈马斯三号人物被杀测试车高速逃费 小米:已补缴老人退休金被冒领16年 金额超20万

玻璃钢生产厂家 XML地图 TXT地图 虚拟主机 SEO 网站制作 网站优化