一使用 typeof bar === "object" 来确定 bar 是否是对象的潜在陷阱是什么? 如何避免这个陷阱?
首先 typeof bar === "object" 是检测 bar 是否是对象的可靠方法, 但在 javascript 中 null 也被认为是对象, 因此以下代码在控制台中将输出 true:
所以知道了 null 的问题, 同时检测 bar 是否是 null, 就可以避免这一问题啦:
当 bar 是一个数组的时候, 例如, 当 var bar = []的时候; 在很多情况下, 这是期望行为, 因为数字是真正的对象, 但如果你想数组也返回 false 时, 可以修改上述方案:
二下面的代码将输出什么到控制台? 为什么?
var a = b = 3; 这句代码等同于: b = 3; var a = b; 这时候变量 b 是不加 var 声明的变量, 也就是全局变量, 在函数内部没有 var 声明的变量是隐式全局变量所以控制台打印的结果为: true 和 false
如果再深入一步: 在严格模式(使用 use strict), 结果又会怎样?
在严格模式下运行的结果是: 报错: b is not undefined; 这正是严格模式的特点, 避免不必要的 bug(避免全局变量污染)
三关于 this 的指向问题, 以下代码将会输出什么?
在外部函数中, this 和 self 都是指向 myObject, 所以两者都可以正确的引用和访问 foo, 在内部函数中, this 不再指向 myObject, 结果是 this.foo 没有在内部函数中被定义在 ECMA5 之前, 在内部函数中的 this 将指向全局的 window 对象; 反之, 因为作为 ECMA5, 内部函数中的功能 this 是未定义的所以控制台将输出: bar ;bar ;undefined ;bar ;
四 use strict 有什么意义和好处?
use strict 是一种在 JavaScript 代码运行时自动实行更严格解析和错误处理的方法
严格模式的一些主要优点包括:
1. 使调试更加容易那些被忽略或默默失败了的代码错误, 会产生错误或抛出异常, 因此尽早提醒你代码中的问题, 你才能更快地指引到它们的源代码
2. 防止意外的全局变量如果没有严格模式, 将值分配给一个未声明的变量会自动创建该名称的全局变量这是 JavaScript 中最常见的错误之一在严格模式下, 这样做的话会抛出错误
3. 消除 this 强制如果没有严格模式, 引用 null 或未定义的值到 this 值会自动强制到全局变量这可能会导致许多令人头痛的问题和让人恨不得拔自己头发的 bug 在严格模式下, 引用 null 或未定义的 this 值会抛出错误
4. 不允许重复的属性名称或参数值当检测到对象中重复命名的属性, 例如:
var object = {foo: "bar", foo: "baz"};)
或检测到函数中重复命名的参数时, 例如:
function foo(val1, val2, val1){})
严格模式会抛出错误, 因此捕捉几乎可以肯定是代码中的 bug 可以避免浪费大量的跟踪时间
5. 使 eval()更安全在严格模式和非严格模式下, eval() 的行为方式有所不同最显而易见的是, 在严格模式下, 变量和声明在 eval() 语句内部的函数不会在包含范围内创建(它们会在非严格模式下的包含范围中被创建, 这也是一个常见的问题源)
6. 在 delete 使用无效时抛出错误 delete 操作符 (用于从对象中删除属性) 不能用在对象不可配置的属性上当试图删除一个不可配置的属性时, 非严格代码将默默地失败, 而严格模式将在这样的情况下抛出异常
五小心 javascript 自动插入分号机制? 看下面的代码, 它们会返回什么?
以上代码将会打印出:
原因是这样的, 当碰到 foo2()中包含 return 语句的代码行 (代码行上没有其他任何代码), 分号会立即自动插入到返回语句之后请仔细留意上面两个函数中 return 的不同之处, foo2 函数的 return 是单独一行的也不会抛出错误, 因为代码的其余部分是完全有效的, 即使它没有得到调用或做任何事情(相当于它就是是一个未使用的代码块, 定义了等同于字符串 "hello" 的属性 bar) 所以, 在使用 return 语句的时候, 要留意 javascript 的这个特点, 尽可能不要将 return 关键字写在独立的一行, 避免不必造成不必要的错误
在 JavaScript 语言精粹这本书里, 这个自动插入分号机制被划入到了 JavaScript 的毒瘤里面, 与之并列的前面的全局变量
六 NaN 是什么? 如何测试一个值是否等于 NaN?
NaN 属性代表一个不是数字的值这个特殊的值是因为运算不能执行而导致的, 不能执行的原因要么是因为其中的运算对象之一非数字例如:"abc" / 4, 要么是因为运算的结果非数字例如: 除数为零虽然 NaN 意味着不是数字, 但是它的类型, 不管你信不信, 是 Number:
此外, NaN 和任何东西比较, 甚至是它自己本身, 结果是 false:
一种半可靠的方法来测试一个数字是否等于 NaN, 是使用内置函数 isNaN(), 但即使使用 isNaN() 依然并非是一个完美的解决方案
一个更好的解决办法是使用 value !== value, 如果值等于 NaN, 只会产生 true 因为只有 NaN 这货, 才会自己不等于自己
另外, ES6 提供了一个新的 Number.isNaN() 函数, 这是一个不同的函数, 并且比老的全局 isNaN()函数更可靠
七以下代码的运行结果是什么?
- console.log(1 + "2" + "2");// "122";
- console.log(1 + +"2" + "2"); // "32";
根据运算的顺序, 要执行的第一个运算是 +"2"(第一个 "2" 前面的额外 + 被视为一元运算符), 因此, JavaScript 将 "2" 的类型转换为数字, 然后应用一元 + 号 (即将其视为一个正数) 其结果就是得到一个数字 2
- console.log(1 + -"1" + "2"); // "02";
- console.log(+"1" + "1" + "2"); // "112";
- console.log("a" - "b" + "2"); // "NaN2";
- console.log("a" - "b" + 2); // NaN;
八关于逻辑运算符, 下面代码的运行结果是什么?
在 JavaScript 中, || 和 && 都是逻辑运算符, 用于在从左至右计算时, 返回第一个可完全确定的逻辑值
来源: http://www.qdfuns.com/article/38951/9c8e53a15bc98957c79369b27da75cfd.html