2023年9月前端面试必看(部分)

500 阅读22分钟

金九银十,希望大家都能找到好的工作!!!

1.post请求两次? 答:post直接连接跨域的服务器,会先发送一次options去请求是否可以接受

2.tcp三次握手和四次挥手 答:握手: 1.客户端向服务器发送一次报文,包含客户端初始序列号 2. 服务器接收客户端的报文,会回复一个报文,包含服务器选择的初始序列号 3. 客户端收到服务器报文后,,会向服务器发送一个 ACK (Acknowledgement) 报文,确认收到了服务器的确认 主要是保持连接的一致性和可通过性也是可靠的 挥手

  1. 客户端发送 FIN 报文,表示请求关闭连接,并携带一个序列号。
  2. 服务器收到 FIN 报文后,发送一个 ACK 报文作为确认,并确认客户端的序列号。
  3. 服务器发送 FIN 报文,表示同意关闭连接,并携带一个序列号。
  4. 客户端收到 FIN 报文后,发送一个 ACK 报文作为确认,并确认服务器的序列号。

3.跨标签页通信 1.broadcastchannel (postmessage,onmessage) 2.监听storage ...

4.网站性能优化 content方面 减少HTTP请求:合并文件、CSS精灵、inline Image 减少DNS查询:DNS缓存、将资源分布到恰当数量的主机名 减少DOM元素数量 Server方面 使用CDN 配置ETag 对组件使用Gzip压缩,ssr Cookie方面 减小cookie大小 css方面 vite-plugin-css 压缩 CSS 文件 Javascript方面 vite会自动压缩js(prod),weboack用到 terser-webpack-plugin对js压缩 图片方面 优化图片:图片压缩,大图可以切片拼接

5.性能优化

  1. 压缩和合并文件:压缩 HTML、CSS 和 JavaScript 文件,去除空格、注释和不必要的字符,并将多个文件合并为一个文件,减少文件的请求和传输时间。
  2. 图片优化:压缩图片文件大小,使用适当的格式(如 WebP 或 JPEG XR),并使用懒加载或按需加载技术加载图片。
  3. 使用浏览器缓存:通过设置适当的缓存策略,利用浏览器缓存机制缓存静态资源,减少服务器请求和加载时间。
  4. 使用异步加载:将 JavaScript 文件异步加载,使用 asyncdefer 属性,或者通过动态创建 <script> 标签来延迟脚本执行,以避免阻塞页面加载。
  5. CSS 和 JavaScript 最小化:将 CSS 放在页面头部,将 JavaScript 放在页面底部,以最小化对页面的渲染阻塞。
  6. 延迟加载和懒加载:将非关键资源(如广告、社交分享按钮等)的加载推迟到页面其他内容加载之后,或在用户滚动到可见区域时再加载。
  7. 响应式设计:使用响应式布局和媒体查询,根据设备分辨率和屏幕尺寸优化页面布局和内容显示。
  8. 代码优化:优化 JavaScript 代码,减少不必要的计算和操作,使用高效算法和数据结构,避免过度渲染和重绘。
  9. 使用字体图标:使用字体图标代替图片图标,减少请求和下载时间。
  10. DNS 预解析:通过 <link rel="dns-prefetch"> 标签预解析外部资源的域名,减少 DNS 查询时间。
  11. 异步加载第三方脚本:避免阻塞页面加载的第三方脚本,使用异步加载或延迟加载的方式加载并执行。
  12. 服务端渲染(SSR):将部分页面内容在服务器端生成,并使用 SSR 技术提供首屏快速渲染,减少客户端渲染时间。
  13. 使用 CDN 加速:将静态资源部署到 CDN 上,提供全球分布的缓存节点,加速资源的传输和加载

6.v-model 双向绑定的原理是什么? 双向绑定过程基于 Object.defineProperty 或 Proxy 可以通过 getter 和 setter 方法来创建数据的副本,并进行数据的监听和更新。Vue.js 使用这些底层的机制来实现双向绑定,以便在数据或视图的任何一方发生变化时,另一方可以自动更新。

