js 常犯错误
总结自己常犯错误的点,后续常常改正,让自己的基础知识更扎实
一、 数据类型
'' || null || 3 || 4 // 3
4 && 5 && null && '0'// null 过程为:5 && null && '0' -> null && '0' -> null
[1] + [2] // "12"
1 + {} // "1[object Object]"
'1' + [] // "1"
2 + null // 2
1
2
3
4
5
6
7
8
2
3
4
5
6
7
8
- 请指出下面题目是否会输出内容
if([]){console.log(1)}//1
if([] == false){console.log(1)}//1
if({} == false){console.log(1)}//无
if([1] == [1]){console.log(1)}//无
1
2
3
4
2
3
4
【分析】
- if(x) 判断x是否为空,如果为空,则为false,否则为true
- if([] == false) 首先将x与k都转成相同的类型,[] -> 0 false -> 0 因此为true
- [1] == [1] 不相等,因为指针不同
const a = {
i: 1,
toString: function () {
return a.i++;
}
}
if (a == 1 && a == 2 && a == 3) {
console.log('hello world!');
}
// 会输出hello world!
1
2
3
4
5
6
7
8
9
10
11
2
3
4
5
6
7
8
9
10
11
分析:详解关于隐式转换
- 函数与变量声明提升
(function(){
//变量提升,function 比 var 优先级更高
function a(){var a = 1;}
console.log(a);
a();
var a = function(){var a = 2;};//已声明过的变量再次声明会被忽略,不会再提升了
console.log(a);
a();
})();
1
2
3
4
5
6
7
8
9
2
3
4
5
6
7
8
9
- 箭头函数this
this.a = 20;
var test = {
a: 40,
init: () => {
console.log(this.a);
function go(){
this.a = 60;
console.log(this.a);
}
go.prototype.a = 50;
return go;
}
};
var p = test.init();//20
p();//60
new (test.init());//60 60
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
二、 递归
- 如果数组列表太大,以下递归代码将导致堆栈溢出。你如何解决这个问题,仍然保留递归模式
var nextListItem = function() {
var item = list.pop();
if (item) {
nextListItem();
}
};
1
2
3
4
5
6
2
3
4
5
6
解决:
var nextListItem = function(){
var item = list.pop();
if (item) {
setTimeout( nextListItem, 0);
}
}
1
2
3
4
5
6
2
3
4
5
6
分析:
首先浏览器处理js为单线程,程序执行在主队列中,主队列同时还要处理UI及其他操作;本题为递归调用,它占用了内存中的堆栈,这样,直到item为undefined时,才会释放内存,因此会造成内存溢出,
而使用setTimeout,是将递归调用通过事件循环来处理,而不是调用堆栈
三、 作用域
function foo(a){
a = {v:5};
};
var a = {k:30};
foo(a);
alert(a.v); // undefined
foo(a){
a.v = 5
}
var a = {k:30}
foo(a)
alert(a.v) // 5
1
2
3
4
5
6
7
8
9
10
11
12
13
2
3
4
5
6
7
8
9
10
11
12
13
分析:
第一个题目,为按值传递 第二个题目,为按引用传递, 注意点,foo(a) 这里面的a为一个作用域
【思考题】请简述参数传递一共几种方式,分别是什么,并简述它们的区别?
分为2种,按值传递,按引用传递
按值: 可以理解为克隆的副本,在函数内部对其操作,与外部无关
按引用: 因为公用的是同一个引用地址(指针),因此函数内部对其操作,会影响外部