译者按: 漫漫编程路,总有一些坑让你泪流满面。

  • 原文: Who said javascript was easy ?

  • 译者: Fundebug

为了保证可读性,本文采用意译而非直译。另外,本文版权归原作者所有,翻译仅用于学习

这里我们针对JavaScript初学者给出一些技巧和列出一些陷阱。如果你已经是一个砖家,也可以读一读。

1. 你是否尝试过对数组元素进行排序?

JavaScript默认使用字典序(alphanumeric)来排序。因此,[1,2,5,10].sort()的结果是[1, 10, 2, 5]

如果你想正确的排序,应该这样做:[1,2,5,10].sort((a, b) => a - b)

2. new Date() 十分好用

new Date()的使用方法有:

  • 不接收任何参数:返回当前时间;
  • 接收一个参数x: 返回1970年1月1日 + x毫秒的值。
  • new Date(1, 1, 1)返回1901年2月1号。
  • 然而....,new Date(2016, 1, 1)不会在1900年的基础上加2016,而只是表示2016年。

3. 替换函数没有真的替换?

  let s = "bob"const replaced = s.replace('b', 'l')replaced === "lob" s === "bob" 

如果你想把所有的b都替换掉,要使用正则:

  "bob".replace(/b/g, 'l') === 'lol'

4. 谨慎对待比较运算

  // 这些可以'abc' === 'abc' // true1 === 1         // true// 然而这些不行[1,2,3] === [1,2,3] // false{a: 1} === {a: 1}   // false{} === {}           // false

因为[1,2,3]和[1,2,3]是两个不同的数组,只是它们的元素碰巧相同。因此,不能简单的通过===来判断。

5. 数组不是基础类型

  typeof {} === 'object' typeof 'a' === 'string' typeof 1 === number // 但是....typeof [] === 'object'  

如果要判断一个变量var是否是数组,你需要使用Array.isArray(var)

6. 闭包

这是一个经典的JavaScript面试题:

  const Greeters = []for (var i = 0 ; i < 10 ; i++) {Greeters.push(function () { return console.log(i) })}Greeters[0]() // 10Greeters[1]() // 10Greeters[2]() // 10