总结起来,v-model 双向绑定的原理是基于数据属性和表单元素之间的事件监听和数据更新,实现了数据和视图之间的自动同步。这简化了开发者对数据流动的管理,使得操作表单元素和数据的交互更加直观和便捷。

7.vue2.x 和 vuex3.x 渲染器的 diff 算法分别说一下 Vue2.x 和 Vue3.x 的渲染器都使用了虚拟 DOM(Virtual DOM)的概念,但它们的 diff 算法略有不同。

Vue2.x 的 diff 算法

Vue2 的核心 Diff 算法采用了双端比较的算法,同时从新旧 children 的两端开始进行比较,借助 key 值找到可复用的节点,再进行相关操作。相比 React 的 Diff 算法,同样情况下可以减少移动节点次数,减少不必要的性能损耗,更加的优雅。

Vue3.x 的 diff 算法

先通过双端指针获得新老节点的头尾边界。

通过判断边界我们可以知道是否出现包含的情况,对于这种情况,简单的删除和增加就能完成节点的更新。

如果没有出现包含意味着此时新老节点存在乱序的部分,需要节点最长递增子序列等算法完成节点的更新。

对于复杂情况首先建立新节点乱序部分的key,index映射表,和一个长度等长的数组存储新老节点的映射。

遍历老节点乱序部分,如果当前节点没有在新节点乱序部分出现则删除即可,如果出现了那么通过key,index映射表找到当前节点在新节点乱序部分的位置,并将当前节点在老节点处的下标存到 新老节点的映射数组中指定的下标里面。

当老节点乱序部分遍历完成之后,就可以得到新老节点的映射数组,项值为0说明要新增,项值非0 说明当前节点在新老节点中都出现。

通过最长递增子序列找到新老节点的映射数组中不需要移动位置的节点。

开始遍历新老节点的映射数组,如果当前节点的值为0,创建这个节点,如果非0就判断当前节点是否和最长递增子序列存在映射关系,存在说明不需要移动,反之这个节点需要移动。

==============

  1. new map 和普通对象的区别

(1)首先map 使用 哈希表 的数据结构 (散列函数+链表构成的) (2)初始化与使用不同

const obj = {  name: 1,  age: 2,};
const map = new Map([  ['name', 1],  ['age', 2],]);

(3) 键 类型不同: map 可以接受很多类型的东西作为key (函数对象方法等等) 而object 基本只有字符串之内的东西

(4)键 object顺序不固定 map顺序固定

(5) map 不支持 JSON 序列化

