面试速通

文章发布时间:

最后更新时间:

面试问题集合 https://fe-interview.pangcy.cn/docs/engineering/vite/vite-06/ ## Todo - 函数装饰器 ## function和箭头函数区别 箭头函数定义时根据上下文确定this,适用于回调函数 function适用于对象的方法

防抖节流

防抖在连续的事件,只需触发一次回调的场景有:搜索框搜索输入。只需用户最后一次输入完,再发送请求,事件之后延迟n ms,看看还有没有事件 节流:在间隔一段时间执行一次回调的场景

函数压缩

问题: 为什么compose2不行

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
let compose = (...fns) => {
let res = (...args) => args;
for (let fn of fns) {
res = (function(fn, res) {
return (...args) => {
return fn(res(...args));
};
})(fn, res);
}
return res;
}

let compose2 = (...fns) => {
let res = (...args) => args;
for (let fn of fns) {
res = (...args) => {
return fn(res(...args));
};
}
return res;
}

/*
let compose2 = (...fns) => {

  let res = (...args) => args;

  for (let fn of fns) {

    let fnn = fn, ress = res;

    res = (...args) => {

        return fnn(ress(...args));

    };

  }

  return res;

}
*/

let a = (str) => str + 'a';
let b = (str) => str + 'b';
let c = (str) => str + 'c';
let d = (str) => str + 'd';
let e = compose2(a, b, c, d);
console.log(e);
console.log(e("begin"));

js number范围

在 JavaScript 中,数字(Number)类型是基于 IEEE 754 标准的双精度 64 位浮点数。这意味着 JavaScript 中的数字可以表示非常大的范围,但有一个最大安全整数值。

跨域解决办法

CORS

浏览器会阻止这种请求, 当浏览器检测到跨域请求时,会先发送一个 OPTIONS 请求(预检请求)到目标服务器, 服务器需要在响应头中返回 Access-Control-Allow-Origin 等 CORS 相关头信息,以告知浏览器是否允许该请求。 ### jsonp jsonp的原理就是通过<script> 标签绕过浏览器的同源策略。服务器返回的数据被包装在一个回调函数中(例如 callback({"data": "value"})),客户端通过定义好的回调函数处理数据。 容易受到 XSS(跨站脚本攻击)

