总结js面试题(未完成)

Posted Lumbago~

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了总结js面试题(未完成)相关的知识,希望对你有一定的参考价值。

1. this关键字(指向)

this是javascript语言的一个关键字,它是函数运行时,在函数体内部自动生成一个对象,只能在函数体内部使用。函数的不同使用场合,this有不同的值。总的来说this就是函数运行时所在的环境对象。
情况一:
纯粹的函数调用:这是函数的最通常的用法,属于全局调用,因此this就代表全局对象

var x = 1;

function test(){
    console.log(this.x);
}

test();   // 1  情况二:作为对象方法

情况二:
作为对象方法的调用:函数还可以作为某个对象的方法调用,这时this就指这个上级对象。

function test(){
    console.log(this.x);
}

var obj = {};
obj.x = 1;
obj.m = test;
obj.m();

情况三:
作为构造函数调用:所谓构造函数,就是通过这个函数,可以生成一个新对象。这时this就指这个新对象。

function test(){
    this.x = 1;
}

var obj = new test();
console.log(obj.x);   // 1
 
情况四:
apply的调用:
apply( )是函数的一个方法,作用是改变函数的调用对象。它的第一个参数就表示改变后的调用这个函数的对象。因此这时this指的就是这第一个参数。

apply( )的参数为空时,默认调用全局对象。这时运行结果为0,证明this指的是全局对象。