(6)Map 对象在涉及频繁添加和删除键值对的场景中表现更好,而普通对象没有优化。

  1. new 做了哪些事情 那么new的过程发生了什么?

    1、new先创建了一个空对象

    var news = new Object()

    2、我们将这个空对象的__proto__属性指向whatnew构造函数的prototype属性,使两者都有共同的原型对象whatnew.prototype,因此空对象可以访问whatnew函数

    new.proto = whatnew.prototype

    3、修改whatnew的this到object上面,call/apply,并把参数传入

    4、最后把object返回给mynew就可以了

  2. 和weakMap 区别 首先,Map 和 WeakMap 都属于 ES6 中新增的数据类型,用于存储键值对。

    1. Map 是一个普通的键值对集合,可以使用任何类型的值作为键或值,包括基本类型和对象。而 WeakMap 的键必须是对象,值可以是任何类型。

    2. Map 中的键值对是强引用关系,即只要 Map 中的键或值存在,Map 对象就会一直保留这个键值对,不会被垃圾回收。而 WeakMap 中的键值对是弱引用关系,如果 WeakMap 的键不再被引用,那么这个键值对就会被自动删除。

    3. 由于 WeakMap 中的键是弱引用,所以 WeakMap 对象的 size 属性无法访问,也无法使用 forEach() 和 clear() 等方法。

    4. WeakMap 对象的主要应用场景是需要与另外一个对象关联,并且不想影响到这个对象的垃圾回收机制,以避免内存泄漏。例如,将对象存储在 WeakMap 中,可以确保这个对象只在其他地方仍然被引用时才被保留,否则会自动被删除,从而避免内存泄漏。

  3. react 架构15 和16的区别 fiber 改了哪些

    1. 增量渲染(Incremental Rendering):在 React 15 中,每次状态更新会导致组件重新渲染整个树,这可能会导致性能问题。而在 React 16 中,Fiber 架构引入了增量渲染,它只更新组件的子树,而不是整个树。这意味着在组件树中只有受影响的部分才会重新渲染,提高了性能。
    2. 并发模式(Concurrent Mode):React 16 中的 Fiber 架构还引入了并发模式。在并发模式下,React 可以同时处理多个任务,而不仅仅是按顺序一个接一个地处理。这使得 React 在处理用户交互和更新 UI 之间更加流畅。
    3. Error Handling:Fiber 还改进了错误处理机制。在 React 15 中,如果组件抛出错误,整个应用都会崩溃。而在 React 16 中,Fiber 通过在每个组件上附加一个错误边界来捕获错误,并显示适当的错误消息。这使得错误处理更加可靠和可预测。
    4. 数据获取和组件通信:Fiber 还对数据获取和组件通信进行了改进。在 React 15 中,数据获取和组件通信可能会导致阻塞和性能问题。而在 React 16 中,Fiber 通过将数据获取和组件通信拆分为多个小任务,并使用优先级调度来管理这些任务,从而提高了性能和响应速度。
  4. 除了递归树 还有别的方法吗 抛开前端,用数据结构思考 React 16 的 diff 算法采用了层次遍历的方式,从链表的头部开始比较。在比较过程中,对于新旧节点,React 会根据节点类型和属性进行分类处理。例如,对于文本节点(包含字符串和数字),React 会直接进行比较并更新;对于单个 React 元素,React 会通过检查其类型和属性来确定是否需要更新;对于数组和可迭代的子节点,React 会使用类似于处理数组的方式进行处理。

    1. 减少不必要的重新渲染:在 React 15 的 diff 算法中,每次状态更新都会导致组件重新渲染整个 DOM 树,这可能导致不必要的重新渲染。而使用链表可以避免这种情况,因为链表只包含需要更新的子节点,从而减少不必要的重新渲染。
    2. 提高性能:链表结构相比于树结构更加高效地处理更新。在树结构中,每次更新都需要遍历整个 DOM 树,而在链表中,只需要遍历链表头部和尾部即可找到需要更新的节点。这样可以在更短的时间内完成更新操作,提高性能。
    3. 提高代码的可维护性:使用链表结构可以使得 diff 算法更加简洁明了,易于维护。链表结构相比于树结构更容易理解和实现,代码更加清晰易懂。
  5. 页面刷新后 浏览器做了那些事情

    当页面刷新后,浏览器会清除之前的缓存,并重新加载页面和请求服务器接口。 对于之前加载一半的页面或正在请求服务器接口的情况,浏览器会停止当前的请求,并重新发送请求以获取最新的页面内容。这确保了浏览器可以获取到最新的页面数据和正确的渲染结果。 在重新加载页面时,浏览器可能会使用缓存策略来提高加载速度。例如,浏览器会使用缓存中的HTML、CSS和JavaScript文件来加快页面的加载速度。但是,如果页面中的某些资源已经过期(例如,服务器上的文件已经更新),浏览器将发送一个新的请求来获取最新的资源。

总之,当页面刷新后,浏览器会清除之前的缓存并重新加载页面和请求服务器接口。这确保了用户可以获取到最新的页面内容和正确的渲染结果。

  1. 现场看了两道代码题

  2. redux 为啥可以异步更新

    Redux 本身是同步的状态管理库,但在处理复杂的应用场景时,可能需要执行异步操作,例如发起网络请求、处理定时器等。为了支持这些异步操作,Redux 使用了中间件。中间件是一个在 Redux action 被发起之后,到达 reducer 之前的扩展点。它可以拦截 action,执行一些额外的逻辑,然后将 action 继续传递给下一个中间件或最终到达 reducer。这样,中间件允许你处理异步操作、日志记录、路由导航等任务。常见的 Redux 中间件,例如 redux-thunk、redux-saga、redux-observable 等,都是基于这个原理实现的。这些中间件为 Redux 提供了处理异步操作的能力,使开发者可以更灵活地管理应用的状态和副作用。它们能够拦截 action,执行异步操作,然后派发新的 action 来更新状态。

  3. 思考一下,我现在要写一个钩子,我要保存页面上一次的状态,你怎么写。

  4. js class 普通构造函数 的this问题。 bing call apply 哪里不同

  5. 微前端和 ifarme 有啥不同。

