时隔许久,精心整理的超级实用的Web前端面试题总结后续来啦

Posted 蓝枫諾

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了时隔许久,精心整理的超级实用的Web前端面试题总结后续来啦相关的知识,希望对你有一定的参考价值。

文章目录

Web前端面试题总结(二)javascript

1、JavaScript 是一门什么样的语言,它有哪些特点?

javaScript 一种直译式脚本语言,是一种动态类型、弱类型、基于原型的语言,内置支持类型。它的解释器被称为 JavaScript 引擎,为浏览器的一部分,广泛用于客户端的脚本语言,最早是在 html 网页上使用,用来给HTML 网页增加动态功能。JavaScript 兼容于ECMA 标准,因此也称为ECMAScript。
基 本 特 点
1.是一种解释性脚本语言(代码不进行预编译)。
2.主要用来向 HTML(标准通用标记语言下的一个应用)页面添加交互行为。
3.可以直接嵌入 HTML 页面,但写成单独的 js 文件有利于结构和行为的分离。
4.跨平台特性,在绝大多数浏览器的支持下,可以在多种平台下运行(如 Windows、Linux、Mac、androidios 等)。

2、javascript 的本地对象,内置对象和宿主对象?

本地对象为 array obj regexp 等可以 new 实例化内置对象为 gload Math 等不可以实例化的
宿主为浏览器自带的 document,window 等

3、js 的内置对象有哪些?列举一下 arry 和 string 的常用方法?

JavaScript 常见的内置对象有 Object,Math,String,Array,Number,Function,Boolean,JSON 等,其中 Object
是所有对象的基类,采用了原型继承方式.
String:charAt(); charCodeAt(); indexOf(); match(); replace(); search(); slice(); toUpperCase(); toLowerCase(); 等方法
Array:shift(); unshift(); pop(); push(); concat(); reverse(); splice(); slice(); 等方法

4、例举 3 种强制类型转换和 2 种隐式类型转换?

强制:parseInt()、parseFloat()、Number() 隐式:== 、console.log()、alert()

5、操作 DOM 的常用 API ?

1.节 点 查 找 document.getElementById…
2.节点创建. createElement cloneNode… 3.节点修改 appendChild insertBefore RemoveChild replaceChild…
4.元素属性型 setAttribute getAttribute…

6、BOM 之常用 API ?

navigator:window 中封装浏览器属性和配置信息的对象cookieEnabled:识别浏览器是否启用 cookie,返回值 true/false userAgent:保存了浏览器名称和版本的字符串
plugins:保存浏览器中所有插件信息的集合,每个 plugin 对象的 name 属性保存了插件的名称
screen:保存显示屏信息的对象 history:保存窗口的历史记录栈 location:指代当前窗口正在访问的 url 地址对象
location.href:保存了当前窗口正在访问的 url 地址,设置 href 属性为新 url,会在当前窗口打开新的地址页面
location.search():获取 url 上面 ?后面的参数
location.reload():刷新当前页面
location.assign(url):设置当前窗口的新 url
location.reload(true/false):true —— 无论是否更改,都获取更新;false —— 被修改的页面,重新获取,未被修改的页面,从缓冲获取定时器:让程序按指定时间间隔,自动执行任务,任务是所有定时器的核心

7、prop 和 attr 的区别?

对于 HTML 元素本身就带有的固有属性,在处理时,使用 prop 方法。
对于 HTML 元素我们自己自定义的 DOM 属性,在处理时,使用 attr 方法。
栗子 1:

<a href="http://www.baidu.com" target="_self" class="btn">百度</a>

这个例子里a元素的 DOM 属性有“href、target 和 class",这些属性就是a元素本身就带有的属性,也是 W3C 标准里就包含有这几个属性,或者说在 IDE 里能够智能提示出的属性,这些就叫做固有属性。处理这些属性时,建议使用 prop 方法。

<a href="#" id="link1" action="delete">删除</a>

这个例子里a元素的 DOM 属性有“href、id 和 action”,很明显,前两个是固有属性,而后面一个“action”属性是我们自己自定义上去的,a元素本身是没有这个属性的。这种就是自定义的 DOM 属性。处理这些属性时,建议使用 attr 方法。