```javascript
var x = 0;
function test(){
    console.log(this.x);
}

var obj = {};
obj.x = 1;
obj.m = test;
obj.m.apply();    // 0   this指的是全局对象
obj.m.apply(obj);   // 1    this指的是obj

情况六:
箭头函数:
箭头函数没有自己的this,继承外层上下文绑定的this;
let obj = {
age: 20,
info: function() {
return () => {
console.log(this.age); //this继承的是外层上下文绑定的this
}
}
}
let person = {age: 28};
let info = obj.info();
info(); //20
let info2 = obj.info.call(person);
info2(); //28

二. 事件模型:事件委托、代理?如何让事件先冒泡后捕获?

事件委托:
又叫事件代理,利用事件冒泡,只指定一个事件处理程序,就可以管理某一类型的所有事件。

原理:
事件冒泡机制,从最深的节点开始,然后逐步向上传播事件。

作用:
①支持为同一个DOM元素注册多个同类型事件;
②可将事件分为事件捕获和事件冒泡。

代码:

addEventListener(event,function,useCapture布尔值)
默认为false冒泡,true为捕获
attachEvent() 
//IE8及IE更早版本

 detachEvent() 
//移除事件监听

//不使用事件捕获
window.onload = function(){
    	let oBox = document.getElementById("box");
    	oBox.onclick = function(){
    		alert(1);   //不触发
    }
    	oBox.onclick = function(){
    		alert(2);   //触发
    	}
}

//使用事件捕获


window.onload = function(){
    oBox.addEventListener("click",function(){
    	alert(1);   //触发
    })
	oBox.addEventListener("click",function(){
	alert(2);   //触发
	})
}

事件捕获:
(从上到下查找)
当一个事件触发后,从Window对象触发,不断经过下级节点,直到目标节点。在事件到达目标节点之前的过程就是捕获阶段。所有经过的节点,都会触发对应的事件。
当为事件捕获(useCapture:true)时,先执行body的事件,再执行div的事件
事件冒泡:
(从上往上查找)
当事件到达目标节点后,会沿着捕获阶段的路线原路返回。同样,所有经过的节点,都会触发对应的事件。
当为事件冒泡(useCapture:false)时,先执行div的事件,再执行body的事件
先冒泡后捕获:
根据w3c标准,应先捕获再冒泡。若要实现先冒泡后捕获,给一个元素绑定两个addEventListener,其中一个第三个参数设置为false(即冒泡),另一个第三个参数设置为true(即捕获),调整它们的代码顺序,将设置为false的监听事件放在设置为true的监听事件前面即可。

三. 对象和面向对象

对象
属性和方法的集合就是对象(万物皆对象)。

面向对象
首先就是找对象,如果该对象不具备所需要的方法或属性,那就给它添加。面向对象是一种编程思维的改变。通过原型的方式来实现面向对象编程。
封装,继承,多态这些都是编程思想
还有封装一些API()返回一个promise的时候用的也是面向对象

.面向过程编程
“面向过程”(Procedure Oriented)是一种以过程为中心的编程思想。这些都是以什么正在发生为目标进行编程,不同于面向对象的是谁在受影响。与面向对象明显的不同就是封装、继承、类。
特性:模块化 流程化
优点:性能比面向对象高, 因为类调用时需要实例化,开销比较大,比较消耗资源;
单片机、嵌入式开发、Linux/Unix等一般采用面向过程开发,性能是最重要的因素。
缺点:没有面向对象易维护、易复用、易扩展

创建对象的方式(4种):
new Object、字面量、构造函数、原型。

四. for···in和for···of的区别:(for···in取key,for··of取value)

for···in取key(下标),可以遍历数组,对象,字符串
for··of取value(值),for··of只能遍历数组
使用for…of遍历普通对象,需要配合Object.keys()一起使用。

var obj = {name:"Bob",age:25};
for(var i in obj){
	console.log(i)  // name age
}
for(var i of obj){
	console.log(i)   //报错
}

五.查找数组重复项

filter+indexOf

 var arr = [1, true, true, 15, false, undefined, null, "NaN ", 0, " a "]

    function arr_unique5(arr) {
        return arr.filter((val, index, item) => {
            console.log(val)
            console.log(index)
            console.log(item)
            console.log(item.indexOf(val))
            return item.indexOf(val) === index;
        });
    }

    console.log(arr_unique5(arr))

forEach + includes

var arr = [1, true, true, 15, false, undefined, null, "NaN ", 0, " a "]
 function arr_unique6(arr) {
        var res = [];
        var err = [];
        arr.forEach((val) => {
            if (!res.includes(val)) {
                res.push(val);
            } else {
                err.push(val)
            }
        });
        return err;
    }
    console.log(arr_unique6(arr))

六、数组扁平化
数组扁平化就是将一个多维数组转换为一个一维数组
实现基本方式

1、对数组的每一项进行遍历。

2、判断该项是否是数组。

3、如果该项不是数组则将其直接放进新数组。

4、是数组则回到1,继续迭代。

5、当数组遍历完成,返回这个新数组。

1.常规方式 递归处理

Array.prototype.flatten = function () {
  var resultArr = [];
  var len = this.length;
  for (var i = 0; i < len; i ++) {
    if (Array.isArray(this[i])) {
        resultArr = resultArr.concat(this[i].flatten());
    } else {
      resultArr.push(this[i]);
    }
  }
  return resultArr;
}
var arr=[1,2,3,[4,5,'hello',['world',9,666]]]
console.log(arr.flatten())//[1, 2, 3, 4, 5, "hello", "world", 9, 666]

2.es6中的flat函数也可以实现数组的扁平化

let arr1 = [1,2,['a','b',['中','文',[1,2,3,[11,21,31]]]],3];
 console.log( arr1.flat( Infinity ) ); 

七、垃圾回收机制

简单来讲:就是浏览器或定期的查看内存中存储的变量,如果长时间没有使用,机会清除掉也就是回收
闭包的使用是长期在内存中,不会被回收,永久保存。

八、iframe的优缺点有哪些

它是一个标签
优点:
①iframe能够原封不动的把嵌入的网页展现出来;
②如果有多个网页引用iframe,那么你只需要修改iframe的内容,就可以实现调用的每一个页面内容的更改,方便快捷。
③网页如果为了统一风格,头部和版本都是一样的,就可以写成一个页面,用iframe来嵌套,可以增加代码的可重用。
④如果遇到加载缓慢的第三方内容如图标和广告,这些问题可以由iframe来解决。

缺点:
①会产生很多页面不易管理;
②iframe框架结构有时会让人感到迷惑,如果框架个数多的话,可能会出现上下、左右滚动条,会分散访问者的注意力,用户体验度差。
③代码复杂,无法被一些搜索引擎索引到,这一点很关键,现在的搜索引擎爬虫还不能很好的处理iframe中的内容,所以使用iframe会不利于搜索引擎优化。
④很多的移动设备(PDA 手机)无法完全显示框架,设备兼容性差。
⑤iframe框架页面会增加服务器的http请求,对于大型网站是不可取的。

九、函数柯里化(卡瑞化、加载化)

就是比如你写一个项目有很多小功能,可以将这些功能分成一个一个的函数封装起来
可以叫他颗粒化,便于修改这些功能改变和的数据改变等情况 提高效率,便于查找。

把接受多个参数的函数变换成接受一个单一参数(最初函数的第一个参数)的函数,并且返回接受余下的参数而且返回结果的新函数的技术。

容易理解的概念:
Currying概念其实很简单,只传递给函数一部分参数来调用它,让它返回一个函数去处理剩下的参数(主要是利用闭包实现的)。

特点:
①接收单一参数,将更多的参数通过回调函数来搞定;
②返回一个新函数,用于处理所有的想要传入的参数;
③需要利用call/apply与arguments对象收集参数;
④返回的这个函数正是用来处理收集起来的参数。

作用:
能进行部分传值,而传统函数调用则需要预先确定所有实参。如果你在代码某一处只获取了部分实参,然后在另一处确定另一部分实参,这个时候柯里化和偏应用就能派上用场。

用途:
我认为函数柯里化是对闭包的一种应用形式,延迟计算、参数复用、动态生成函数(都是闭包的用途)。

function add(x,y){  //普通函数
    console.log(x+y);
}
function curryingAdd(x){  //柯里化函数(闭包)
    return function(y){
        console.log(x+y);
    }
}
add(1,2)  //3
curryingAdd(1)(2)   //3  

十、window的onload事件和domcontentloaded

window.onload:
当一个资源及其依赖资源已完成加载时,将触发onload事件。

document.onDOMContentLoaded:
当初始的html文档被完全加载和解析完成之后,DOMContentLoaded事件被触发,而无需等待样式表、图像和子框架的完成加载。

区别:
①onload事件是DOM事件,onDOMContentLoaded是HTML5事件。
②onload事件会被样式表、图像和子框架阻塞,而onDOMContentLoaded不会。
③当加载的脚本内容并不包含立即执行DOM操作时,使用onDOMContentLoaded事件是个更好的选择,会比onload事件执行时间更早。

以上是关于总结js面试题(未完成)的主要内容,如果未能解决你的问题,请参考以下文章

Java进阶之光!2021必看-Java高级面试题总结

经验总结:Java高级工程师面试题-字节跳动,成功跳槽阿里!

js 面试题总结

JS作用域面试题总结

js面试题总结

2021.6月最新前端面试题总结(JavaScriptHtml5小程序ReactES6Vue.js源码全栈)