Qiankun微前端框架在样式隔离方面主要采用了两种方式:

  1. 基于Web Components的样式隔离:Qiankun利用Shadow DOM的特性,在应用程序容器中创建一个隔离的DOM树,使得每个子应用都可以拥有自己独立的样式作用域。每个子应用都被封装为一个Custom Element,这个Custom Element包含了子应用所需的所有HTML、CSS和JavaScript代码,并使用ShadowDOM将其包裹起来。由于Shadow DOM具有隔离性,因此子应用中声明的CSS样式只会作用于其内部,不会影响到其他子应用或主应用。

  2. Scoped样式隔离:Qiankun还提供了基于属性选择器实现的Scoped样式隔离。在解析html模板字符串之前,会先包裹一层div,并为这个div节点添加data-qian属性,属性值为子应用的name属性 然后遍历html模板字符串中所有的style节点,依次为内部样式表中的样式添加div["data-qiankun=xxx"]前缀。这样就可以确保子应用中的样式只作用于其内部,不会影响到其他子应用或主应用。

requestAnimationFrame

equestAnimationFrame是浏览器提供的一个用于优化动画和渲染的API。它基于浏览器的刷新率,调度回调函数的执行,以确保动画和渲染的流畅性和高性能。

使用requestAnimationFrame,开发者可以在每个浏览器刷新帧之前请求执行一个函数。浏览器会在适当的时机调用这个函数,以保证动画和渲染的协调性。通过与浏览器的合作,requestAnimationFrame可以避免不必要的渲染操作,并确保动画的效果更加平滑。

在 React 中,useEffectuseLayoutEffect 的实现原理是使用 JavaScript 的闭包和回调函数。当你在组件中使用 useEffectuseLayoutEffect 时,React 会创建一个内部函数(也称为清理函数)并将其存储在一个数组中。这个数组是一个副作用(side effect)的注册表,其中每个条目都包含一个清理函数和它被创建时传递给 useEffectuseLayoutEffect 的所有参数。

当组件完成渲染和更新后,React 会调用这些清理函数。这是通过遍历副作用注册表并调用每个清理函数来完成的。清理函数通常用于取消任何在创建时可能已经启动的异步操作(例如网络请求或定时器),以避免在组件卸载或更新后继续执行这些操作。

总结一下,useEffectuseLayoutEffect 的实现原理是使用 JavaScript 的闭包和回调函数来存储和执行清理函数。它们使用的数据结构是一个副作用注册表,其中每个条目都包含一个清理函数和它被创建时传递给 Hook 的参数。

PWA(Progressive Web App,渐进式网页应用)是一种使用多种技术增强web app的功能,让其体验变得更好的理念。它旨在模拟一些原生功能,如通知推送,让网站的体验变得更好。PWA不能包含原生OS相关代码,但仍被认为是网站,只是在缓存、通知、后台功能等方面表现更好。访问更快,首屏可以部署在服务端,节省网页请求时间,加载速度更快,拥有更平滑的动态效果和快速的页面响应。同时支持各种类型的终端和屏幕,提供沉浸式的全屏幕体验。

Shadow DOM 是一种在 HTML 中隐藏 DOM 结构的技术,它被视为“DOM中的DOM”。它允许在文档渲染时插入一颗DOM元素子树,但这棵子树不在主DOM树中,因此它是一种独立的DOM结构。

Shadow DOM 可以被视为一种作用域的概念,它不会被外部所影响。可以将Shadow DOM视为一个单独的DOM树,它具有自己的元素和样式,与原始DOM完全隔离。

在Web组件中,Shadow DOM是一种关键技术,可以将标记结构、样式和行为隐藏起来,并与页面上的其他代码相隔离,保证不同的部分不会混在一起,使代码更加干净、整洁。在Shadow DOM中,可以将一个隐藏的、独立的DOM附加到一个元素上,这样就可以在其中包含自定义的元素和样式,而不会影响主DOM树。

