美文网首页
js底层面试题+代码(机试)

js底层面试题+代码(机试)

作者: 落魂灬 | 来源:发表于2025-07-23 17:09 被阅读0次

1、 new操作符都做了哪些事,手写new操作符

function myNew(func,...args){
  //1.创建一个新的空对象
  const newObj = {}
  //2.将新对象的原型指向构造函数的原型
  newObj._proto_ = func.prototype
  //3.将构造函数的this指向新对象
  let result = apply(newObj,args)
  //4.处理构造函数的返回值,根据返回值进行判断,判断是基本类型还是引用类型
  return result instanceof Object ? result : newObj
}

2、闭包的理解,手写一个闭包函数使用场景

  • 闭包就是能够读取其他函数内部变量的函数
  • 闭包是为了设计私有方法和变量,实现js封装
  • 函数嵌套函数,内部函数可以访问外部函数的变量
//1.解决for循环问题
for(var i = 0;i<5,i++){
  (function(j){
      setTimeOut(function(){
        console.log(j) // 0 1 2 3 4
      },500)
  })(i)
}

3、手写防抖和节流函数

  • 防抖:应用于搜索框输入、窗口大小调整、表单提交事件
function debonce(func,delay){
  let timer = null
  return function(...args){
    if(timer) clearTimeout(timer);
    timer = setTimeout(()=>{
        func.apply(this,args) //延迟执行
      },delay)
  }
}
const searchInput = document.getElementById("myInput")
const fetchData = () => console.log("发送请求")
searchInput.addEventListener("input",debonce(fetchData,500))
  • 节流:应用于滚动加载、鼠标移动事件、高频触发事件
function throttle(func,delay){
  let timer = null
  return function(...args){
    if(!timer){
      timer = setTimeout(()=>{
        func.apply(this,args)
        timer = null
      },delay)
    }
  }
}

window.addEventListener("scroll",throttle(()=>{
  console.log("滚动加载数据")
},1000))

4、js实现快速排序算法

1.快速排序是一种高效的排序算法,采用分治策略

function quickSort(arr) {
  // 如果数组长度小于等于1,直接返回(递归的终止条件)
  if (arr.length <= 1) {
    return arr;
  }

  // 选择基准值(pivot),这里选择中间元素
  const pivotIndex = Math.floor(arr.length / 2);
  const pivot = arr[pivotIndex];
  
  // 定义左右两个数组
  const left = [];
  const right = [];

  // 遍历数组,将元素分配到左右两个数组
  for (let i = 0; i < arr.length; i++) {
    if (i === pivotIndex) continue; // 跳过基准元素
    
    if (arr[i] < pivot) {
      left.push(arr[i]);
    } else {
      right.push(arr[i]);
    }
  }

  // 递归调用并合并结果
  return [...quickSort(left), pivot, ...quickSort(right)];
}

// 使用示例
const unsortedArray = [3, 6, 8, 10, 1, 2, 1];
const sortedArray = quickSort(unsortedArray);
console.log(sortedArray); // 输出: [1, 1, 2, 3, 6, 8, 10]

2.为了更高效地实现快速排序,通常使用Lomuto分区方案,即在数组中选择最后一个元素作为基准值,并通过一次遍历来重新排列数组

function quickSort(arr, left = 0, right = arr.length - 1){
  if(left < right){
    const pivotIndex = partition(arr, left, right);
    quickSort(arr, left, pivotIndex - 1);
    quickSort(arr, pivotIndex + 1, right);
  }
  return arr
}
function partition(arr, left, right){
  const pivot = arr[right]; //选择最右边元素作为基准
  let i = left;
  for(let j = left; j < right; j++){
    if(arr[j] < pivot){
      [arr[i], arr[j]] = [arr[j], arr[i]]; //交换元素
      i++;
    }
  }
   
  [arr[i], arr[right]] = [arr[right], arr[i]]; //将基准放到正确位置
  return i;
}

//使用示例
const array = [3,6,8,10,1,2,1]
quickSort(array);
console.log(array);

5、实现浅拷贝和深拷贝

  • 浅拷贝方法
//1.Object.assign()
const obj = { a: 1, b: { c: 2 } };
const shallowCopy = Object.assign({}, obj);

