前言
咳咳~找到实习前也面了好几家,但找到实习后就懒得写面经了,一直拖到现在才从草稿箱中拿出来
北京 知能科技(300 - 400/天)
1.项目中规划了哪些功能?挑几个了解的讲讲用了什么技术实现?遇到印象深刻的困难怎么解决?
2. CSS中的清除浮动的方法有哪些?
- 添加额外标签
html
<div class="parent">
//添加额外标签并且添加clear属性
<div style="clear:both"></div>
//也可以加一个br标签
</div>
- 父级添加overflow属性,或者设置高度
- 建立伪类选择器清除浮动
js
//在css中添加:after伪元素
.parent:after{
/* 设置添加子元素的内容是空 */
content: '';
/* 设置添加子元素为块级元素 */
display: block;
/* 设置添加的子元素的高度0 */
height: 0;
/* 设置添加子元素看不见 */
visibility: hidden;
/* 设置clear:both */
clear: both;
}
3. (场景题)如何使用js和css实现一个时钟?
4. 讲一下箭头函数?
5. 你用的vue比较多,你可以讲讲它的响应式原理吗?
6. get和post请求在使用上的区别?
从w3schools
得到的标准答案的区别如下:
-
GET在浏览器回退时是无害的,而POST会再次提交请求。
-
GET产生的URL地址可以被Bookmark,而POST不可以。
-
GET请求会被浏览器主动cache,而POST不会,除非手动设置。
-
GET请求只能进行url编码,而POST支持多种编码方式。
-
GET请求参数会被完整保留在浏览器历史记录里,而POST中的参数不会被保留。
-
GET请求在URL中传送的参数是有长度限制的,而POST没有。
-
对参数的数据类型,GET只接受ASCII字符,而POST没有限制。
-
GET比POST更不安全,因为参数直接暴露在URL上,所以不能用来传递敏感信息。
-
GET参数通过URL传递,POST放在Request body中
7. 对MVC有了解吗?
MVC(Model-View-Controller)是一种软件架构模式,广泛应用于各种编程语言和框架中,包括 Node.js。该模式的目标是将应用程序的不同部分分离开来,以促进代码的可维护性、可扩展性和重用性。
在 Node.js 中,MVC 也被广泛应用于构建 Web 应用程序。下面是 MVC 的三个核心组件及其职责:
-
Model(模型):负责处理应用程序的数据逻辑,通常与数据库进行交互。它负责定义数据的结构、数据的获取和存储等操作。在 Node.js 中,通常使用 ORM(Object Relational Mapping)库或者 ODM(Object Document Mapping)库来简化与数据库的交互。
-
View(视图):负责呈现数据给用户,并处理用户界面的展示逻辑。视图是用户界面的一部分,可以是 HTML、模板引擎的渲染结果或其他前端技术生成的界面。在 Node.js 中,可以使用模板引擎(如 EJS、Pug 等)来生成动态的视图。
-
Controller(控制器):接收请求并处理请求中的数据,在模型和视图之间协调数据的流动。控制器负责处理用户的输入,调用相应的模型来获取数据,并将数据传递给视图进行展示。在 Node.js 中,通常使用路由来将请求映射到相应的控制器函数。
MVC 的好处在于明确的角色分工和逻辑分离,可以提高代码的可读性、可维护性和可测试性。它还有利于团队协作和代码重用,使得应用程序的开发更加高效和可靠。
江苏 雪浪云(150 - 200/天) (全是vue系列)
1. vue2和vue3的响应式区别,有了解过吗?
vue2响应式
实现原理:
对象类型:通过Object.defineProperty()对属性的读取、修改进行拦截(数据劫持)。
数组类型:通过重写更新数组的一系列方法来实现拦截。(对数组的变更方法进行了包裹)。
存在问题:
当对象中属性过多时Object.defineProperty()
需针对每个属性进行遍历实现响应式,效率不高;
新增属性、删除属性, 界面不会更新;
只有configurable为true时候,该属性才能从对应的对象上被删除,但源数据不会响应删除;
直接通过下标修改数组, 界面不会自动更新。
vue3响应式
实现原理:
- 通过Proxy(代理): 拦截对象中任意属性的变化, 包括:属性值的读写、属性的添加、属性的删除等。
2. vue2的话对于数组的监听,有了解过吗?
在 Vue 2 中,对于数组的监听有一些限制和注意事项。Vue 2 使用了 Object.defineProperty 来追踪数组的变化,但是它只能拦截数组的部分方法(如 push、pop、shift、unshift、splice、sort 和 reverse)。这意味着直接通过索引修改数组元素或使用其他数组特有的方法(如 slice、concat 等)时,并不会触发响应式更新。
为了解决这个问题,Vue 2 提供了一些数组变异方法的替代方案,例如通过以下方式更新数组:
js
// 使用 Vue.set 或 this.$set
Vue.set(array, indexOfItem, newValue);
this.$set(this.array, indexOfItem, newValue);
// 使用 splice
array.splice(indexOfItem, 1, newValue);
另外,Vue 2 还提供了 $watch
方法来监听数组的变化,可以通过监听数组的 $data
属性来实现:
js
this.$watch('$data.array', (newVal, oldVal) => {
// 数组变化后的回调处理
});
需要注意的是,在 Vue 2 中,直接修改数组或使用非变异方法时,并不会触发响应式更新。所以如果需要对数组的修改进行响应式追踪,需要使用上述提供的替代方案或选择使用 Vue 3,其中的 Proxy 响应式系统可以更好地追踪数组的变化。
3. vue3的ref和reative的区别是什么?
4. vue3中watch和watcheffect讲一下?
在 Vue.js 3 中,watch
和 watchEffect
是用于监测响应式数据变化的两个 API。它们的用途和功能略有不同,下面我会对它们进行详细说明:
-
watch:
-
watch
是一个函数,接受两个参数:要监测的响应式数据或者计算属性,以及一个回调函数。 -
当被监测的数据发生变化时,
watch
会立即执行回调函数,并传入两个参数:新值和旧值。 -
watch
还可以接收一个可选的配置对象,用于指定更多的选项,比如是否深度监听、立即触发回调等。 -
示例代码:
javascriptwatch(() => count.value, (newValue, oldValue) => { console.log(newValue, oldValue); });
-
-
watchEffect:
-
watchEffect
是一个函数,接受一个回调函数作为参数。 -
在回调函数内部,可以直接访问响应式数据,并且当这些响应式数据发生变化时,回调函数会被重新执行。
-
watchEffect
会在组件初始化时立即执行一次,然后在其依赖的响应式数据变化时再次执行。 -
示例代码:
scsswatchEffect(() => { console.log(count.value); });
-
需要注意的是,watch
和 watchEffect
的使用场景略有差异:
-
如果需要对特定的响应式数据变化做一些具体的操作,可以使用
watch
,并在回调函数中编写相应的逻辑。 -
如果只是希望在某个响应式数据发生变化时执行一些代码逻辑,可以使用
watchEffect
,无需指定具体的依赖项。
5. vue中watch和compute的区别是什么?
通俗来讲,既能用 computed 实现又可以用 watch 监听来实现的功能,推荐用 computed, 重点在于 computed 的缓存功能。computed 计算属性是用来声明式的描述一个值依赖了其它的值,当所依赖的值或者变量 改变时,计算属性也会跟着改变; watch 监听的是已经在 data 中定义的变量,当该变量变化时,会触发 watch 中的方法。
watch 属性监听 是一个对象,键是需要观察的属性,值是对应回调函数,主要用来监听某些特定数据的变化,从而进行某些具体的业务逻辑操作,监听属性的变化,需要在数据变化时执行异步或开销较大的操作时使用
computed 计算属性 属性的结果会被缓存
,当computed
中的函数所依赖的属性没有发生改变的时候,那么调用当前函数的时候结果会从缓存中读取。除非依赖的响应式属性变化时才会重新计算,主要当做属性来使用 computed
中的函数必须用return
返回最终的结果 computed
更高效,优先使用。data 不改变,computed 不更新。
使用场景
computed
:当一个属性受多个属性影响的时候使用,例:购物车商品结算功能
watch
:当一条数据影响多条数据的时候使用,例:搜索数据
6. 路由懒加载这个概念了解过吗?
7. vue中keep-alive怎么实现的以及里面属性的使用场景?
keep-alive
是vue
中的内置组件,能在组件切换过程中将状态保留在内存中,防止重复渲染DOM
keep-alive
包裹动态组件时,会缓存不活动的组件实例,而不是销毁它们
keep-alive
可以设置以下props
属性:
include
- 字符串或正则表达式。只有名称匹配的组件会被缓存exclude
- 字符串或正则表达式。任何名称匹配的组件都不会被缓存max
- 数字。最多可以缓存多少组件实例
8. 使用keep-alive缓存过多,页面过卡,有对它做些什么算法优化吗?
- keep-alive 的中还运用了 LRU(最近最少使用) 算法,选择最近最久未使用的组件予以淘汰。
9. 加了keep-alive多了哪两个工作函数有了解过吗?
- 两个生命周期 activated/deactivated,用来得知当前组件是否处于活跃状态。
10. vue-router有几种类型?
-
hash模式
,兼容性非常,基本兼容所有浏览器,但是对SEO不够友好,在路由上会多出一个 # 字符,使路由看起来不够纯粹。 -
HTML5模式
(history模式
),使用这种历史模式,URL看起来会正常,但是初次访问或者刷新都会向服务器请求,如果在服务器没有一个适当的配置,就会得到一个404
,这就很尴尬。
11. 有了解过哈希路由和history路由是基于原生的什么方式去实现的吗?
hash 模式
- location.hash 的值实际就是 URL 中#后面的东西 它的特点在于:hash 虽然出现 URL 中,但不会被包含在 HTTP 请求中,对后端完全没有影响,因此改变 hash 不会重新加载页面。
- 可以为 hash 的改变添加监听事件
js
window.addEventListener("hashchange", funcRef, false);
每一次改变 hash(window.location.hash),都会在浏览器的访问历史中增加一个记录利用 hash 的以上特点,就可以来实现前端路由"更新视图但不重新请求页面"的功能了
特点:兼容性好但是不美观
history 模式
利用了 HTML5 History Interface 中新增的 pushState() 和 replaceState() 方法。
这两个方法应用于浏览器的历史记录站,在当前已有的 back、forward、go 的基础之上,它们提供了对历史记录进行修改的功能。这两个方法有个共同的特点:当调用他们修改浏览器历史记录栈后,虽然当前 URL 改变了,但浏览器不会刷新页面,这就为单页应用前端路由"更新视图但不重新请求页面"提供了基础。
特点:虽然美观,但是刷新会出现 404 需要后端进行配置
12. 使用pinia的话进行刷新页面可能会导致store的数据丢失,怎么解决?
-
持久化存储数据: 将 store 的数据进行持久化存储,以防止页面刷新导致数据丢失。你可以使用浏览器提供的 Web Storage API,如 localStorage 或 sessionStorage,将 store 数据存储在本地浏览器中。在加载应用程序时,可以从存储中恢复数据到 store。
-
在页面刷新时触发保存操作: 监听浏览器的
beforeunload
事件,在页面刷新或关闭之前触发保存 store 数据的操作。这样,在用户尝试刷新页面时,可以先将数据保存到持久化存储中,然后再刷新页面。可以通过添加以下代码来实现:jswindow.addEventListener('beforeunload', () => { // 在这里触发保存 store 数据的操作 });
-
使用插件管理持久化状态: 你还可以使用 Vue 插件来管理 store 的持久化状态。例如,vuex-persistedstate 是一个用于 Vuex 的插件,它可以自动将 store 数据持久化到本地存储中,并在页面加载时恢复数据。对于 Pinia,你可以寻找类似的插件来管理持久化状态。
13. vite和webpack的区别?
Webpack
和Vite
都是现代前端开发中常用的构建工具,用于帮助开发者管理、打包和优化项目中的代码资源。它们有一些区别,下面是它们的主要区别:
vite和webpack的区别:1、基础概念不同;2、编译方式不同;3、开发效率不同;4、扩展性不同;5、应用场景不同。总的来说,vite以其更快的编译速度和更低的内存占用率,给前端开发带来了全新的体验,而webpack凭借其高度的自定义性和成熟的生态,仍是前端构建工具的重要选择。
一、基础概念不同
webpack是一个模块打包器,它可以把许多不同类型的模块和资源文件打包为静态资源。它具有高度的可配置性,可以通过插件和loader扩展其功能。
vite,由Vue.js作者尤雨溪开发并维护,是一个基于浏览器原生 ES imports 的开发服务器。它能够提供丰富的功能,如快速冷启动、即时热更新和真正的按需编译等。
二、编译方式不同
webpack在编译过程中,会将所有模块打包为一个bundle.js文件,然后再运行这个文件。
而vite在开发模式下,没有打包的步骤,它利用了浏览器的ES Module Imports特性,只有在真正需要时才编译文件。在生产模式下,vite使用Rollup进行打包,提供更好的tree-shaking,代码压缩和性能优化。
三、开发效率不同
webpack的热更新是全量更新,即使修改一个小文件,也会重新编译整个应用,这在大型应用中可能会导致编译速度变慢。
vite的热更新是增量更新,只更新修改的文件,所以即使在大型应用中也能保持极快的编译速度。
四、扩展性不同
webpack有着成熟的插件生态,几乎可以实现任何你想要的功能,扩展性非常强。
vite虽然也支持插件,但相比webpack的生态,还有一些距离。
五、应用场景不同
webpack由于其丰富的功能和扩展性,适合于大型、复杂的项目。
而vite凭借其轻量和速度,更适合于中小型项目和快速原型开发。
14. 使用vite对浏览器的兼容会不会有影响?有了解过吗?
需要浏览器支持ES module
15. babel是用来干嘛的有了解过吗?
Babel 是一个 JavaScript 编译器,是一个工具链,主要用于将采用 ECMAScript 2015+ 语法编写的代码转换为向后兼容的 JavaScript 语法,以便能够运行在当前和旧版本的浏览器或其他环境中。
Babel
本质上就是在操作 AST
来完成代码的转译。AST是抽象语法树(Abstract Syntax Tree, AST)
Babel
的功能很纯粹,它只是一个编译器。大多数编译器的工作过程可以分为三部分:
- 解析(Parse) :将源代码转换成更加抽象的表示方法(例如抽象语法树)。包括词法分析和语法分析。词法分析主要把字符流源代码(Char Stream)转换成令牌流( Token Stream),语法分析主要是将令牌流转换成抽象语法树(Abstract Syntax Tree,AST)。
- 转换(Transform) :通过 Babel 的插件能力,对(抽象语法树)做一些特殊处理,将高版本语法的 AST 转换成支持低版本语法的 AST。让它符合编译器的期望,当然在此过程中也可以对 AST 的 Node 节点进行优化操作,比如添加、更新以及移除节点等。
- 生成(Generate) :将 AST 转换成字符串形式的低版本代码,同时也能创建 Source Map 映射。
经过这三个阶段,代码就被 Babel
转译成功了。
16. 项目中koa的话会把前端路由地址管理起来吗?
17. jwt和SSO的授权方式有什么区别吗?
JWT(JSON Web Token)和 SSO(Single Sign-On)都是常见的授权方式,它们在实现方式和应用场景上有一些区别。
JWT 是一种基于令牌(Token)的授权方式。它使用 JSON 格式将用户的身份信息进行加密并生成一个令牌,在每次请求中将该令牌发送给服务器进行验证。JWT 通常包含了用户的身份信息和其他附加信息,通过签名来确保令牌的完整性和真实性。客户端保存令牌,并在每次请求时将其放在请求头中或者作为参数传递给服务器。
SSO 是一种单点登录的授权方式,旨在减少用户在多个应用程序之间重复登录的问题。当用户登录成功后,SSO 系统会生成一个全局的凭证,将该凭证传递给其他关联的应用程序,在后续登录过程中,用户无需再次输入凭证即可直接访问其他应用程序。
下面是 JWT 和 SSO 的区别:
-
数据存储方式:JWT 将用户的身份信息加密并存储在令牌中,可以在客户端保存。而 SSO 的凭证通常存储在服务器端的共享存储中,如数据库、缓存等。
-
安全性:JWT 使用签名来验证令牌的真实性,确保令牌在传输过程中不被篡改。而 SSO 使用单一的凭证来实现登录,这要求 SSO 系统本身的安全性非常重要。
-
应用场景:JWT 适用于无状态的分布式系统,每个应用程序都可以独立验证令牌的有效性,无需额外的网络调用。SSO 主要用于多个关联应用程序之间的登录共享,用户只需登录一次,即可访问所有相关应用程序。
-
生命周期管理:JWT 的生命周期由令牌的过期时间和签发者定义,并且客户端自行管理令牌。而 SSO 的凭证通常有一个固定的过期时间,并且需要 SSO 系统负责管理和维护。
需要根据具体场景和需求选择适合的授权方式,JWT 更适用于分布式系统和 API 访问授权,而 SSO 则更适用于企业内部的应用程序集成和用户便利
18. token超时了你是怎么验证的?是放在redis里还是哪边?
19. axios请求后返回值是什么?
在使用 axios 进行请求后,返回值是一个 Promise 对象。你可以通过对该 Promise 对象进行链式调用来处理请求的返回结果。
通常情况下,axios 请求的返回值包含以下属性:
- data:服务器返回的响应数据。
- status:HTTP 状态码。
- statusText:HTTP 状态消息。
- headers:响应头信息。
- config:请求的配置信息。
- request:请求的 XMLHttpRequest 对象实例。
20. 事件循环的概率能讲一下吗?
21. css里面有一个重绘和回流的概念,你能讲一下吗?
上海 东吴金融(190 - 200/天)
1. 使用chatgpt提高开发效率,举个例子
2. HTTP和HTTPS的区别
-
http 是超文本传输协议,信息是明文传输,HTTPS 协议要比 http 协议
安全
,https 是具有安全性的 ssl 加密传输协议,可防止数据在传输过程中被窃取、改变,确保数据的完整性(当然这种安全性并非绝对的,对于更深入的 Web 安全问题,此处暂且不表)。 -
http 协议的
默认端口
为 80,https 的默认端口为 443。 -
http 的连接很简单,是无状态的。https 握手阶段比较
费时
,会使页面加载时间延长 50%,增加 10%~20%的耗电。 -
https
缓存
不如 http 高效,会增加数据开销。 -
Https 协议需要 ca 证书,费用较高,功能越强大的
证书费
用越高。 -
SSL 证书需要绑定
域名
。
3. 说一下强缓存和弱缓存的过程
4. 说一下git协同办公的一些指令
5. 讲一下你最近的那个项目吧?
6. 针对你的项目,你知道keep-alive的一些钩子吗?
- 两个生命周期 activated/deactivated,用来得知当前组件是否处于活跃状态。
7. 对称加密和非对称加密的区别?
对称加密和非对称加密是两种常见的加密算法,它们的主要区别在于加密和解密所使用的密钥是否相同。
-
对称加密:
-
对称加密算法使用相同的密钥进行加密和解密。即,发送方和接收方都需要知道相同的密钥才能正常地进行加密和解密。
-
这种加密方式的优点在于加解密速度快,适合对大量数据进行加密和解密。
-
但是,对称加密算法的安全性较低。因为发送方和接收方都需要知道相同的密钥,如果密钥被泄露,那么加密的数据也就不再安全。
-
-
非对称加密:
-
非对称加密算法使用一对密钥进行加密和解密,包括公钥和私钥。发送方使用接收方的公钥进行加密,接收方使用自己的私钥进行解密。
-
这种加密方式的优点在于密钥的安全性更高,因为只有接收方知道自己的私钥,没有其他人能够解密密文。
-
但是,非对称加密算法的加密和解密速度较慢,适合对少量数据进行加解密。
-
因此,应根据具体的场景和需求来选择合适的加密方式。在实际应用中,也可以将对称加密和非对称加密结合起来使用,以达到更好的安全性和性能表现。
8. 小程序和h5有什么区别?
-
开发技术和环境:小程序通常使用微信开发工具进行开发,采用的是微信自定义的开发语言和框架,如微信小程序开发框架、WXML、WXSS等。而H5使用HTML、CSS和JavaScript标准的Web开发技术进行开发,并在移动浏览器中运行。
-
用户获取渠道:小程序通过微信内置的小程序商店(应用市场)进行分发,用户可以通过搜索、扫描二维码等方式获得并安装小程序。而H5可以通过在移动浏览器中输入网址或点击链接来访问。
-
功能限制:小程序相对于H5有一定的功能限制。它的能力受到微信开放的接口和组件的限制,无法直接访问设备的底层功能(如摄像头、指纹识别等),但可以通过微信提供的API来实现一些特定功能。相比之下,H5可以通过浏览器提供的API和插件来获取更多底层功能,并具有更好的兼容性。
-
用户体验:小程序在用户体验上更接近原生应用,可以提供更顺畅、流畅的交互体验,且打开速度较快。而H5在用户体验方面受限于浏览器性能和网络环境,可能存在加载速度较慢、交互体验不如原生应用的情况。
-
更新和分发:小程序的更新相对便捷,无需用户手动更新,开发者可以灵活地发布和更新小程序版本。而H5的更新需要用户重新访问页面或刷新页面才能获取最新版本。
9. 小程序里面有没有DOM或BOM操作?
小程序中没有DOM(Document Object Model)和BOM(Browser Object Model)的操作,因为它不是基于Web的技术。相反,小程序提供了一组特定的API来实现与页面交互的功能。
小程序的核心使用了一个叫做WXML(WeiXin Markup Language)的标记语言,类似于HTML。但是,它与HTML不同,WXML只是一种描述页面结构的语言,而不包括与页面样式或行为相关的内容。
小程序中提供了一些组件和API来实现与页面交互的功能。例如:
- 组件:小程序提供了一些内置的基础组件和扩展组件,比如按钮组件、输入框组件、列表组件等,可以通过WXML标签添加到页面中,并通过WXSS样式文件进行布局和样式控制。
- API:小程序提供了一套API,开发者可以使用它们来实现各种功能,例如数据存储、网络请求、音视频播放、地理位置获取等。常用的API有wx.request、wx.navigateTo、wx.getStorage等。
10. 你所了解的前端优化的方法?
11. 什么时候用服务端渲染?什么时候用客户端渲染?
服务端渲染(Server-Side Rendering,SSR)和客户端渲染(Client-Side Rendering,CSR)是两种不同的页面渲染方式,它们适用于不同的场景。
-
服务端渲染(SSR):
-
当页面内容在服务器端能够完全生成时,可以选择使用服务端渲染。这种方式将在服务器上生成HTML代码,并将其发送给浏览器进行展示。用户在浏览器上访问时会首先收到已经渲染好的HTML页面,因此可以更快地呈现页面内容。
-
适用于对搜索引擎优化(SEO)要求较高的网站。搜索引擎爬虫可以直接获取到完整的HTML页面内容。
-
适用于对初始加载速度较为敏感的场景。对于一些内容较多、复杂的页面,服务端渲染可以提供更快的初始加载体验。
-
-
客户端渲染(CSR):
-
当页面内容需要通过与服务器或API交互后再进行渲染时,可以选择使用客户端渲染。这种方式将在浏览器端使用JavaScript动态地生成并更新页面内容。
-
适用于需要较为复杂的交互和动态变化的页面。例如,单页应用(Single-Page Application,SPA)通常采用客户端渲染,可以实现流畅的页面切换和交互效果。
-
适用于较为简单的静态页面或对初始加载速度要求不高的场景。对于一些内容较少、交互较简单的页面,客户端渲染可以提供更好的灵活性。
-