8、 typeof 和 instanceof 区别 ?

在 javascript 中,判断一个变量的类型可以用 typeof
1、数字类型、typeof 返回的值是 number。比如说:typeof(1),返回值是 number 2、字符串类型,typeof 返回的值是 string。比如 typeof(“123”返回值时 string) 3、布尔类型,typeof 返回的值是 boolean。比如 typeof(true)返回值时 boolean 4、对象、数组、null 返回的值是 object。比如 typeof(window),typeof(document),typeof(null)
返回的值都是 object
5、函数类型,返回的值是 function。比如:typeof(eval),typeof(Date)返回的值都是 function。 6、不存在的变量、函数或者 undefined,将返回 undefined。比如:typeof(abc)、typeof(undefined)
都返回 undefined
在 javascript 中,instanceof 用于判断某个对象是否被另一个函数构造
使用 typeof 运算符时采用引用类型存储值会出现一个问题,无论引用的是什么类型的对象,它都 返回”object”。ECMAScript 引入了另一个 Java 运算符 instanceof 来解决这个问题。Instanceof 运算 符与 typeof 运算符相似,用于识别正在处理的对象的类型。与 typeof 方法不同的是,instanceof 方法要求开发者明确地确认对象为某特定类型

9、什么是闭包?

“闭包就是能够读取其他函数内部变量的函数。例如在 javascript 中,只有函数内部的子函数 才能读取局部变量,所以闭包可以理解成“定义在一个函数内部的函数“。在本质上,闭包是将函 数内部和函数外部连接起来的桥梁。”
举例:创建闭包最常见方式,就是在一个函数内部创建另一个函数。下面例子中的 closure 就 是一个闭包,

function func(){
var a =1 ,b = 2;
funciton closure(){ return a+b; } return closure; } 

10、说说你对原型(prototype)理解 ?

JavaScript 是一种通过原型实现继承的语言与别的高级语言是有区别的,像 java,C#是通 过类型决定继承关系的,JavaScript 是的动态的弱类型语言,总之可以认为 JavaScript 中所有 都是对象,在 JavaScript 中,原型也是一个对象,通过原型可以实现对象的属性继承,JavaScript 的对象中都包含了一个” prototype”内部属性,这个属性所对应的就是该对象的原型
“prototype”作为对象的内部属性,是不能被直接访问的。所以为了方便查看一个对象的原 型,Firefox 和 Chrome 内核的 JavaScript 引擎中提供了”proto“这个非标准的访问器(ECMA 新 标准中引入了标准对象原型访问器”Object.getPrototype(object)”)
原型的主要作用就是为了实现继承与扩展对象

11、介绍下原型链(解决的是继承问题吗)?

JavaScript 原型: 每个对象都会在其内部初始化一个属性,就是 prototype(原型) 原型链:
当我们访问一个对象的属性时,如果这个对象内部不存在这个属性,那么他就会去 prototype 里找这个属性,这个 prototype 又会有自己的 prototype,于是就这样一直找下去, 也就是我们平时所说的原型链的概念
特点:
JavaScript 对象是通过引用来传递的,我们创建的每个新对象实体中并没有一份属于自己 的原型副本。当我们修改原型时,与之相关的对象也会继承这一改变

12、简单说说 js 中的继承 ?

继承有以下六种方法
1、原型链继承 JavaScript 实现继承的基本思想:通过原型将一个引用类型继承另一个引用 类型的属性和方法
2、借用构造函数继承(伪造对象或经典继承) JavaScript 实现继承的基本思想:在子类构造 函数内部调用超类型构造函数。 通过使用 apply()和 call()方法可以在新创建的子类对象上执行构造函数
3、组合继承(原型+借用构造)(伪经典继承) JavaScript 实现继承的基本思想:将原型链和借 用构造函数的技术组合在一块,从而发挥两者之长的一种继承模式 将原型链和借用构造函数的技术组合到一起,从而取长补短发挥两者长处的一种继承模式 4、型式继承 JavaScript 实现继承的基本思想:借助原型可以基于已有的对象创建新对象, 同时还不必须因此创建自定义的类型
5、寄生式继承 JavaScript 实现继承的基本思想:创建一个仅用于封装继承过程的函数,该 函数在内部以某种方式来增强对象,最后再像真正是它做了所有工作一样返回对象。 寄生式继承是原型式继承的加强版
6、寄生组合式继承 JavaScript 实现继承的基本思想:通过借用函数来继承属性,通过原型 链的混成形式来继承方法

