力扣八股文
https://zhuanlan.zhihu.com/p/346468901
https://zhuanlan.zhihu.com/p/141134693
https://blog.csdn.net/sayUonly/article/details/117520021
https://blog.csdn.net/qq_28766729/article/details/102839161
https://zhuanlan.zhihu.com/p/413440875
https://zhuanlan.zhihu.com/p/91674680
https://www.zhihu.com/question/587456887?utm_id=0
https://zhuanlan.zhihu.com/p/390394730
https://it.cha138.com/nginx/show-467347.html
其他前端相关内容见
CSS基础学习总结
HTML基础学习总结
js基础学习总结
Vue基础学习总结
H5新特性,相对于全部div,结构清晰,利于搜索引擎优化
1.绝对定位(子绝父相)
div {
// 父
position: relative;
}
div {
position: absolute;
left: 50%;
top: 50%;
transform: translate(-50%,-50%);
}
2.绝对定位:确定了当前 div 的宽度,margin 值为当前 div 宽度一半的负值。
3.绝对定位:绝对定位下 top left right bottom 都设置0 ,margin 设置为 auto
4.flex布局:
display: flex;
align-items: center; //项目在竖轴的对齐方式
justify-content: center; //主轴上的对齐方式
5.table-cell 实现水平垂直居中:table-cell middle center 组合使用
6.绝对定位:calc() 函数动态计算实现水平垂直居中
opacity:0; 继续占据空间,内容不可见。如果该元素已经绑定事件,点击也能触发点击事件。
visibility:hidden; 继续占据空间,内容不可见 ;但是不会触发该元素已经绑定的事件
display:none ; 不占据任何空间(v-show)
1.flex布局(弹性布局)
2.rem布局(移动端)
3.百分比布局(用的少)
4.浮动布局(用的少)
伪类在dom树,伪元素不在。
其他内容见CSS基础学习总结
href,表示超文本引用。用来建立当前元素和文档之间的链接。src 指向的内容会嵌入(下载)到文档中当前标签所在的位置(src 用于替换当前元素)。
title: 鼠标滑动到元素上的时候显示
alt: 图片无法加载时显示
(在pc调移动端时,由于浏览器内核限制,可能导致某些像素无法显示,但到移动端就好了)
其他内容见
js基础学习总结
let a = Symbol("11");
let b = Symbol("11");
console.log(a==b); // false
console.log(a===b); // false
console.log(a.description === b.description); // true
判空代码
// 普通判空
if (obj === undefined || obj === null || obj === '') {
}
等价于
if(!obj)
// 对象判空
if(JSON.stringify(obj) === '{}') {
}
// 数组判空
if(JSON.stringify(obj) === '[]') {
}
一个函数A,作为另一个函数B的参数,那么函数A就被称为回调函数。回调函数A就是一个普普通通的函数,它被其他函数B作为参数在B的内部调用,那么在这个时候A才能被称为B的回调函数**。回调函数这个概念是相互的,一个单独的函数是无法叫做回调函数的**,它只能被称为XXX(被谁在内部调用)的回调函数。
ES6出现之前,这种代码可以说是随处可见。它虽然解决了异步执行的问题,可随之而来的是我们常听说的回调地狱问题:没有顺序可言:嵌套函数执行带来的是调试困难,不利于维护与阅读;耦合性太强:一旦某一个嵌套层级有改动,就会影响整个回调的执行
ES6异步编程的一种解决方案,比传统的方案(回调函数和事件)更加的合理和强大,可以解决回调地狱问题。
案例1:
let promise = new Promise((resolve, reject) => {
// do something
if (true) {
// 将参数返回,供then方法使用
resolve("value");
} else {
// 将参数返回,供then方法使用
reject("error");
}
});
// Promise实例生成以后,可以用then方法分别指定resolved状态和rejected状态的回调函数。
promise.then(
value => {
// resolved时调用,value为resolve函数返回的参数
console.log(value);
},
err => {
// rejected时调用,err为reject函数返回的参数
console.log(err);
}
);
// 当then方法只有一个函数参数时,此时为resolved状态的回调方法
promise.then(value => {
// 只有状态为resolved时才能调用,如果返回的是rejected状态,则报错 Uncaught (in promise) error
console.log(value);
});
案例2:
// 从 买笔 -> 写作业 -> 交作业 三个异步状态,都需要依赖上一步的结果才能执行
// 如果单纯在 ajax 异步回调里又做异步,就会形成回调地狱,看看 promise 是如何解决回调地狱的问题
// 买笔
function buy(){
console.log("开始买笔");
return new Promise( (resolve,reject) => {
$.ajax({
url: 'xxx.com',
data: {name:'krry'},
success: res => {
console.log('买了笔芯');
resolve(res); // 成功
},
error: (err) => {
reject(err); // 失败
}
});
});
}
// 写作业
function work(data){
console.log("开始写作业:" + data);
return new Promise( (resolve,reject) => {
$.ajax({
url: 'xxx.com',
data: {name:'krry'},
success: res => {
console.log('写完搞定');
resolve(res); // 成功
},
error: (err) => {
reject(err); // 失败
}
});
});
}
// 交作业
function out(data){
console.log("开始上交:" + data);
return new Promise( (resolve,reject) => {
$.ajax({
url: 'xxx.com',
data: {name:'krry'},
success: res => {
console.log('上交完成');
resolve(res); // 成功
},
error: (err) => {
reject(err); // 失败
}
});
});
}
// 调用异步的时候,如此简单,优雅地解决了回调地狱的问题
// 调用每一个方法的时候自动将参数放进去了
// 这里调用的是成功的回调
buy().then(work).then(out).then( data => {
console.log(data);
});
// 上面的写法等同于这种写法:还是没有上面的简洁,推荐上面写法
buy().then(res => work(res)).then(res => out(res)).then( data => {
console.log(data);
});
// 考虑失败的回调
buy().then( work, err => {
console.log('买笔失败啦' + err);
}).then( out, err => {
console.log('作业太难,写不了')
}).then( data => {
console.log(data);
});
案例3:体现promise异步(顺便体现setTimeOut)
setTimeout(() => {
console.log(7) // 宏任务
}, 0)
new Promise((resolve, reject) => {
console.log(3); // 主线程
resolve();
console.log(4); // 主线程
}).then(() => {
console.log(6) // 回调(微任务)
})
console.log(5) // 主线程
// 执行结果3,4,5,6,7
1.async为异步标识,标识在该函数内可以使用await
2.async返回的是promise,await可以阻塞,并解promise的result
javascript是一门单线程语言:单线程的特性,与它的用途有关,作为浏览器脚本语言,JavaScript的主要用途是互动和操作DOM。为了利用多核CPU的计算能力,HTML5提出Web Worker标准,允许JavaScript脚本创建多个线程,但是子线程完全受主线程控制,且不得操作DOM(故HTML5提出Web Worker标准后,我理解JS的单线程应该叫DOM操作单线程)。所以,这个新标准并没有改变JavaScript单线程的本质。
Event Loop是javascript的执行机制:图中,主线程运行的时候,产生堆和栈,栈中的代码调用各种外部API,异步操作执行完成后,就在消息队列中排队。只要栈中的代码执行完毕,主线程就会去读取消息队列,依次执行那些异步任务所对应的回调函数。
同一次事件循环中,微任务永远在宏任务之前执行。
宏任务macrotask: script(整体代码), setTimeout, setInterval, setImmediate, I/O, UI rendering
微任务microtask: process.nextTick, Promise, MutationObserver
1.防抖:只执行最后一次。n 秒内函数只会执行一次,若在 n 秒内被重复触发,则重新计时。
常见场景:下拉框模糊搜索、手机号/邮箱格式的输入验证检测、登录等按钮避免用户快速点击产生两笔交易(两次请求)…
function debounce(fn, delayTime) {
let timer = null;
return function() {
if (timer !== null) { // 这个if不写也行,===null了相当于清了
clearTimeout(timer) // 清除掉定时任务
}
let context = this
let args = arguments
timer = setTimeout(() => {
fn.apply(context, args)
timer = null
}, delayTime)
}
}
2.节流。一次次间隔执行。n 秒内只运行一次,若在 n 秒内重复触发,只执行一次。
常见场景:下拉框模糊搜索、监听滚动事件(懒加载)…
// fn为回掉业务逻辑,delayTime为延迟时间
function throttle(fn, delayTime) {
let time = null // 闭包产生的私有属性,产生私有数据
// let usedFlag = 1 // usedFlag用来测试当前节流是否生效
return function() { // fun() 套一个 return fun()闭包写法
if(time !== null) { return } // n 秒内只运行一次
// console.log('usedFlag', usedFlag)
let context = this // 获取上下文(看似不体现作用)
let args = arguments // 传参
// fn.apply(context, args) // 写在外面运行是(业务->[间隔]->业务)
// usedFlag = usedFlag + 1
time = setTimeout(() = > {
fn.apply(context, args) // 写在里面运行是([间隔]->业务->[间隔])
time = null // 到时间清空定时器,关键操作
}, delayTime) // 延迟时间设置
}
}
window.addEventListener('scroll', this.handleScroll)
handleScroll: throttle(function () {
// 全部有浏览器内核适配问题
// 网页被卷起来的高度(即浏览器滚动条滚动后隐藏的页面内容高度),初始值是0,它是一个变化的值
document.documentElement.scrollTop
// 视口高度
document.documentElement.clientHeight
// 页面不能滚动时是不存在的,body长度超过window时才会出现,所表示body所有元素的长度
document.documentElement.scrollHeight
// 某一dom元素的高度
document.getElementById('idXXX').offsetTop
// 触底公式
if(scrollTop + clientHeight >= scrollHeight) {
// 触底
}
}, 1000)
JS的继承思想设计(模仿java子类继承父类共有),产生原型与原型链。
比js更像java,包括class、注解符号、private等等
1.递归
2.ES6 的 flat 方法
3.JSON.stringify()转成字符串,用正则替换掉括号,再用JSON.parse()转回数据
堆栈,和java一样
深拷贝JSON.parse(JSON.stringify())
arr.map()返回的是数组(给数组做处理)
arr.reduce()返回的是一个数(累加)
arr.forEach()遍历数组,所以想做操作得外面建个变量接它
细节见计算机网络基础复习总结、2022秋招面经总结(补充前面文章中不含的内容)计算机网络部分
DNS解析得到IP地址(网络层IP)
建立TCP连接(传输层,三次握手)
发送HTTP请求(应用层协议,传输层的协议TCP或UDP加上端口就可以标识一个应用层协议;常见POST/GET)(涉及HTTP缓存)
HTTP报文是包裹在TCP报文中发送的,服务器端收到TCP报文时会解包提取出HTTP报文。体现请求响应7层模型从顶到底加协议再从底到顶解封。
服务器处理请求,然后返回HTTP报文。
请求行、请求头、请求报文 => http请求报文
状态码、响应头、响应报文 = > http响应报文
浏览器接收到响应后,显示渲染页面
HTML是一种超文本标记性语言,HTML在经过浏览器编译以后在内存是以一种树形结构存在着,这个树也被称为DOM树(document object model)。将HTML或XML文档转化为DOM树的过程称为解析(parse)。DOM树叫文档对象模型。
客户端和服务器通过四次挥手终止 TCP 连接。
Reflow:当 DOM 的变化影响了元素的几何信息,浏览器需要重新计算元素的几何属性,将其安放在界面中的正确位置。表现为重新生成布局,重新排列元素。
Repaint: 当一个元素的外观发生改变,但没有改变布局,重新把元素外观绘制出来的过程。表现为某些元素的外观被改变。
谷歌浏览器开发者工具的network的Disable cache,勾选时会禁用浏览器缓存。这里的缓存是指http缓存,而不是cookie、storage。浏览器每次发起请求,都会先在浏览器缓存中查找该请求的结果以及缓存标识。
不存在该缓存结果和缓存标识,强制缓存失效,则直接向服务器发起请求(跟第一次发起请求一致);存在该缓存结果和缓存标识,但该结果已失效,强制缓存失效,则使用协商缓存;存在该缓存结果和缓存标识,且该结果尚未失效,强制缓存生效,直接返回该结果。
Cache-Control 和 Expires(HTTP/1)。network里找请求看,当浏览器对某个资源的请求命中了强缓存时,返回的http状态为200,在chrome的开发者工具的network里面size会显示为from cache
协商缓存生效,返回 304;协商缓存失效,返回 200 和请求结果结果
Last-Modified,If-Modified-Since。ETag、If-None-Match。
静态资源下载、接口请求等看瀑布
纯js代码逻辑可以console.time(‘flag’)与console.timeEnd(‘flag’),这两个方法均使用一个参数,参数值可以为任何字符串,但是这两个方法所使用的参数字符串必须相同,才能正确地统计出开始时间与结束时间之间所经过的毫秒数。
单页面应用(single page web application,SPA),就是只有一张Web页面的应用,是加载单个HTML 页面(如vue打包后dist里只有一个index.html)并在用户与应用程序交互时动态更新该页面的Web应用程序。
构建 SPA,需要引入前端路由系统(如vue中的Vue-Router)。前端路由的核心在于改变视图的同时不会向后端发出请求。
hash模式路由(vue-router 默认使用 hash 模式):
history模式路由:
AJAX不是编程语言,而是一门提供网页局部刷新的技术。AJAX最大的优点是在不重新加载整个页面的情况下,与服务器交换数据并更新部分网页内容。XML是一种古老的数据交互格式,目前多数情况下会使用JSON数据格式替换XML数据格式,所以AJAX可以看做是异步JavaScript和JSON形式。
js中:var xhr = new XMLHttpRequest();
作者:LeetCode
链接:https://leetcode.cn/leetbook/read/2023-ming-qi-qian-duan-mian-shi-kao-dian/wb1ig7/
来源:力扣(LeetCode)
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
webpack网站
At its core, webpack is a static module bundler for modern JavaScript applications. When webpack processes your application, it internally builds a dependency graph from one or more entry points and then combines every module your project needs into one or more bundles, which are static assets to serve your content from.
参考:
https://www.cnblogs.com/jacksplwxy/p/11495700.html
参考(更详细):https://blog.csdn.net/qq_40772692/article/details/124988974
前端一定要懂后端基础,某些业务逻辑落在哪一端做才可以讨论清楚
解决方案:章节锚点(定位) + 上拉滚动监听(优化按需渲染压力、按需发送请求压力)+ 节流(优化滚动监听频率)+ 异步组件懒加载(优化按需渲染压力、按需发送请求压力)+ 章节锚点flag数组(避免重复发送请求)
echarts / g2plot 画图:1.id重复画图问题。2.g2plot更新数据要调用更新数据的方法,echarts更新数据要重置配置里的data。3.实时更新数据用watch就行。
数据制作成展示结构:.map方法数组筛选出数组、三个点…拆装箱、固定自定义数据结构(页面多个模块显示内容是调用不同接口得到数据,且包含列表、echarts、直接显示等多种展示方式,给每个某块设计一个独立的vue data属性,即独立的数据结构对象)。注意let temp = { a:[] }初始化列表。直接属性temp.b = 3可以,列表temp.a.push()必须初始化了a才行。
webworker:该需求js数据计算的量级不大,单次处理不到100条数据,所以没用webworker
后续将持续更新…