英文原文:Stack Overflow 编译:西城一隅
这是stackoverflow上的一个老问题,却有个干货答案,但是扩展的信息量很大,我只在此抛个砖。
Not jQuery. Not YUI. Not 等等…
js的框架的确很有用,但是它们却常常把一些js的丑陋细节和DOM原理给你隐藏了。如果你的目标是做一个精通javascript的工程师,那花大把的时间放在框架上可能恰恰背道而驰了。
下面就有javascript这门语言的一些特性,你应该知道并且深谙此道,但是很多人可能还并不清楚。
一、对象属性,object.prop和object[‘prop’]是一回事(所以你能停止使用eval了吗?!3KU);对象的属性多是String类型(有些也是数组Array)
for…in是什么情况下使用,什么情况慎用?
方括号可以通过变量来访问属性
1 2 3 4 |
person.name; person['name']; var propertyName = 'name'; person[propertyName]; // name |
当属性是带空格的string时就只能用方括号了:person[‘first name’];
for…in 循环输出的属性名顺序不可预测,使用之前先检测对象是否为null 或者 undefined
二、属性检测;undefined和null;为什么鲜为人知的in运算符非常有用,以及它和typeof、undefined的区别;hasOwnProperty;delete作用
undefined好理解一般用来表示未定义,而且不能用delete来删除它。
null 表示一个空对象指针 所以 typeof null返回 object
undefined派生自null alert(null == undefined) 返回true; 但alert(null === undefined)就返回false了
关于hasOwnProperty和Object:
hasOwnProperty是js中唯一一个处理属性但是不查找原型链的函数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
Object.prototype.prop = 'propsss'; var obj = {und:undefined}; obj.prop; // propsss 'und' in obj; // true obj.hasOwnProperty('prop'); // false obj.hasOwnProperty('und'); // true //只有hasOwnProperty可以给出正确和期望的结果,尤其在遍历一个对象时 //除了hasOwnProperty外,没有其他方法可以排除原型链上的属性(不是定义在对象自身上的属性) //如果hasOwnProperty被占用呢?来看: var obj = { hasOwnProperty: function(){ return false; }, prop: 'this is bad...' }; obj.hasOwnProperty('prop'); // 总是返回false //这样解决: {}.hasOwnProperty.call(obj,'prop'); // 返回true |
var o =new Object();
Object的每个实例都具有下列属性方法:
1.Constructor:保存着用于创建当前对象的函数 上面例子 构造函数就是 Object()
2.hasOwnProperty(prop):检查给定的属性是否在当前对象实例中(而不是在实例的原型中)。作为参数的属性必须以string形式指定
3.isPrototypeOf(object):用于检查传入的对象是否是另一个对象的原型。
4.propertyIsEnumerable(propertyName):用于检查给定的属性是否能够使用for in语句
5.toLocaleString():返回对象的字符串表示,与环境的地区对应
6.toString():同上
7.valueOf(): 返回对象的字符串、number、Boolean表示。通常与toString()相同
三、Number类型就是浮点类型(64位浮点数);使用浮点数会遇到语言无关性的问题;避免使用parseInt时的八进制陷阱
ECMAScript5不具有解析八进制的能力,可在IE7和chrome上测试 parseInt(069);
ES3和ES5之间存在分歧
javascript中的乘法问题:
一般可以用 10000 作为基数
31.12 * 10000 * 9.7 / 10000
四、嵌套函数作用域;避免全局变量导致的意外而使用var的必要性;闭包的作用域如何结合使用;在循环与闭包的问题
作用域和var关键字的面试题
1 2 3 4 5 |
function(){ var a=b=10; } console.log(a); console.log(b); |
循环中使用闭包
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
function createFunctions(){ var result = new Array(); for(var i=0;i<10;i++){ result[i] = function(){ return i; } } return result; } //每个函数的作用域链中都保存着createFunctions()函数的活动对象,所以他们引用的都是同一个变量i。 //当createFunctions()返回后 变量i的值是10 //所以可以这样写 for(var i=0;i<10;i++){ result[i] = function(num){ return function(){ return num; }; }(i); } |
之前写过的闭包的理解关于闭包
五、全局变量和window对象的属性产生冲突怎么办(它们其实是一回事);全局变量和DOM元素在IE中的冲突;在全局作用域中使用var来避免这些问题
六、 function语句在解析时会被提升(不管function被放置在哪里,它都会被移动到定义时所在作用域的顶层) 函数声明和函数表达式;为什么命名函数表达式不应该使用
关于函数声明提升:
解析器会执行一个函数声明提升(function decalaration hoisting)的过程,读取并将函数声明添加到执行环境中。
对代码求值时js引擎在第一遍会声明函数并将它们放到源代码树的顶部。
1 د扩展的信息量很大,我只在此抛个砖。
Not jQuery. Not YUI. Not 等等… js的框架的确很有用,但是它们却常常把一些js的丑陋细节和DOM原理给你隐藏了。如果你的目标是做一个精通javascript的工程师,那花大把的时间放在框架上可能恰恰背道而驰了。 下面就有javascript这门语言的一些特性,你应该知道并且深谙此道,但是很多人可能还并不清楚。 一、对象属性,object.prop和object[‘prop’]是一回事(所以你能停止使用eval了吗?!3KU);对象的属性多是String类型(有些也是数组Array) for…in是什么情况下使用,什么情况慎用? 方括号可以通过变量来访问属性
当属性是带空格的string时就只能用方括号了:person[‘first name’]; for…in 循环输出的属性名顺序不可预测,使用之前先检测对象是否为null 或者 undefined 二、属性检测;undefined和null;为什么鲜为人知的in运算符非常有用,以及它和typeof、undefined的区别;hasOwnProperty;delete作用 undefined好理解一般用来表示未定义,而且不能用delete来删除它。 null 表示一个空对象指针 所以 typeof null返回 object undefined派生自null alert(null == undefined) 返回true; 但alert(null === undefined)就返回false了 关于hasOwnProperty和Object: hasOwnProperty是js中唯一一个处理属性但是不查找原型链的函数
var o =new Object(); Object的每个实例都具有下列属性方法: 1.Constructor:保存着用于创建当前对象的函数 上面例子 构造函数就是 Object() 2.hasOwnProperty(prop):检查给定的属性是否在当前对象实例中(而不是在实例的原型中)。作为参数的属性必须以string形式指定 3.isPrototypeOf(object):用于检查传入的对象是否是另一个对象的原型。 4.propertyIsEnumerable(propertyName):用于检查给定的属性是否能够使用for in语句 5.toLocaleString():返回对象的字符串表示,与环境的地区对应 6.toString():同上 7.valueOf(): 返回对象的字符串、number、Boolean表示。通常与toString()相同 三、Number类型就是浮点类型(64位浮点数);使用浮点数会遇到语言无关性的问题;避免使用parseInt时的八进制陷阱 ECMAScript5不具有解析八进制的能力,可在IE7和chrome上测试 parseInt(069); ES3和ES5之间存在分歧 javascript中的乘法问题: 一般可以用 10000 作为基数 31.12 * 10000 * 9.7 / 10000 四、嵌套函数作用域;避免全局变量导致的意外而使用var的必要性;闭包的作用域如何结合使用;在循环与闭包的问题 作用域和var关键字的面试题
循环中使用闭包
之前写过的闭包的理解关于闭包 五、全局变量和window对象的属性产生冲突怎么办(它们其实是一回事);全局变量和DOM元素在IE中的冲突;在全局作用域中使用var来避免这些问题 六、 function语句在解析时会被提升(不管function被放置在哪里,它都会被移动到定义时所在作用域的顶层) 函数声明和函数表达式;为什么命名函数表达式不应该使用 关于函数声明提升: 解析器会执行一个函数声明提升(function decalaration hoisting)的过程,读取并将函数声明添加到执行环境中。 对代码求值时js引擎在第一遍会声明函数并将它们放到源代码树的顶部。 |