13、介绍 this 各种情况?

this 的情况:
1、以函数形式调用时,this 永远都是 window 2、以方法的形式调用时,this 是调用方法的对象 3、以构造函数的形式调用时,this 是新创建的那个对象 4、使用 call 和 apply 调用时,this 是指定的那个对象 5、箭头函数:箭头函数的 this 看外层是否有函数
如果有,外层函数的 this 就是内部箭头函数的 this
如果没有,就是 window
6、特殊情况:通常意义上 this 指针指向为最后调用它的对象。这里需要注意的一点就是
如果返回值是一个对象,那么 this 指向的就是那个返回的对象,如果返回值不是一个对象那么 this 还是指向函数的实例

14、数组中的 forEach 和 map 的区别?

forEach 和 map 的相同点
相同点 都是循环遍历数组中的每一项
forEach 和 map 方法里每次执行匿名函数都支持 3 个参数,参数分别是 item(当前每一项), index(索引值),arr(原数组)
匿名函数中的 this 都是指向 window 只能遍历数组 都不会改变原数组 区别:
map 方法
1.map 方法返回一个新的数组,数组中的元素为原始数组调用函数处理后的值
2.map 方法不会对空数组进行检测,map 方法不会改变原始数组。 3.浏览器支持:chrome、Safari1.5+、opera 都支持,IE9+, 若 arr 为空数组,则 map 方法返 回的也是一个空数组。
forEach 方法
1.forEach 方法用来调用数组的每个元素,将元素传给回调函数
2.forEach 对于空数组是不会调用回调函数的。 无论 arr 是不是空数组,forEach 返回的都是 undefined。这个方法只是将数组中的每一项作为 callback 的参数执行一次

15、for in 和 for of 的区别 ?

1、推荐在循环对象属性的时候使用 for…in,在遍历数组的时候的时候使用 for…of
2、for…in 循环出的是 key,for…of 循环出的是 value
3、注意,for…of 是 ES6 新引入的特性。修复了 ES5 引入的 for…in 的不足
4、for…of 不能循环普通的对象,需要通过和 Object.keys()搭配使用

16、Call 和 apply,bind 的区别 ?

call 方法调用一个函数, 其具有一个指定的 this 值和分别地提供的参数(参数的列表)。 注意:该方法的作用和 apply() 方法类似,只有一个区别,就是 call()方法接受的是若干个 参数的列表,而 apply()方法接受的是一个包含多个参数的数组
方法调用一个具有给定 this 值的函数,以及作为一个数组(或类似数组对象)提供的参数。 注意:call()方法的作用和 apply() 方法类似,区别就是 call()方法接受的是参数列表,而 apply() 方法接受的是一个参数数组
bind()方法创建一个新的函数,当这个新的函数被调用时,其 this 置为提供的值,其参数 列表前几项,置为创建时指定的参数序列

17、New 操作符具体干了什么呢?

1、创建一个空对象: 并且 this 变量引入该对象,同时还继承了函数的原型
2、设置原型链 空对象指向构造函数的原型对象
3、执行函数体 修改构造函数 this 指针指向空对象,并执行函数体
4、判断返回值 返回对象就用该对象,没有的话就创建一个对象

18、用 js 实现随机选取 10–100 之间的 10 个数字,存入一 个数组并排序?

function randomNub(aArray, len, min, max) {
if (len >= (max - min)) {
return '超过' + min + '-' + max + '之间的个数范围' + (max - min - 1) + '个 的总数';
}
if (aArray.length >= len) {
aArray.sort(function(a, b) {
return a - b
});
return aArray;
}
var nowNub = parseInt(Math.random() * (max - min - 1)) + (min + 1);
for (var j = 0; j < aArray.length; j++) {
if (nowNub == aArray[j]) {
randomNub(aArray, len, min, max);
return;
}
}
aArray.push(nowNub);
randomNub(aArray, len, min, max);
return aArray;
}
var arr=[];
randomNub(arr,10,10,100);

