JavaScript 闭包后的面试题
1、闭包的面试题
使用原生js,addEventListener 给每个li元素绑定一个click事件输出li的顺序
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>闭包</title> <style> ul{ list-style:none; } li:nth-of-type(2n){ background-color:darkgoldenrod; } li:nth-of-type(2n + 1){ background-color:#00FFFF; } </style> </head> <body> <ul> <li>a</li> <li>b</li> <li>c</li> <li>d</li> </ul> </body> </html>
这题表面是考 addEvenListener 绑定事件实际是考闭包,绑定事件 addEventListener 和 onclick 差不多,onclick写着更简便一些
1. onclick相当于给对象加一个属性
2. 只不过 onclick 把函数 function(){ console.log(this.innerHTML); } 绑定到了li元素身上, 总的来说把里面的函数保存到了外部
3. 利用立即执行函数,用闭包解决闭包
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title>闭包</title> <style> ul{ list-style:none; } li:nth-of-type(2n){ background-color:darkgoldenrod; } li:nth-of-type(2n + 1){ background-color:#00FFFF; } </style> </head> <body> <ul> <li>a</li> <li>b</li> <li>c</li> <li>d</li> </ul> <script> function test(){ var liCollection = document.getElementsByTagName("li"); for(var i = 0; liCollection.length > i; i++){ (function(num){ liCollection[num].onclick = function(){ console.log(this.innerHTML); alert(liCollection[num].innerHTML); } }(i)); } } test(); </script> </body> </html>
2、计算一个字符串的字节长度
写一个方法,求一个字符串的字节长度。
提示:
一个中文占两个字节,一个英文占一个字节
字符串有一个方法 charCodeAt() ,可以返回指定字符串的Unicode编码,返回值是 0-65535 之接的整数。当返回值<=255时为英文,当返回值>255时为中文
语法:
stringObject.charCodeAt( index )
var str = "Hello world"; console.log(str.charCodeAt(1)); // 输出字符H的Unicode编码是 101
定义计算字符串长度的 retBytesLength(target) 方法:
1. 一个英文字符一个字节,一个中文字符二个字节
2. 先判断字符串每一位的ASCII码,小于等于255是英文,大与255的是中文,最后就能求出相应的结果
function retBytesLength(target){ var count = 0, len = target.length; for(var i = 0; len > i; i++){ if(target.charCodeAt(i) <= 255){ count ++; }else if(target.charCodeAt(i) > 255){ count +=2; } } return count; } var str = "Hello world 你好"; console.log(retBytesLength(str)); // 16
优化一下:
找到一个规律,大余255的只不过多了一个字节而已,就是说汉字比英文字符多了一个字节,
基础字符串长度不变,看看有没有汉字,循环遇到汉字的时候就加一个,程序简单多了效率更高。
程序再简化一下,才是最终整洁高效的代码
function retBytesLength(target){ var count, len; count = len = target.length; // 这里计算一次字符串长度,赋值len在下面循环里调用,不用每次循环都获取一次字符长度 for(var i = 0; len > i; i++){ if(target.charCodeAt(i) > 255){ count ++; } } return count; } var str = "Hello world 你好"; console.log(retBytesLength(str));
3、微店2017笔试题
先学 "逗号操作符"
(2, 3) 这块必须加括号,不加括号优先级顺序识别会发生混乱,
逗号是一个计算符,由于有括号的加持会先计算逗号运算符,然后把结果赋给变量a
var a = (2, 3); // 3
逗号操作符的意思是:
1. 先看逗号前面的表达式,如果前面表达是需要计算就先计算
2. 再计算逗号后面的表达式,如果后面表达式需要计算就计算后面的表达式
3. 都计算完了之后,会把逗号后面的计算结果返回去
var a = (1 - 1, 1 + 1); // 2 var a = (9 - 1, 1 + 1); // 2
接下来看这道题,写出程序的执行结果
var f = ( function f(){ return "1"; }, function g(){ return 2; } )(); console.log(typeof f); // Number
1. 外面的括号优先级高,里面有逗号运输符,把最后一个函数g返回
2. 剩下的形成一个立即执行函数,执行结果返回数字类型 2,最后变成 var f = 2;
var f = (
function g(){
return 2;
}
)();
3. typeo f 返回数字类型Number
最厉害的问题天使:
函数f 不会和变量var f 预编译的时候会不会覆盖?有一个优先级,先看括号里面的逗号运算符,返回逗号后面的函数g。
4、写出程序的执行结果
var x = 1; if(function f() {}){ x += typeof f; } console.log(x); // 1undefined
分析:
1. if括号里是 functionf(){} ,怎么分析这个问题?if( 条件) if括号里的条件 functionf(){} 不是为false那六个值,那肯定能进入判断
2. 但是这个函数 functionf(){} 当完条件之后,函数他自己产生了什么变化?
括号一定会把里面变成表达式,变成表达式他就不是函数定义了,函数名f 从此后消失了。
3. f名消失了,未经过声明的变量应该报错,但是只有放到typeof里是唯一不报错的操作符,
所以 typeof f 返回字符串类型的 "undefined"
4. 变量x等于1,数字1加上undefined等于NaN,
但 typeof 返回的是字符串类型的"undefined",字符串加什么都是字符串,所以最后的结果是 "1undefined"
5、记录一些面试题
1. html顶部DOCTYPE有什么作用?有什么影响
2. Display的参数值极其含义
3. 描述一下盒子模型
4. css3伪类都有哪些
5. position属性有哪些值,有什么区别
6. 如何创建一个div,并添加到页面里
7. 写一个正则表达式,检验字符串首尾是否含有数字