咖啡加点糖:javascript中该注意的几点

1、JavaScript允许对任意数据类型做比较

第一种是==比较,它会自动转换数据类型再比较,很多时候,会得到非常诡异的结果;

第二种是===比较,它不会自动转换数据类型,如果数据类型不一致,返回false,如果一致,再比较。

由于JavaScript这个设计缺陷,不要使用==比较,始终坚持使用===比较

浮点数在运算过程中会产生误差,因为计算机无法精确表示无限循环小数。要比较两个浮点数是否相等,只能计算它们之差的绝对值,看是否小于某个阈值:

Math.abs(1/3- (1-2/3)) <0.0000001;//true

2、JavaScript的设计者希望用null表示一个空的值,而undefined表示值未定义。事实证明,这并没有什么卵用,区分两者的意义不大。大多数情况下,我们都应该用null。undefined仅仅在判断函数参数是否传递的情况下有用。

3、数组Array

3.1、直接给Array的length赋一个新的值会导致Array大小的变化,即数组的length属性是可写

如果赋一个比length大的值,数组多出的部分用undefined代替

如果通过索引赋值时,索引超过了范围,同样会引起Array大小的变化:

var arr = [1,2,3];
arr[5] ='x';
arr;// arr变为[1, 2, 3, undefined, undefined, 'x']

如果赋一个比length小的值,那么多出的部分就会被截断。(引申:如果赋0,则是清空数组)
但是需要注意一点,通过点属性的方式及 "att.属性 " 来添加内容是不会引起length长度的变化,即js中的length只用来描述索引元素的长度,忽略关联元素

3.2、对于Array,如果不给slice()传递任何参数,它就会从头到尾截取所有元素。利用这一点,我们可以很容易地浅复制一个Array:

var arr = ['A','B','C','D','E','F','G'];
var aCopy = arr.slice();
aCopy;// ['A', 'B', 'C', 'D', 'E', 'F', 'G']
aCopy === arr;// false

3.3、对于数组的concat()方法,习惯上我们认为它接收一个数组参数,其实它可以接收任意个非数组元素和Array(如果是个一维数组,则会进行一次拆分,否则不拆分),然后全部添加到新的Array里:

var arr = ['A','B','C'];
arr.concat(1,2, [3,4]);// ['A', 'B', 'C', 1, 2, 3, 4]

注意:concat对添加的数组只进行一次拆分,如果接收的Array是个多维数组,不会进行拆分

3.4、Array的sort()方法默认把所有元素先转换为String再排序,如果不知道sort()方法的默认排序规则,直接对数字排序,绝对栽进坑里!

4、对象

对象的属性访问可以通过两个方式进行:一种是"对象.属性名",一种是 对象[ '属性名' ]

如果属性名是个合常规的,上边两种方式都可以,但是如果属性名中含有特殊的字符,如“-” 或者 空格 ,则只能通过第二种方式进行访问

测试一个对象是否拥有某一属性,可以用in操作符 或者 hasOwnProperty()方法,in会搜索原型链,检索对象自己的和继承过来的属性,而hasOwnProperty()方法只会检测是否是自己的属性

5、for( item  in target)

如果target是一个对象,则item代表的是对象的属性

如果target是一个数组,由于Array也是对象,而它的每个元素的索引被视为对象的属性的一部分,所以item代表的是索引,但是如果不通过Array提供的方法(方法和初始化)向数组中添加元素,你在数组上手动添加的属性不会被认为是索引的,即length是不会发生变化的,但是遍历的时候属性包括了索引和添加上来的内容,如下

var a = ['A','B','C'];
a.name ='Hello';
for(var x in a) {
    alert(x);// '0', '1', '2', 'name'
}
a // ['A','B','C']
a.length // 3

6、方法内部有关变量的提升

JavaScript的函数定义有个特点,它会先扫描整个函数体的语句,把所有申明的变量“提升”到函数顶部,只是提升声明,赋值操作是在代码执行到对应位置的时候才执行

functionfoo(){
    var x ='Hello, '+ y;
    alert(x);
    var y ='Bob';
}
等价于:
functionfoo(){
    var y;// 提升变量y的申明
    var x ='Hello, '+ y;   
    alert(x);
    y ='Bob';
}

所以在开发中,应严格遵守“在函数内部首先申明所有变量”这一规则

7、作用域