总之,Shadow DOM是一种允许在HTML中隐藏DOM结构的技术,它可以将标记结构、样式和行为隐藏起来,与页面上的其他代码相隔离,使代码更加干净、整洁。

==============

www.yuque.com/u211232/gql…

待做问题

  • webworker中为什么能提升js执行的性能?

  • 你是怎么使用webworker的?

  • 浏览器内存你在实战中处理过吗?

  • 浏览器的垃圾回收机制是什么样的?

  • 你在做微前端的时候,为什么选择qiankun

  • qiankun的原理了解哪些

  • 你在使用qiankun的时候,有没有发现这个框架的不足之处1. vite为什么比webpack快

  • vite的预构建是如何做的

  • tree-shaking是如何做的,commonjs能用吗

  • qiankun的js沙箱和css沙箱原理是啥

天融信(2023.08)

  • 1.浅拷贝深拷贝
  • 2.原型和原型链
  • 3.函数柯里化
  • 4.BOM和DOM
  • 5.for in和for of
  • 6.哪些地方不能使用箭头函数
  • 7.创建一个对象的过程
  • 8.防抖节流
  • 9.写一个自定义事件
  • 10.前端怎么获取页面中哪个元素是最多的。
  • 11.React diff算法
  • 12.Redux源码有看过吗
  • 13.three性能优化
  • 14.多个模型共享材质,一个模型需要修改,怎么做
  • 15.隐藏一个模型用什么属性
  • 16.用过哪些three的控制器
  • 17.微前端怎么做的
  • 18.点云怎么优化的
  • 19.大数据量加载怎么优化的
  • 20.聊项目,项目中做了哪些事情,主要是用three做了哪些事情

2.集度(2023.08)

  • 1.requestAnimationFrame
  • 2.plugin
  • 3.load
  • 4.Webpack你项目中做过哪些配置
  • 5.hooks
  • 6.useEffect
  • 7.useMemo和useCallback
  • 8.flex:1是什么意思
  • 9.BFC
  • 10.两数之和
  • 11.项目有什么亮点
  • 12.项目有什么难点
  • 13.webwork在项目中怎么用的
  • 14.点云大文件渲染

3.滴滴(2023.09)

  • 1.react fiber
  • 2.http1.1、http2、http3
  • 3.https和http的区别,http是怎么加密的
  • 4.OSI 七层网络模型
  • 5.tcp和udp区别
  • 6.三次握手
  • 7.webpack打包流程
  • 8.babel原理
  • 9.tree shaking原理
  • 10.输入一个url到页面显示整个过程
  • 11.JS事件循环,宏任务、微任务
  • 12.设计模式有没有了解过
  • 13.项目webwork怎么用的
  • 14.如何通过角度去计算弧度
  • 15.如何判断一条线在一个平面内
  • 16.写一个发布订阅
  • 17.写一个前序遍历
  • 18.写一个Promise.all

4.如祺出行(2023.09)

  • 1.three拾取是怎么做的
  • 2.有没有写过shader,有没有用shader写过一些效果

5.淘车车二手车(2023.10)

  • 1.reducer
  • 2.实现一个发布订阅
  • 3.函数柯里化
  • 4.事件循环
  • 5.微前端沙箱隔离怎么实现
  • 6.antd form组件中自定义组件,双向绑定的实现
  • 7.fiber架构,react18并发
  • 8.useEffect先执行还是dom先渲染,生命周期的深入理解
  • 9.纯函数,高阶函数,高阶组件
  • 10.useEffect useLayoutEffect
  • 11.父组件和子组件渲染过程
  • 12.函数组件和类组件
  • 13.hooks
  • 14.有没有封装过组件,写过组件库

6.泰瑞数创(2023.10)

  • 1.three相关
  • 2.shader相关

7.白龙马云行科技(2023.11)

  • 1.three相关 法向 点击操作
  • 2.数组去重
  • 3.css position ui组件库样式修改
  • 4.介绍一下Promise以及它的方法
  • 5.react useEffect
  • 6.闭包
  • 7.requestAnimationFrame
  • 8.跨域
  • 9.浏览器存储
  • 10.微前端怎么做的

