前端面试笔试题集锦(二)
最近有点飘,人在江湖飘,哪能不挨刀。面试题走一波,集成一下从负责人角度常见的问题,让列位帝国精英都能成功崛起。
面试常问问题一:你如何分配前端任务和把控项目进度?
答曰:分配任务和把控进度需要根据团队成员技术指标的一个宏观把控,做到合理划分。具体来说主要有以下几方面:
1.指定项目计划,项目开始前明确项目的里程碑、目标和任务。对任务排期进行总的一个预估。
2.任务拆解。把项目任务拆解成一个一个好管理的、更小粒度的子任务。
3.确定优先级。根据任务的紧急、重要性、依赖关系划分任务的优先级,明确给成员。
4.责任划分。根据成员的经验和技术程度分配任务,注意避免任务的过度分配和任务之间的失衡。
简单的说就是定计划、拆解、定优先级、分配四步。然后实时与成员沟通进度和协作,具有风险意识和备用方案,灵活调整,综合把控。
面试常问问题二:在前端项目中如何进行协作和沟通?
沟通上的可采用的方式主要体现在:
1.使用团队协作工具:jira、微信等等交流工具;
2.定期开展团队会议:可以是日常短会或时间更长的周会。会议的内容有项目进度、解决问题、讨论需求和知识分享。
3.分享文档和知识库。
4.使用版本控制工具。
5.实时沟通。
6.倾听和尊重:鼓励成员与他人分享观点和建议。
7.及时反馈和评估。
参考:
https://www.nowcoder.com/issue/tutorial?zhuanlanId=Mg58Em&uuid=3c850e207f56463599b3017d0d89a8cc
笔试或上机出现的高频测试题:
1.如何判断回文字符数字(或回文字符串、回文数组)
// 法一:利用数组反转为字符串后与原数据比较
var isPalindrome = function(x) { if ( x < 0 ) return false let str = '' + x return Array.from(str).reverse().join('') === str };
// 法二:以中间数为节点,判断左右两边首尾是否相等
var isPalindrome = function(x) {
if ( x < 0 || (x !== 0 && x % 10 === 0)) {
return false
} else if ( 0 <= x && x < 10) {
return true
}
x = '' + x
for(let i = 0 ; i < x.length/2; i++) {
if (x[i] !== x[x.length - i - 1]) {
return false
}
}
return true
};
参考:https://blog.csdn.net/weixin_44517301/article/details/103504834
2.如何添加数字千位符?
// 法一:正则实现
/*
*这里我们直接对数字进行toString(),将其转换成字符串。
*然后使用正则表达式 /\B(?=(\d{3})+(?!\d))/g 来匹配数字中的每三位。
*\B 匹配非单词边界,也就是数字中间位置。(?=(\d{3})+(?!\d)) 是一个正向前瞻匹配,匹配后面接三位数字但是不能把最后一位数字包含进来。
*replace() 中使用逗号替换匹配到的位置。
*这样就可以非常简洁的实现三位分隔了。
*/
// const reg = /(\d)(?=(\d{3})+$)/g; // 只支持不带小数点的数字
function numberWithCommas(x) {
return x.toString().replace(/\B(?=(\d{3})+(?!\d))/g, ",");
}
// 或者:
1. 带有小数点的数据
function addThousandSeparator(number) {
if (!isNaN(number)) {
var source = String(number).split(".");
source[0] = source[0].replace(new RegExp('(\\d)(?=(\\d{3})+$)', 'ig'), "$1,");//只将整数部分进行都好分割
return source.join(".");//再将小数部分合并进来
} else {
return number;
}
}
2.传进参数为数组,返回数组
function addThousandSeparator (numArr) {
var newNumArr = [];
for (var i = 0; i < numArr.length; ++i) {
if (!isNaN(numArr[i])) {
var source = String(numArr[i]).split(".");
source[0] = source[0].replace(new RegExp('(\\d)(?=(\\d{3})+$)', 'ig'), "$1,");//只将整数部分进行都好分割
newNumArr[i] = source.join(".");//再将小数部分合并进来
} else {
newNumArr[i] = numArr[i];
}
}
return newNumArr;
}
// 法二:
function numberWithCommas(x) {
x = x.toString();
var pattern = /(-?\d+)(\d{3})/;
while (pattern.test(x))
x = x.replace(pattern, "$1,$2");
return x;
}
// 法三:toLocaleString()方法
// !!!必须是数字,如果是null或者undefined的话,会报错
console.log((123456789).toLocaleString('en-US')); // 123,456,789
// 最多保留三位小数
console.log((123456789.1315454).toLocaleString('en-US')); // 123,456,789.132
// 法四:new Intl.NumberFormat()方法实现
console.log(new Intl.NumberFormat('en-US', {}).format(123456789.1315454));
// 123,456,789.132
console.log(new Intl.NumberFormat('ja-JP', { style: 'currency', currency: 'JPY' }).format(123456789.1315454));
// ¥123,456,789
// 法五:
function processDot(num, precision) {
return (+(Math.round(+(num + "e" + precision)) + "e" + -precision)).toFixed(
precision,
);
}
function formatNumber(num) {
const result = processDot(num, 2);
return result.replace(/\d(?=(\d{3})+\.)/g, "$&,");
}
3.如何找出数组(或字符串)中成员出现次数最多的那个?
参考:
https://blog.csdn.net/jianlu_blet/article/details/79364797
https://baijiahao.baidu.com/s?id=1603855462187333466&wfr=spider&for=pc
// 对于统计出现的次数的功能,还可以使用reduce的方法;具体实现如下所示:
var arr=[1,2,3,4,5,6,7,8,2,3,4,2,3,6,2,1,4,3,5,2];
arr.reduce((result,cur)=>{
result[cur]?result[cur]++:result[cur]=1
return result;
},{})
// 不统计所有成员出现的次数,只统计成员出现的最多的那个
function maxCountElement(arr) {// 传入一个字符串或者数组
let obj = {};//声明一个接收对象
for (let i = 0; i < arr.length; i++) {// 循环字符串或者数组
let key = arr[i];// 数组或者字符串下标对应的每一项 用key存起来 比如arr=[“a”,“b”,“c”]
//分别是 key=["a","b","c"][0], key=["a","b","c"][1], key=["a","b","c"][2]
if (!obj[key]) {//因为obj开始是空对象 所以初始obj[key]必然为undefined 取反
obj[key]=1;//给obj下对应的key 赋值为1,代表她第一次出现了,之前都是undefined
} else {//当数组或者字符串对应的下标元素 和之前出现的下标元素相同时,
obj[key]++;//obj下对应的key已经存在了 次数递增即可
}
}
let maxCount = 0;//声明一个number值 代表字符串或者数组内某个元素出现的最大次数
let maxElement = arr[0];// 先声明最大数为 字符串或者数组第一项
let repeatElement = [];//声明一个对象接收重复的对象
// console.log(obj,'obj')
// {a: 1, b: 2, c: 4, d: 2, e: 1, …} "obj"
for (let key in obj) {//将接收到的obj 进行for in 循环
if (obj[key] > maxCount) {//如果obj对应的下标大于 某个元素出现的最大次数
maxCount = obj[key];//则将obj对应的下标 出现的次数 用变量存下来
maxElement = key;//这个元素用maxElement存下来
repeatElement.length = 0;// 将重复的元素组成的数组 清空
} else if (maxCount === obj[key]) {//如果最大次数就等于了,接收obj对应的下标出现的次数
repeatElement.push(key);//那么将这个元素放入 接收重复元素的数组
}
}
if (repeatElement.length) {//当eq数组多于一个->也就是出现了同样重复次数的项
for (let j = 0; j < repeatElement.length; j++) {//再次循环接收重复元素的数组
maxElement += ',' + repeatElement[j];//用字符串将重复的元素 连接起来
}
}//最后将,该数组中出现次数最多的元素:maxElement 和它出现次数maxCount return出去;
return "该数组中出现次数最多的元素:" + maxElement + "-出现次数为:" + maxCount + "次";
}
let arr = ["a", "b","b","c", "c","c","c","d","e", "d", "A",];
let res = maxCountElement(arr);
console.log(res);
4.如何实现阶乘?
// 法1:非递归写法
function f(n) {
if (0 === n) {
return 1;
}
let res = 1;
for (let i = 1; i <= n; ++i) {
res *= i;
}
return res;
}
// 法2:递归写法
function g(n) {
if (0 === n) {
return 1;
}
return n*g(n-1);
}
// 法3:动态规划写法
let dp = [];
function h(n) {
if (n < 0 || n !== Math.floor(n)) {
return undefined;
}
if (dp[n]) {
return dp[n];
}
if (0 === n) {
dp[n] = 1;
return 1;
}
for (let i = dp.length; i <= n; ++i) {
dp[i] = dp[i-1]*i;
}
return dp[n];
}
5.数组如何去重{},null,undefined?
function unique(arr) {
var obj = {};
return arr.filter(function(item, index, arr){
return obj.hasOwnProperty(typeof item + item) ? false : (obj[typeof item + item] = true)
})
}
var arr = [1,1,'true','true',true,true,15,15,false,false, undefined,undefined, null,null, NaN, NaN,'NaN', 0, 0, 'a', 'a',{},{}];
console.log(unique(arr))
//[1, "true", true, 15, false, undefined, null, NaN, "NaN", 0, "a", {}]
参考:https://zhuanlan.zhihu.com/p/684324686
6.JS如何实现斐波那契数列?
// 法1:使用迭代循环实现斐波那契数列
function fibonacci(n) {
var fib = [0, 1]; // 斐波那契数列的前两项
for (var i = 2; i <= n; i++) {
fib[i] = fib[i - 1] + fib[i - 2]; // 当前项等于前两项的和
}
return fib[n];
}
// 法2:使用递归实现斐波那契数列
function fibonacci(n) {
if (n <= 1) {
return n; // 当n小于等于1时,直接返回n
}
return fibonacci(n - 1) + fibonacci(n - 2); // 当n大于1时,返回前两项的和
}
// 法3:使用尾递归优化实现斐波那契数列
function fibonacci(n, a = 0, b = 1) {
if (n === 0) {
return a; // 当n等于0时,返回a
}
return fibonacci(n - 1, b, a + b); // 当n大于0时,交换a和b的值,并将n减1,迭代调用函数
}
// 注意:第一种方法使用迭代循环,效率较高;第二种方法使用递归调用,代码简洁但效率较低;第三种方法使用尾递归优化可以提高效率,但需要JavaScript引擎支持尾递归优化。

浙公网安备 33010602011771号