19、已知数组 var stringArray = [“This”,“is”, “Baidu”,“Campus”],Alert 出”This is Baidu Campus”

var stringArray = ["This", "is", "Baidu", "Campus"] alert(stringArray.join(""))

20、已知有字符串 foo=”get-element-by-id”,写一个 function 将其转化成驼峰 表示法”getElementById”

function combo(msg){
var arr=msg.split("-");
for(var i=1;i<arr.length;i++){ arr[i]=arr[i].charAt(0).toUpperCase()+arr[i].substr(1,arr[i].length-1); }
msg=arr.join("");
return msg;
}```

##  21、有这样一个 URL: http://item.taobao.com/item.htm?a=1&b=2&c=&d=xxx&e,请写 一段 JS 程序提取 URL 中的各个 GET 参数(参数名和参数个数不确定),将其按 key-value 形式返回到一个 json 结构中,如{a: "1", b: "2", c: "", d: "xxx", e: undefined}

```javascript
function serilizeUrl(url) {
var urlObject = {};
if (/\\?/.test(url)) {
var urlString = url.substring(url.indexOf("?") + 1); var urlArray = urlString.split("&");
for (var i = 0, len = urlArray.length; i < len; i++) { var urlItem = urlArray[i];
var item = urlItem.split("=");
urlObject[item[0]] = item[1];
}
return urlObject; }
return null;
}

22、写一个 function,清除字符串前后的空格。(兼容所有 浏览器)

//使用自带接口 trim(),考虑兼容性:
if (!String.prototype.trim) {
String.prototype.trim = function() {
return this.replace(/^\\s+/, "").replace(/\\s+$/,"");
}
}
// test the function
var str = " \\t\\n test string ".trim(); alert(str == "test string"); // alerts "true"

23、判断一个字符串中出现次数最多的字符,统计这个次数

 var str = 'asdfssaaasasasasaa';
var json = {};
for (var i = 0; i < str.length; i++) {
if(!json[str.charAt(i)]){ json[str.charAt(i)] = 1;
}else{ json[str.charAt(i)]++;
} };
var iMax = 0; var iIndex = ''; for(var i in json){
if(json[i]>iMax){ iMax = json[i]; iIndex = i;}}
alert('出现次数最多的是:'+ iIndex + '出现'+ iMax +'次')

24、Split()和 join()的区别?

Split()是把一串字符(根据某个分隔符)分成若干个元素存放在一个数组里 即切割成数组的形式;
join() 是把数组中的字符串连成一个长串,可以大体上认为是 Split()的逆操作

25、js 数组去重,能用几种方法实现?