shallowCopy.b.c = 3; // 修改嵌套对象
console.log(obj.b.c); // 3(原对象也被修改)

//2. 扩展运算符 ...
const obj = { a: 1, b: { c: 2 } };
const shallowCopy = { ...obj };

shallowCopy.b.c = 3;
console.log(obj.b.c); // 3(原对象也被修改)

//3.数组的slice()方法
const arr = [1, 2, { a: 3 }];
const shallowCopy = arr.slice();

shallowCopy[2].a = 4;
console.log(arr[2].a); // 4(原数组也被修改)

//4.Array.from()
const arr = [1, 2, { a: 3 }];
const shallowCopy = Array.from(arr);

shallowCopy[2].a = 4;
console.log(arr[2].a); // 4(原数组也被修改)

//5. 使用赋值运算符(=)进行拷贝
const a = [1, 2, 3];
const b = a; // 浅拷贝
b[0] = 4;
console.log(a); // [4, 2, 3]
console.log(b); // [4, 2, 3]
  • 深拷贝方法
//1. JSON.parase(JSON.stringify(obj))
const obj = { a: 1, b: { c: 2 } };
const deepCopy = JSON.parse(JSON.stringify(obj));

deepCopy.b.c = 3;
console.log(obj.b.c); // 2(原对象不受影响)

缺点:
不能复制 undefined、function、Symbol。
不能处理循环引用(如 obj.self = obj)。
会丢失 Date 对象(转为字符串)。

//2.递归手动实现
function deepClone(obj, hash = new WeakMap()) {
  if (obj === null || typeof obj !== "object") return obj;
  if (hash.has(obj)) return hash.get(obj); // 解决循环引用

  const clone = Array.isArray(obj) ? [] : {};
  hash.set(obj, clone);

  for (const key in obj) {
    if (obj.hasOwnProperty(key)) {
      clone[key] = deepClone(obj[key], hash);
    }
  }

  return clone;
}

// 测试
const obj = { a: 1, b: { c: 2 }, d: [3, 4] };
const deepCopy = deepClone(obj);

deepCopy.b.c = 99;
deepCopy.d.push(5);
console.log(obj); // { a: 1, b: { c: 2 }, d: [3, 4] }(原对象不变)

相关文章

  • OC源码分析-Runtime源码分析(五)

    一 : 几种情况底层调用 减 号 方法底层 加号 方法底层 二 : 面试题 代码执行效果以及原因. 上述代码结构...

  • 2017.8.28打卡5/9

    今天: 1.前桥 1.1 代码:底层,返修代码;底层,下线代码;OPC通讯,机械手 1.2 工程:机加线---...

  • 2017.9.4打卡3/6

    今天: 1.前桥 1.1 代码:底层,返修代码;底层,下线代码;OPC通讯,机械手 1.2 工程:机加线---主桥...

  • iOS - superclass 底层分析

    [toc] 面试题 先切入一个面试问题, 下面代码会输出什么? 底层分析 OC代码 转成C++代码 上面代码拆解 ...

  • 2017.8.15打卡1/5

    今天: 1.前桥--底层,返修代码 2.前桥--底层,下线代码 3.前桥--工作安排;杨工PPT材料;机加工工控机...

  • Javascript学习地图

    学习地图 多分享多总结 js基础 面试题 笔试题 好的代码 新的问题

  • 笔记-关联对象

    目录 面试题 伪代码实现 Category添加属性的几种用法 Category为什么不能添加成员变量 底层源码解读...

  • js基础面试题

    面试题:延迟加载JS有哪些方式? 面试题:JS数据类型有哪些? 面试题:JS数据类型考题 考题一: 考题二: 面试...

  • JS 函数的执行时机

    1. 常见的面试题代码解释 // 6 个 6JS是单线程运行的,setTimeout(code,millisec)...

  • OC对象本质

    面试题:一个NSObject对象占用多少内存?探寻OC对象的本质,我们平时编写的Objective-C代码,底层实...

网友评论

      本文标题:js底层面试题+代码(机试)

      本文链接:https://www.haomeiwen.com/subject/blebnjtx.html