虽然期望输出0,1,2,...,然而实际上却不会。知道如何Debug嘛?
有两种方法:

  • 使用let而不是var。备注:可以参考Fundebug的另一篇博客[ ES6之"let"能替代"var"吗?](https://blog.fundebug.com/2017/05/04/ hy-you-should-not-use-var/)
  • 使用bind函数。备注:可以参考Fundebug的另一篇博客[ JavaScript初学者必看“this”](https://blog.fundebug.com/2017/05/17/ avascript-this-for-beginners/)
    Greeters.push(console.log.bind(null, i))

    当然,还有很多解法。这两种是我最喜欢的!

7. 关于bind

下面这段代码会输出什么结果?

  class Foo {constructor (name) {this.name = name}greet () {console.log('hello, this is ', this.name)}someThingAsync () {return Promise.resolve()}asyncGreet () {this.someThingAsync().then(this.greet)}}new Foo('dog').asyncGreet()

如果你说程序会崩溃,并且报错:Cannot read property 'name' of undefined。
因为第16行的geet没有在正确的环境下执行。当然,也有很多方法解决这个BUG!

  • 我喜欢使用bind函数来解决问题:

    asyncGreet () {this.someThingAsync().then(this.greet.bind(this))
    }

    这样会确保greet会被Foo的实例调用,而不是局部的函数的this

  • 如果你想要greet永远不会绑定到错误的作用域,你可以在构造函数里面使用bind来绑 。
    class Foo {constructor (name) {this.name = namethis.greet = this.greet.bind(this)}
    }
  • 你也可以使用箭头函数(=>)来防止作用域被修改。备注:可以参考Fundebug的另一篇博客[ JavaScript初学者必看“箭头函数”](https://blog.fundebug.com/2017/05/25/ rrow-function-for-beginner/)。
    asyncGreet () {this.someThingAsync().then(() => {this.greet()})
    }

8. Math.min()比Math.max()大

  Math.min() < Math.max() 

因为Math.min() 返回 Infinity, 而 Math.max()返回 -Infinity。

关于Fundebug

Fundebug专注于JavaScript、微信小程序、微信小游戏、支付宝小程序、React Native、Node.js和Java实时BUG监控。 自从2016年双十一正式上线,Fundebug累计处理了7亿+错误事件,得到了Google、360、金山软件、百姓网等众多知名用户的认可。欢迎免费试用!

版权声明

转载时请注明作者Fundebug以及本文地址:
https://blog.fundebug.com/2017/06/28/who-said-js-was-easy/

转载于:https://blog.51cto.com/13957060/2317508

JS中8个常见的陷阱相关推荐

  1. 【JS中循环嵌套常见的六大经典例题+六大图形题,你知道哪几个?】

    首先,了解一下循环嵌套的特点:外层循环转一次,内层循环转一圈. 在上一篇随笔中详细介绍了JS中的分支结构和循环结构,我们来简单的回顾一下For循环结构: 1.for循环有三个表达式,分别为: ①定义循 ...

  2. js中一种常见条件判断if(var)的坑

    在处理js代码判断真假时经常会这么写. //从某个地方获取的值. var vale = fun(......... );if(!value){进入这里表示value的布尔值为false } 我们知道, ...

  3. JS中4种常见的内存泄漏

    一.什么是内存泄漏 本质上讲,内存泄漏是当一块内存不再被应用程序使用的时候,由于某种原因,这块内存没有返还给操作系统或空闲内存池的现象. 二.几种常见的内存泄漏 1.意外的全局变量 一个未声明变量的引 ...

  4. js html utf8编码转换,js中的UTF-8编码与解码

    讲解之前我们先了解一些基本概念,什么是字符集?字符集就像一张表,这个表里面有很多的符号,每个符号都可以通过下标(这个符号在表的中的序号)对应到,有点类似js中的map,例如97这个下标代表的就是符号a ...

  5. Js中最常见的异常捕捉 TryCatch

    Js中最常见的异常捕捉 TryCatch 参考文章: (1)Js中最常见的异常捕捉 TryCatch (2)https://www.cnblogs.com/Zwq286179/p/5999450.ht ...

  6. react 组件连动效果_React组件开发中常见的陷阱

    React作为使用最广泛Web前端开发之一,在Web开发领域越来成熟和稳固.其新版本发布的Hook API/concept使得组件更加便捷易用.虽然如此,React开发中仍然有很多的陷阱值得每一位Re ...

  7. react 中组件隐藏显示_React组件开发中常见的陷阱及解决

    React作为使用最广泛Web前端开发之一,在Web开发领域越来成熟和稳固.其新版本发布的Hook API/concept使得组件更加便捷易用.虽然如此,React开发中仍然有很多的陷阱值得每一位Re ...

  8. JS中常见的String方法

    对于JS中的字符串(String)我们经常使用,今天总结了一下常见的String方法. 1. length 检测字符串的长度 let str = 'abcdef';console.log(str.le ...

  9. JS中常见的内存泄漏及识别方式

    JavaScript常见的内存泄漏及识别方式 1.什么是内存 2.什么是内存泄漏 3.内存泄漏导致的后果 4.常见的内存泄漏 (1)全局变量引起的内存泄漏 (2)闭包引起的内存泄漏 (3)被遗忘的定时 ...

最新文章

  1. 首届“AIIA杯”人工智能巡回赛起航,5大赛区邀你来战
  2. 【每日一算法】重排链表
  3. java自己实现读写锁_关于读写锁算法的Java实现及思考
  4. swing下拉框从mysql_Java Swing JComboBox下拉列表框的示例代码
  5. Makefile 学习 2 - 基于若干 Blog 的汇总
  6. 【HTML】------HTML的标签
  7. Android中活动Activity方面的知识点
  8. BAdI implementation in ABAP workbench dispatch event
  9. [系统审计]SAP HANA 中的系统审计策略管理
  10. 十大旗舰基金是怎样炼成的(主动权益)
  11. springboot 程序发布到tomcat运行
  12. 【Jsp】第一课 Jsp网络编程的介绍与入门学习
  13. 无线通信设备安装工程概预算编制_起重设备安装资质承接多大工程
  14. 风一更,雪一更,聒碎乡心梦不成,故园无此声。
  15. JavaScript 修改地址栏指定参数
  16. linux系统服务器日志,linux系统日志及日志服务器
  17. 人性化,中国制造新境界
  18. fairyGUI的学习记录1
  19. ubuntu下Android开发环境的搭建:eclipse+SDK详细安装教程+常见问题及其解决方案
  20. 2018年十大区块链投资机构盘点-千氪

热门文章

  1. 我先了解一下博客园创建随笔/文章/日记的过程与三者的区别(隐私等级,是否审核等)...
  2. 深入浅出PHP(Exploring PHP)
  3. 存储方式与介质对性能的影响
  4. Ajax实现DataGrid/DataList动态ToolTip
  5. 经典的导航二级式导航菜单增强版
  6. DllMain中不当操作导致死锁问题的分析——线程中调用GetModuleFileName、GetModuleHandle等导致死锁
  7. Ubuntu下CodeBlocks的安装、配置及静态库动态库的简单使用举例
  8. 【EMC】电磁兼容性相关名词解释、基础知识
  9. blob二进制显示在html,使用Blob获取图片并二进制显示实例页面
  10. 实现了html实现网页无限下滑,10行代码实现页面无限滚动