Javascript的变量范围是以函数为基础的,每个函数都有它自己的变量范围,Javascript这一点上表现的很酷,根本不理睬一些无意义的花括弧包起来的范围。

不在任何函数内定义的变量就具有全局作用域

var a = 1 等价于 window.a = 1

如果对象中定义了方法,要保证方法中this指向正确,必须用obj.xxx()的形式调用,否则this会被调用方法时调用该方法的对象改写

方法.apply(obj, [ ])、方法.call(obj, arg1, arg2, ...)可以动态改变方法中的this指向,对于普通方法的调用,我们可以使用 方法.apply(null, [ ])和 方法.call(null,arg1,arg2,...)的方式,比如调用Math.max(3, 5, 4),分别用apply()和call()实现如下:

Math.max.apply(null, [3,5,4]);// 5
Math.max.call(null,3,5,4);// 5

8、闭包

返回闭包时牢记的一点就是:返回函数不要引用任何循环变量,或者后续会发生变化的变量。

如果一定要引用循环变量怎么办?方法是再创建一个函数,用该函数的参数绑定循环变量当前的值(即函数有一个参数来接收变量)并用“创建一个匿名函数并立刻执行”的语法将i的值传入,无论该循环变量后续如何更改,已绑定到函数参数的值不变。

闭包的实质:闭包就是携带状态的函数!携带状态的函数!是携带状态的函数!并且它的状态可以完全对外隐藏起来。!

9、包装对象

包装对象用new创建:

var n =new Number(123);// 123,生成了新的包装类型
var b =new Boolean(true);// true,生成了新的包装类型
var s =new String('str');// 'str',生成了新的包装类型

虽然包装对象看上去和原来的值一模一样,显示出来也是一模一样,但他们的类型已经变为object了!所以,包装对象和原始值用===比较会返回false!

所以闲的蛋疼也不要使用包装对象!尤其是针对string类型!!!

如果我们在使用Number、Boolean和String时,没有写new,那么Number()、Boolean()和String()被当做普通函数,把任何类型的数据转换为number、boolean和string类型(注意不是其包装类型)

所以闲的蛋疼也不要使用包装对象!尤其是针对string类型!!!

10、字符串型数值快速转变为数值类型,只需在字符串前边加上“+”
var a = '123.4' ;
var b = +a + 100 // b=223.4

11、数值快速取整:数值|0

总结一下,有这么几条规则需要遵守:
不要使用new Number()、new Boolean()、new String()创建包装对象;
用parseInt()或parseFloat()来转换任意类型到number;
用String()来转换任意类型到string,或者直接调用某个对象的toString()方法;
通常不必把任意类型转换为boolean再判断,因为可以直接写if (myVar) {...};
typeof操作符可以判断出number、boolean、string、function和undefined;
判断Array要使用Array.isArray(arr);
判断null请使用myVar === null;
判断某个全局变量是否存在用typeof window.myVar === 'undefined';
函数内部判断某个变量是否存在用typeof myVar === 'undefined'。

12、
event.currentTarget指向事件所绑定的元素,
而event.target始终指向事件发生时的元素。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 211,290评论 6 491
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,107评论 2 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 156,872评论 0 347
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,415评论 1 283
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,453评论 6 385
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,784评论 1 290
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,927评论 3 406
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,691评论 0 266
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,137评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,472评论 2 326
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,622评论 1 340
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,289评论 4 329
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,887评论 3 312
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,741评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,977评论 1 265
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,316评论 2 360
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,490评论 2 348

推荐阅读更多精彩内容

  • 第5章 引用类型(返回首页) 本章内容 使用对象 创建并操作数组 理解基本的JavaScript类型 使用基本类型...
    大学一百阅读 3,216评论 0 4
  • FreeCodeCamp - Basic JavaScript 写在前面: 我曾经在进谷前刷过这一套题,不过当时只...
    付林恒阅读 16,431评论 5 28
  • 原文: https://github.com/ecomfe/spec/blob/master/javascript...
    zock阅读 3,371评论 2 36
  • 在那段我自以为空虚的日子里,我看遍了曾经追的紧的电视剧,看遍了所有的院线电影,听遍了所有在我青春时光里陪伴我的歌曲...
    湘湘离阅读 235评论 0 1
  • 登永青山组诗 胡荣生。 2014.年正月十六作于内乡县永青山下文溪河畔 一 过刁河 永青山下大刁河, 自北...
    AAA王者归来阅读 682评论 1 1