前端面试总结

241 阅读4分钟

1.前端项目如何找到性能瓶颈


定位问题:性能监控工具、chromedevtools查看耗时操作。
解决问题:常见问题:大量列表渲染(分页加载、递归加载。fragment片段加载,时间分片,虚拟列表) 大量图片(预加载、懒加载、图片压缩、base64)
代码中大量计算(循环、递归、内存占用过高) 组件逻辑过于复杂
资源过大(分包加载,异步加载)

2.字符串转二进制


/*
* 字符串转为二进制,空格隔开
* @param {String}
* @return {String}*/
function strToBin (str) {
	var result = '';
	var list =  [];
	for (let i=0; i<str.length; i++) {
		// 将单个字符转换成二进制字符串
		var charCode = str.charCodeAt(i).toString(2)
		list.push(charCode)
		result = list.join(' ')
	}
	return result
}

/*
* 二进制转换为字符串
* @param {binString}
* @result {String}*/
function binToStr (bin) {
  var result = '';
	var list = bin.split(' ');
	for (let i=0; i<list.length; i++) {
		// 将asciiCode字符串转为asciiCode
		let asciiCode = parseInt(list[i],2)
		// 将asciiCode转为字符串
	  result += String.fromCharCode(asciiCode)
	}
	return result
}

/*
* image画到canvas上*/
function imageToCanvas(src, cb){
    var canvas = document.createElement('CANVAS');
    var ctx = canvas.getContext('2d');
    var img = new Image();
    img.src = src;
    img.onload = function (){
        canvas.width = img.width;
        canvas.height = img.height;
        ctx.drawImage(img, 0, 0);
        cb(canvas);
    };
    document.body.appendChild(canvas)
}


/*
* canvas转img*/
function canvasToImage(canvas){
    var img = new Image();
    img.src = canvas.toDataURL('image/jpeg', 1.0);
    return img;}
}


/*
* canvas转dataURL:canvas对象、转换格式、图像品质*/
function canvasToDataURL(canvas, format, quality) {
	return canvas.toDataURL(format||'image/jpeg', quality||1.0);
}



// DataURL转canvas
function dataURLToCanvas(dataurl, cb){
    var canvas = document.createElement('CANVAS');
    var ctx = canvas.getContext('2d');
    var img = new Image();
    img.onload = function(){
        canvas.width = img.width;
        canvas.height = img.height;
        ctx.drawImage(img, 0, 0);
        cb(canvas);
    };
    img.src = dataurl;
}


// File/Blob对象转DataURL
function fileOrBlobToDataURL(obj, cb){
    var a = new FileReader();
    a.readAsDataURL(obj);
    a.onload = function (e){
        cb(e.target.result);
    };
}

// DataURL转Blob对象
function dataURLToBlob(dataurl){
    var arr = dataurl.split(',');
    var mime = arr[0].match(/:(.*?);/)[1];
    var bstr = atob(arr[1]);
    var n = bstr.length;
    var u8arr = new Uint8Array(n);
    while(n--){
        u8arr[n] = bstr.charCodeAt(n);
    }
    return new Blob([u8arr], {type:mime});
}



// Blob转image
function blobToImage(blob, cb){
    fileOrBlobToDataURL(blob, function (dataurl){
        var img = new Image();
        img.src = dataurl;
        cb(img);
    });
}



// image转Blob
function imageToBlob(src, cb){
    imageToCanvas(src, function (canvas){
        cb(dataURLToBlob(canvasToDataURL(canvas)));
    });
}


// canvas转Blob
function canvasToBlob(canvas, cb){
    cb(dataURLToBlob(canvasToDataURL(canvas)));
}

// image转dataURL
function imageToDataURL(src, cb){
    imageToCanvas(src, function (canvas){
        cb(canvasToDataURL(canvas));
    });
}

// dataURL转image,这个不需要转,直接给了src就能用
function dataURLToImage(dataurl){
    var img = new Image();
    img.src = d;
    return img;
}

3.获取数组的交集

/*
* 获取数组的交集*/
function mix(...args){
	// 判断参数的长度如果0,返回空数组
	if(args.length == 0) return []
	// 判断参数长度如果1,返回第一个参数
	if(args.length == 1) return args[0]
	return args.reduce((result,ele) => {
		return result.filter((item) => {
			return ele.includes(item)
		})
	})
}

4.为什么 HTTP1.1 不能实现多路复用


HTTP/1.1 不是二进制传输,而是通过文本进行传输。由于没有流的概念,在使用并行传输(多路复用)传递数据时,接收端在接收到响应后,并不能区分多个响应分别对应的请求,所以无法将多个响应的结果重新进行组装,也就实现不了多路复用。

5.谈一谈 nextTick 的原理


Vue.js中的 nextTick 函数,会传入一个 cb ,这个 cb 会被存储到一个队列中,在下一个 tick 时触发队列中的所有 cb 事件。同步修改状态,异步操作Dom。 异步优先采用微任务microTask(Promise),如果浏览器不支持则用宏任务macroTask(优先setImmediate ,不支持则用settimeout(()=> {}, 0))

6. 如何在 H5 和小程序项目中计算白屏时间和首屏时间,说说你的思路


白屏时间 = 地址栏输入网址后回车 - 浏览器出现第一个元素
1、在head标签的末尾插入script来统计时间节点作为页面开始展示时间节点
2、Timing.navigation Start-Performance Timing.dom Loading
首屏时间 = 地址栏输入网址后回车 - 浏览器第一屏渲染完成
1、最后一个元素后面内嵌js记录时间
2、图片多的页面记录最后一张图片的

7.如何实现骨架屏,说说你的思路


如何实现骨架屏,说说你的思路 1.如果是首屏可以在index.html中手写骨架屏样式
2.如果是其他页面,可以让UI做一个小的SVG图
3.可以使用组件库中的骨架屏组件
4.指令首先要有骨架效果的dom必须要有初始的width,height在刚插入的钩子函数里面去获取dom,设置css渐变动画。在有数据进来时,在update的钩子函数里面去删除骨骼动画。
4.可以使用饿了么团队开源的根据页面样式生成骨架屏的工具[还可配置生效路由],使用puppeteer获取页面,解析dom信息,渲染骨架屏

8.在一个字符串数组中有红、黄、蓝三种颜色的球,且个数不相等、顺序不一致,请为该数组排序。使得排序后数组中球的顺序为:黄、红、蓝。

例如:红蓝蓝黄红黄蓝红红黄红,排序后为:黄黄黄红红红红红蓝蓝蓝。


function sortBalls (str) {
	var tempArr = str.split('')
	// 设置排序规则
	var sortRules = {
		'黄': 0,
		'红': 1,
		'蓝': 2
	}
	// 进行排序
	tempArr = tempArr.sort((a,b) => {
		return sortRules[a]-sortRules[b]
	})
	return tempArr.join('')
}