parseInt遇上map:
["1", "2", "3"].map(parseInt)
console.log(["1", "2", "3"].map(parseInt)); // 1 NaN NaN
// 首先搞懂parseInt(被解析的值,进制的基数) 输入以下值 即可明白
console.log(parseInt("1", 0)); // 1
console.log(parseInt("2", 1)); // NaN
console.log(parseInt("3", 2)); // NaN
string要被解析的值。如果参数不是一个字符串,则将其转换为字符串。
radix_ 可选_从
2到36的整数,表示进制的基数。例如指定16表示被解析值是十六进制数。如果超出这个范围,将返回NaN。假如指定0或未指定,基数将会根据字符串的值进行推算。例如:
parseInt("3", 2) :将3解析成2进制的数,3超出2进制的范围,所以返回NaN。
var ary = Array(3);
ary[0] = 2;
console.log(
ary.map(function (elem) {
return "1";
})
); // ['1', 空属性 × 2]
map 方法会给原数组中的每个元素都按顺序调用一次 callback 函数。callback 每次执行后的返回值组合起来形成一个新数组。callback 函数只会在有值的索引上被调用;那些从来没被赋过值或者使用 delete 删除的索引则不会被调用。
null:
typeof null, null instanceof Object
// typeof 判断除了null之外的基本类型
// instanceof 是根据检测构造函数的prototype属性是否出现在某个实例对象的原型链上(可检测引用类型)
console.log(typeof null, null instanceof Object); // object false
reduce:
[[3, 2, 1].reduce(Math.pow)]
// 如果数组为空且未指定初始值 initialValue,则会抛出 TypeError。
console.log([[3, 2, 1].reduce(Math.pow)]); // 9
// console.log([, [].reduce(Math.pow)]); // 报错
// 所以
// console.log([[3, 2, 1].reduce(Math.pow), [].reduce(Math.pow)]); // 报错
运算符优先级:
"Value is " + (val === "smtg") ? "Something" : "Nothing"
// + 的运算符要高于 条件运算符
// 即: Value is " + (val === "smtg") 是一个整体 得到结果为 true 则 为Something
var val = "smtg";
console.log("Value is " + (val === "smtg") ? "Something" : "Nothing"); // Something
变量提升:
var name = "World!";
(function () {
// 这里的name会先找自身有没有 有则用 没有则向上找
if (typeof name === "undefined") {
var name = "Jack";
console.log("Goodbye " + name); // Goodbye Jack
} else {
console.log("Hello " + name);
}
})();
// 相当于
var name = "World!";
(function () {
var name; // 变量提升
if (typeof name === "undefined") {
name = "Jack";
console.log("Goodbye " + name);
} else {
console.log("Hello " + name);
}
})();
在 JavaScript中, functions 和 variables 会被提升。变量提升是JavaScript将声明移至作用域 scope (全局域或者当前函数作用域) 顶部的行为。
这意味着你可以在声明一个函数或变量之前引用它,或者可以说:一个变量或函数可以在它被引用之后声明。
死循环陷阱
var END = Math.pow(2, 53);
var START = END - 100;
var count = 0;
for (var i = START; i <= END; i++) {
count++;
}
console.log(count);
js的number类型有个最大值(安全值)。即2的53次方,为9007199254740992,没有比这更大的值了。所以 2^53 + 1 == 2^53,所以这个循环无法终止。
警惕IEEE 754标准
var two = 0.2;
var one = 0.1;
var eight = 0.8;
var six = 0.6;
[two - one == one, eight - six == two]
JavaScript中采用双精度浮点数格式,即IEEE 754标准。在该格式下,有些数字无法表示出来,比如:0.1 + 0.2 = 0.30000000000000004 ,这不是JavaScript的锅,所有采用该标准的语言都有这个问题,比如:Java、Python等。
字符串陷阱
function showCase(value) {
switch(value) {
case 'A':
console.log('Case A');
break;
case 'B':
console.log('Case B');
break;
case undefined:
console.log('undefined');
break;
default:
console.log('Do not know!');
}
}
showCase(new String('A')); // Do not know!
howCase(String("A")); // Case A
console.log(new String("A")); // {'A'}
console.log(String("A")); // A
在 switch 内部使用严格相等 === 进行判断,new String("A") 返回的是一个对象,而 String("A") 则是直接返回字符串 "A"。
并非都是奇偶
function isOdd(num) { return num % 2 == 1; } function isEven(num) { return num % 2 == 0; } function isSane(num) { return isEven(num) || isOdd(num); } var values = [7, 4, "13", -9, Infinity]; console.log(values.map(isSane)); // [true, true, true, false, false]
console.log("13" % 2); // 1
console.log(-9 % 2); // -1
console.log(Infinity % 2); // NaN
强制转换
var a = [0];
if ([0]) {
console.log(a == true); // false
} else {
console.log("wut");
}
当 [0] 需要被强制转成 Boolean 的时候会被认为是 true。所以进入第一个 if 语句,而 a == true 的转换规则在ES5规范的第11.9.3节中已经定义过,你可以自己详细探索下。规范指出,== 相等中,如果有一个操作数是布尔类型,会先把他转成数字,所以比较变成了 [0] == 1;同时规范指出如果其他类型和数字比较,会尝试把这个类型转成数字再进行宽松比较,而对象(数组也是对象)会先调用它的 toString() 方法,此时 [0] 会变成 "0",然后将字符串 "0" 转成数字 0,而 0 == 1 的结果显然是 false。
==
console.log([] == []); //false
对象(Object):仅当两个操作数引用同一个对象时返回
true。 有关==详情可参考:
相等(==) - JavaScript | MDN
var a = [1, 2, 3];
var b = [1, 2, 3];
var c = [1, 2, 4];
console.log(a == b);
console.log(a === b);
console.log(a > c);
console.log(a < c); // false, false, false, true
对象进行相等比较,只有在它们指向同一个对象的情况下才会返回 true,其他情况都返回 false。
对象进行大小比较,会调用 toString 方法转成字符串进行比较,所以结果就变成了字符串 "1,2,3" 和 "1,2,4" 按照字典序进行比较了
自动提升为全局变量
(function () {
var x = (y = 1);
})();
console.log(y); //1
console.log(x); // x is not defined
(私有)函数作用域中的变量提升:
带var的在私有作用域变量提升时声明为私有变量。
不带var的不是私有变量,去上一级作用域的变量中找,直到找到window为止。
// 函数作用域的变量提升
function fn() {
// 函数作用域 a变量提升 b没有变量提升
console.log(a, b); //undefined b is not defined
var a = (b = 13);
console.log(a, b); //13 13
}
fn();
console.log(a); // a is not defined
// 不带Var不是私有变量
console.log(b); //13
正则表达式
var a = /123/;
var b = /123/;
console.log(a == b); // false
console.log(a === b); // false
每个字面的正则表达式都是一个单独的实例,即使它们的内容相同。
禁止修改函数名
function foo() {}
var oldName = foo.name;
foo.name = "bar";
console.log([oldName, foo.name]); // ['foo', 'foo']
name属性是只读的,不能用赋值操作符修改
文章探讨了JavaScript中parseInt函数的使用,map方法的执行逻辑,以及reduce方法处理数组的规则。还提到了运算符优先级、变量提升的原理,以及JavaScript中的死循环问题,特别是Number类型的上限。此外,文章还讨论了IEEE754标准导致的浮点数精度问题,字符串陷阱,相等运算符的使用,正则表达式的特性,以及函数作用域中的变量提升行为。

被折叠的 条评论
为什么被折叠?