8.云奥赛凡(2023.11)

  • 1.antd中的form表单组件,父组件没有使用props传值给Form.item,那么Form.item是怎么拿到数据的。
  • 2.输入URL到页面显示的过程?
  • 3.反转链表
  • 4.强缓存和协商缓存
  • 5.浏览器缓存
  • 6.webpack中的环境变量是怎么注入的
  • 7.页面菜单切换
  • 8.原型和原型链
  • 9.闭包
  • 10.微前端
  • 11.项目介绍,具体做了哪些东西,技术方面
  • 12.前端图片相关的介绍处理,图片裂了该怎么处理
  • 13.说一说canvas
  • 14.遇到过哪些问题,在项目中做了哪些事情?
  • 15.在写React代码的时候你自己做过哪些性能优化

9.地平线(2023.11)

  • 1.节流代码实现
  • 2.深拷贝代码实现
  • 3.事件循环
  • 4.看代码说输出题,关于作用域以及基本类型和引用类型的
  • 5.什么是回调地狱,如何解决?引出 Promise async await
  • 6.position属性介绍
  • 7.介绍一下hooks,你用过哪些
  • 8.类组件和函数组件
  • 9.useCallback和useRefs区别
  • 10.Redux
  • 11.浏览器缓存
  • 12.git相关操作
  • 13.项目中点云相关
  • 14.项目帧率处理相关
  • 15.怎么进行新技术的学习?
  • 16.react相比于原生js或jquery这些原生或框架如果要说出你觉得最重要的一条特点是什么?
  • 17.类组件和生命周期,对比函数组件
  • 18.组件卸载,怎么卸载
  • 19.高阶组件 高阶组件的生命周期
  • 20.useEffect原理,更新
  • 21.受控组件与非受控组件,非受控组件怎么操作
  • 22.useMemo与React.memo
  • 23.纯函数里面发一个请求,那么这个函数还是纯函数吗
  • 24.React中设置一个随机key会怎样
  • 25.html缓存了怎么更新,js和css缓存是怎么更新的
  • 26.canvas怎么做点击拾取
  • 27.three怎么做点击拾取操作
  • 28.m * n 的矩阵乘以 n*m的矩阵得到一个几乘几的矩阵
  • 29.逆矩阵
  • 30.四元数
  • 31.说一下着色器
  • 32.函数柯里化,并且在什么场景下使用
  • 33.察者模式和发布订阅模式的区别
  • 34.场景题:实现一个小方块跟随鼠标移动

10.恺望数据(2023.11)

  • 1.项目难点优化
  • 2.monorepo是怎么做的
  • 3.微前端是怎么做的,原理?
  • 4.项目构建工具有考虑换vite吗?vite有什么优势?
  • 5.搭建项目架构怎么搭的?
  • 6.react中一个父组件,两个子组件,一个传props,一个不传props,父组件重新渲染,两个子组件会不会都重新渲染
  • 7.hooks
  • 8.useMemo、useCallback、useRef
  • 9.React.memo有什么优点缺点
  • 10.用栈实现队列
  • 11.three坐标系转换

11.百度(2023.11)

  • 1.事件循环输出题
js
复制代码
console.log('1')
setTimeout(() => {
    console.log('2');
}, 0)
requestAnimationFrame(() => {
    console.log('3') 
})
requestIdleCallback(() => {
    console.log('4')
})
new Promise(resolve => {
    console.log('5');
}).then(value => {
    console.log(value);
});
async function a() {
    console.log(await '7');
}
a()
console.log('8')
  • 2.手写promise.all
  • 3.最长回文子串(leetcode第5题)
  • 4.requestAnimationFrame
  • 5.useEffect useLayoutEffect useLayoutEffect使用场景
  • 6.hooks为什么只能写在顶层,不写在顶层会报错吗
  • 7.函数组件中的生命周期
  • 8.Vite为什么比Webpack快
  • 9.webpack打包的产物是怎么样的,要你去写你怎么写
  • 10.webpack打包优化
  • 11.Es Module 和 CommonJs
  • 12.前端页面性能优化
  • 13.大模型3D中的前端性能优化