您现在的位置是:首页 > web开发 > JS常用面试题

JS常用面试题

web开发作者:dayu日期:4天前点击:0


var ul = document.get ...

var str = " ";

for(var i =0;i<3000;i++){

str += ‘<li></li>‘;

}

ul.innerHTML = str;


2、减少dom操作

1)节点克隆 - cloneNode

var ul = doc...
var li = document.createElement(‘li‘);
ul.innerHTML = ‘li‘;
for(var i = 0;i<3000;i++){

var new = li.cloneNode(true);
ul.appendChild(new);

}


2)访问元素集合 - 尽量用局部变量

var lei = li.length;//优化

for(var i = 0;i<len;i++){

li[i]....
}


3)元素节点 - 尽量用只获取元素的节点方法

childNodes:能获取元素节点、文本节点
children:只能获取元素节点,推荐使用

firstChild:能获取元素节点、文本节点
firstElementChild:只能获取元素节点,推荐使用


4)选择器API

querySelector、querySelectorAll



3、dom与浏览器:


重排:改变页面的内容(改变元素的宽高和位置)
重绘:浏览器显示内容(重排后的显示就是重绘)

改变元素的背景颜色是重绘

1)添加顺序 - 尽量在appendChild前添加操作

2)合并dom操作 - 利用cssText

3)缓存布局信息 - 把操作用变量先保存起来

4)文档碎片 - createDocumentFragment();创建少的话提高不大

var ul = document.get...

var frag = document.createDocumentFragment();

for(var i = 0 ; i <3000; i++){

var li = document.createElement(‘li‘);

frag.appendChild(li);

}

ul.appendChild(frag);


4、dom与事件的关系:

可以用事件委托

5、dom与前端模板:

能更好地对逻辑和视图分离,MVC架构的基础




十一、变量预解析



alert(a);
//在很多的其他语言中,变量需要先申明再使用,但是在js中我们可以先使用再申明(虽然这里的结果不是10,是undefined)
var a = 10;
//在js中,js解析器会对我们的代码做一些初始化分析的工作,其他包含了这么一项内容,解析器会把程序中变量的申明在程序代码执行之前做一个初始化, 解析器会把变量的申明提前处理,上面的先调用,后申明其实也可以是下面这样

变量预解析:

var a; //申明会提前,赋值不会提前

alert(a);

a = 10;//赋值

作用域:

var a = 10;

function fn() { //函数申明
//var a;
alert(a); //函数内部的a
var a = 100; //申明被提前到了当前作用域的最开始
alert(a);
}

fn(); //undefined 100




十二、callee 和 caller


callee返回正在执行的函数本身的引用,它是arguments的一个属性

1 这个属性只有在函数执行时才有效
2 它有一个length属性,可以用来获得形参的个数,因此可以用来比较形参和实参个数是否一致,即比较arguments.length是否等于arguments. callee.length
3 它可以用来递归匿名函数。

function fn() {
//arguments.callee => 当前函数
alert(arguments.callee);// function fn(){}
}

eg:让setTimeout来模拟setInterval

函数递归方法:

var a = 1;

function interval() {
setTimeout(function() {
document.title = a++;
interval();
}, 100);
}

interval();

利用闭包自执行和callee来递归:

var a = 1;

(function() {
var _arguments = arguments;
setTimeout(function() {
document.title = a++;
_arguments.callee(); //_arguments代表之前定义的父级函数的
}, 100);
})();



caller:返回一个函数的引用,这个函数调用了当前的函数。即调用该函数的函数。

使用这个属性要注意:

1 这个属性只有当函数在执行时才有用
2 如果在javascript程序中,函数是由顶层调用的,则返回null
functionName.caller: functionName是当前正在执行的函数。

function fn1() {
console.log(1);
console.log(fn1.caller);//fn2
}

function fn2() {
console.log(2);
console.log(fn2.caller); //null
fn1();
}

fn2(); //2 -> null -> 1 -> fn2



十三、call 和 apply


call和apply都是能改变函数内部this的指向

function fn1(a, b) {
console.log(this);
console.log(a + b);
}

fn1.call(document, 1, 2);// 第一个参数是this的指向,可以为null,其后的都是该函数的参数

apply 和call基本一致,不同的是参数的传递上

fn1.apply(document, [1, 2]); //第二个参数就是fn1中的arguments

求最大值:

var arr = [1,6,4,8,3,10,2];

//console.log( Math.max(1,6,4,8,3,10,2) ); //arguments => [1,6,4,8,3,10,2]

console.log( Math.max.apply(null, arr) ); //arguments => arr


十四、this

this
* 函数外 : window
* 函数内 :
* 当一个函数被对象调用,则该函数内的this指向调用该函数的对象
* 当一个函数被事件调用,则该函数内的this指向触发该事件的对象
* 通过call、apply去调用一个函数,那么这个函数指向call、apply的第一个参数(如果call、apply的第一个参数是undefined/null,则this指向调用该函数的对象)

十五、优化

减少全局变量:作用域链
只加载可视区内容
减少dom操作:事件委托 、文档碎片
减少请求和质量:合并JS 、压缩JS
能使用正则尽量使用正则



十六、变量的作用域:

1、外层的变量,内层可以找到(全局);内层的变量,外层找不到(局部)。

var a = 10;
function aaa(){

alert(a);

}

function bbb(){

var a = 20;
aaa();

}

bbb(); // 10


2、当var 不加的时候,会自动生成全局的变量(不建议这样写。最好把所有要定义的变量加上var)。

function aaa(){

var a = b = 10; // 拆分为b = 10; var a = 10;

}
aaa();
alert(a); // undefined
alert(b); // 10;

3、变量的查找是在代码逐行解读下就近原则去寻找var定义的变量或者function的参数 ,当就近没找到就到父级去找。

var a = 0;

function aaa(){

alert(a); // undefined;代码逐行解读
var a = 20;

}
aaa();

```
var a = 10;

function aaa(){

a = 20;
alert(a); //20

}
aaa();

```

var a = 0;

function aaa(){

alert(a); //10
a = 20;

}
aaa();

```

var a = 10;
function aaa(){

bbb();
alert(a);//10
function bbb(){
var a = 20;
}


}


4、当参数和局部变量重名的时候,优先级是等同的。

var a = 10;

function aaa(a){

alert(a); //10
var a = 20;

}
aaa(a);


5、基本类型的赋值,只是值的改变;对象之间是引用的关系,在内存中地址是相同的。

var a = 20;

function aaa(a){

a+=3;

}
aaa(a);
alert(a);//10 函数中的a和外部的a不同


···

var a = [1,2,3];

function aaa(a){

a.push(4); // 修改了外部a

}
aaa(a);
alert(a); // 1,2,3,4

···

var a = [1,2,3];

function aaa(a){

a = [1,2,3,4]; //在内存中重新生成了一个a,与外部的a不同

}
aaa(a);
alert(a); // 1,2,3

JS常用面试题

原文地址:http://www.cnblogs.com/hello-web/p/7221472.html


下一篇       上一篇