1、使用 es6 set 方法 [...new Set(arr)] let arr = [1,2,3,4,3,2,3,4,6,7,6]; 
let unique = (arr)=> [...new Set(arr)]; 
unique(arr);//[1, 2, 3, 4, 6, 7]
2、利用新数组 indexOf 查找 indexOf() 方法可返回某个指定的元素在数组中首次出现的位置。 如果没有就返回-13for 双重循环 通过判断第二层循环,去重的数组中是否含有该元素,如果有就退出第二层循环,如果没有 j==result.length 就相等,然后把对应的元素添加到最后的数组里面。 
let arr = [1,2,3,4,3,2,3,4,6,7,6]; 
let result = []; for(var i = 0 ; i< arr.length; i++) {
for(var j = 0 ; j < result.length ; j++)
 { if( arr[i] === result[j]){
break;};};
if(j == result.length){
result.push(arr[i]); };};
console.log(result);
4、利用 for 嵌套 for,然后 splice 去重 functionunique(arr){ for(vari=0; i<arr.length;
i++){ for(varj=i+1; j<arr.length; j++){ if(arr[i]==arr[j]){ //第一个等同于第二个,splice 方法删除第二个 arr.splice(j,1); j--; } } } returnarr; }
5、利用 filter 
let arr = [1,2,3,4,3,2,3,4,6,7,6]; 
let unique = (arr) => {     
 return arr.filter((item,index) => { 
 return arr.indexOf(item) === index;
   }) }; unique(arr);
6let arr = [1,2,3,4,3,2,3,4,6,7,6]; 
let unique = (arr) => { return arr.filter((item,index) => {
return arr.indexOf(item) === index;
}) }; unique(arr);
7、利用 Map 数据结构去重 
let arr = [1,2,3,4,3,2,3,4,6,7,6]; 
let unique = (arr)=> { let seen = new Map();
return arr.filter((item) => {
return !seen.has(item) && seen.set(item,1);
});
}; unique(arr);

26、谈谈你对 Javascript 垃圾回收机制的理解?

1、标记清除(mark and sweep)
这是 JavaScript 最常见的垃圾回收方式,当变量进入执行环境的时候,比如函数中声明一个变量, 垃圾回收器将其标记为“进入环境”,当变量离开环境的时候(函数执行结束)将其标记为“离开 环境” 垃圾回收器会在运行的时候给存储在内存中的所有变量加上标记,然后去掉环境中的变量以及被 环境中变量所引用的变量(闭包),在这些完成之后仍存在标记的就是要删除的变量了
2、引用计数(reference counting)
在低版本 IE 中经常会出现内存泄露,很多时候就是因为其采用引用计数方式进行垃圾回收。引 用计数的策略是跟踪记录每个值被使用的次数,当声明了一个 变量并将一个引用类型赋值给该 变量的时候这个值的引用次数就加 1,如果该变量的值变成了另外一个,则这个值得引用次数减 1,当这个值的引用次数变为 0 的时 候,说明没有变量在使用,这个值没法被访问了,因此可以 将其占用的空间回收,这样垃圾回收器会在运行的时候清理掉引用次数为 0 的值占用的空间
在 IE 中虽然 JavaScript 对象通过标记清除的方式进行垃圾回收,但 BOM 与 DOM 对象却是通过引 用计数回收垃圾的,也就是说只要涉及 BOM 及 DOM 就会出现循环引用问题

27、js 如何处理防抖和节流?

在进行窗口的 resize、scroll,输入框内容校验等操作时,如果事件处理函数调用的频率无限 制,会加重浏览器的负担,导致用户体验非常糟糕
此时我们可以采用 debounce(防抖)和 throttle(节流)的方式来减少调用频率,同时又不 影响实际效果
函数防抖: 函数防抖(debounce):当持续触发事件时,一定时间段内没有再触发事件,事件处理函数 才会执行一次,如果设定的时间到来之前,又一次触发了事件,就重新开始延时 如下,持续触发 scroll 事件时,并不执行 handle 函数,当 1000 毫秒内没有触发 scroll 事件时, 才会延时触发 scroll 事件

function debounce(fn, wait) {
var timeout = null;
return function() {
if(timeout !== null) clearTimeout(timeout); timeout = setTimeout(fn, wait);
} } // 处理函数 function handle() { console.log(Math.random()); }
// 滚动事件 
window.addEventListener('scroll', debounce(handle, 1000));

函数节流(throttle):当持续触发事件时,保证一定时间段内只调用一次事件处理函数 节流通俗解释就比如我们水龙头放水,阀门一打开,水哗哗的往下流,秉着勤俭节约的优 良传统美德,我们要把水龙头关小点,最好是如我们心意按照一定规律在某个时间间隔内 一滴一滴的往下滴
如下,持续触发 scroll 事件时,并不立即执行 handle 函数,每隔 1000 毫秒才会执行一次 handle 函数

var throttle =function(func, delay) {
var prev = Date.now(); return function() {
var context = this;
var args = arguments; var now = Date.now();
if (now - prev >= delay) { func.apply(conte

以上是关于时隔许久,精心整理的超级实用的Web前端面试题总结后续来啦的主要内容,如果未能解决你的问题,请参考以下文章

时隔三月!我把整理的Java面试指南在Github开源后,破百万 star了!

前端面试题全面整理-带解析 涵盖CSSJS浏览器VueReact移动web前端性能算法Node

Web前端面试题目及答案汇总

web前端面试题整理(HTML篇)

web前端面试题整理02前端面试题第二弹袭来,接招!(转)

常见的10道Web前端面试题及答案分享!