nginx

  • 增加cors相关
  • 进行反向代理(把 http://front_server/api 转到 http://backend_server)
    • 正向代理:代理客户端,向服务器发送请求,隐藏客户端身份(如 VPN)。
    • 反向代理:代理后端服务器,接收客户端请求并转发,隐藏后端服务器。

部署

先来说下前端项目的部署,一般来说有以下几个步骤:项目打包,上传到服务器,域名解析,SSL 证书,申请Nginx ,配置CDN 加速。 vercel自动化部署:如果是自己做一些小项目,再也不用每次修改代码之后还要打包上传到服务器了,只需要把代码提交到仓库,Vercel 会自动触发部署,部署完成之后再通知你,这体验真的是无比丝滑。

http缓存

在 HTTP Caching 标准中,有两种不同类型的缓存:私有缓存(存在客户端)和共享缓存(共享缓存位于客户端和服务器之间)。

响应age

1
Cache-Control: max-age=604800

过时的缓存不会立即被丢弃。HTTP 有一种机制,可以通过询问源服务器这个缓存是否真的过期。这称为验证,有时也称为重新验证

1
If-Modified-Since: 最近修改日期(服务器上次响应的 Last-Modified头部)

文档没被修改过,条件就为假,服务端会返回一个 304 NotModified 响应报文

1
ETag: 版本标识符

重写,修改不重要,or 在毫秒级间隙发生变化(if modified since不够用)

网络攻击 XSS and CSRF

XSS: 注入脚本,让受害者浏览器执行,来窃取cookie - 非持久型 XSS(反射型 XSS)诱骗点击url - 持久型 XSS 漏洞,一般存在于 Form 表单提交等交互功能,如文章留言,提交文本信息等,黑客利用的 XSS 漏洞,将内容经正常功能提交进入数据库持久保存

CSRF:诱导受害者发送伪造的请求到目标网站,利用受害者的身份(cookie)执行未经授权的操作。(目标网站的服务器也被篡改)

解决办法: - xxs 可以设置csp,让代码不能执行 - xxs 可以转义字符 - CSRF 攻击依赖于伪造用户身份发送请求,但攻击者无法获取受害者的 CSRF Token(因为它存储在会话中或受同源策略保护)。 - cookie标记samesite,跨域请求不发送cookie - 敏感信息使用 httponly cookie (xss) - Cookie 是存储在用户浏览器端的小段数据,用于跟踪用户会话等信息。而 HttpOnly 是 Cookie 的一个属性。 - 当设置为 HttpOnly 时,该 Cookie 只能通过 HTTP 或 HTTPS 协议进行访问,不能被客户端脚本(如 JavaScript)访问。这有助于防止一些跨站脚本攻击(XSS)。因为如果 Cookie 被恶意脚本访问到,攻击者可能会窃取用户的会话信息等敏感数据。 - 不要设置Access-Control-Allow-Origin=*

事件委托

dom元素的事件自动冒泡 动态生成的元素(如列表);减少内存占用和提高性能;统一处理相似元素的事件

浅拷贝深拷贝分别怎么实现

浅拷贝用展开运算符(...) 深拷贝用structuredClone() JSON.stringify实现深拷贝有什么问题:会忽略函数,date,error等对象会变成字符串,对象无法循环引用

CommonJS 和 ES6 模块系统区别

es6 异步加载,静态分析,也支持动态导入,导出值实时绑定(响应式)

ts class写法

class Person { name: string; age: number;

constructor(name: string, age: number) { this.name = name; this.age = age; }

sayHello(): void { console.log(Hello, my name is ${this.name} and I am ${this.age} years old.); } }

// 创建实例 const person = new Person('Alice', 25); person.sayHello(); // 输出: Hello, my name is Alice and I am 25 years old.

worker

new Worker('worker.js') 主程序/worker worker/self.postmessage worker/self.onmessage/onerror AddEventListener 和promise一起 ommessage->resolve onerror->reject

前面说过,主线程与 Worker 之间的通信内容,可以是文本,也可以是对象。需要注意的是,这种通信是拷贝关系,即是传值而不是传址,Worker 对通信内容的修改,不会影响到主线程。事实上,浏览器内部的运行机制是,先将通信内容串行化,然后把串行化后的字符串发给 Worker,后者再将它还原。“串行化”是指把一个对象或者数据结构转换成一个字节序列的过程,这样做的目的是为了方便存储或者传输。

slice

python [a:b] = js .slice(a, b)

内存泄漏

https://elvinn.wiki/nodejs/memory.html 1. 全局变量 2. 闭包引用 3. 事件绑定(dom移除时没有移除eventlistener,这是node?? 4. 缓存爆炸 heapdump

特性 computed watch
缓存机制 有缓存,只有依赖项变化时才会重新计算 无缓存,每次依赖项变化都会执行回调
更新机制 同步更新 异步更新
用途 用于基于现有数据派生新数据 用于监听数据变化并执行复杂逻辑
依赖响应式 自动追踪依赖项 需要手动指定依赖项

var 声明提前

这里声明了变量,js解释器“前瞻性”查找所有变量定义,把它们“提升”到函数顶部

首屏优化

懒加载

有时候我们想把某个路由下的所有组件都打包在同个异步块 (chunk) 中。在Vite中,你可以在rollupOptions下定义分块:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
// 将 import UserDetails from './views/UserDetails.vue' 
// 替换成 const UserDetails = () => import('./views/UserDetails.vue')

// vite.config.js
export default defineConfig({
build: {
rollupOptions: {
// https://rollupjs.org/guide/en/#outputmanualchunks
output: {
manualChunks: {
'group-user': [
'./src/UserDetails',
'./src/UserDashboard',
'./src/UserProfileEdit',
],
},
},
},
},
})

css和js阻塞渲染的问题

https://blog.csdn.net/qq_44318215/article/details/125392575