- 博客(41)
- 收藏
- 关注
原创 谈谈对传输层协议TCP的理解
TCP(Transmission Control Protocol,传输控制协议)是 TCP/IP 协议簇中传输层的核心协议,专为实现可靠、有序、面向连接的端到端数据传输设计,广泛应用于对数据完整性要求高的场景(如 HTTP、FTP、SMTP 等应用层协议均基于 TCP)。下面从核心特性、工作原理、关键机制三方面详细拆解。
2025-12-21 13:25:46
1274
1
原创 HTTP一些问题的解答(接上篇)
HTTP/1.x在弱网环境下可能比HTTP/2表现更好的原因在于其多连接策略能规避TCP队头阻塞问题。HTTP/2的多路复用机制虽然高效,但在高丢包率环境下,单个TCP连接的数据包丢失会阻塞所有请求,而HTTP/1.x的多个独立连接可将丢包影响限制在单个请求内。此外,HTTP/2的复杂特性(如头部压缩和流优先级)在弱网中可能适得其反,而HTTP/1.x的简单结构更稳健。HTTP/2并非强制单连接,但推荐单连接以实现最佳性能,仅在特殊情况下使用多连接。其多路复用通过二进制帧、流标识和单连接共享实现请求并行处理
2025-12-14 12:59:02
846
原创 谈谈我对HTTP的理解
HTTP是互联网基础协议,采用"请求-响应"无状态模式。主要版本演进包括:HTTP/0.9(纯文本)、HTTP/1.0(引入头信息)、HTTP/1.1(持久连接/缓存)、HTTP/2(二进制帧/多路复用)、HTTP/3(基于QUIC)。通信包含请求报文(方法/路径/头)和响应报文(状态码/数据),支持HTTPS加密。应用场景涵盖网页浏览、API交互、文件传输等。协议发展持续优化性能、安全性和扩展性,是Web开发的核心基础。
2025-12-14 12:50:56
2809
原创 WebSocket客户端封装类
关于WebSocket的基础概念在上一篇文章中已经详细说明,本文不再赘述。接下来我们将重点实现一个具备心跳检测和断线重连功能的WebSocket封装类。
2025-12-07 13:43:29
262
原创 基于TCP全双工特性,HTTP、SSE与WebSocket通信模式差异解析
本文探讨了基于TCP协议的HTTP、SSE和WebSocket三种应用层协议在通信模式上的差异。虽然TCP本身具备全双工特性,但不同应用层协议对其能力的调用方式各不相同:HTTP采用"请求-响应"的半双工模式,SSE实现服务端单向推送的增强型半双工,而WebSocket则充分利用TCP全双工能力实现双向实时通信。这些差异源于各自适配的业务场景需求:HTTP满足通用请求-响应场景,SSE针对单向实时推送需求,WebSocket则专为双向实时交互设计。
2025-12-07 13:03:21
1036
1
原创 一个有趣的题
本文通过一个CSS Flexbox布局案例揭示了AI工具在计算元素高度时的常见错误。案例中一个600px高的父容器包含三个子元素(header:200px、content:100%、footer:200px),实际渲染结果却是header/footer各120px,content360px。原因在于:1)百分比高度会解析为父容器绝对高度(content初始为600px);2)Flex布局需按基准尺寸比例收缩(总基准1000px需收缩400px);3)content按600/1000比例收缩240px
2025-11-30 14:48:30
485
原创 谈谈最近学习的低延迟直播系统的一些收获
协议选型无优劣,适配场景是关键:互动场景选 WebRTC,低延迟直播选 SRT/RTMP,跨平台兼容选 LL-HLS;开源工具的力量:SRS 这类成熟框架节省了底层开发成本,聚焦业务逻辑即可快速落地;实践出真知:从手动封装组件到踩坑 SRS 配置,每一步试错都加深了对直播技术栈的理解。目前已实现 OBS(WebRTC)推流、前端 / VLC 拉流的低延迟直播,后续计划探索 SRT 协议集成、高并发优化。万事开头难,技术沉淀在于持续踩坑与复盘。
2025-11-23 10:42:26
767
原创 原生js+canvas+HTML+css写的一个视频弹幕系统(附源代码)
还有文字描边的粗细、弹幕的随机位置范围(避免超出视频区域),都得调好几次才自然。会发现满屏的弹幕也不会卡,就是在点击暂停后,由于弹幕是静态的,没有运行的时间,会有问题,跟后端结合的话,就没有这个问题。弹幕本质是在视频上方盖了一层 Canvas,所有文字都画在 Canvas 上,这样既能保证性能,又能灵活控制动画。如果每次发弹幕都新建对象、消失后就删除,大量弹幕时会导致内存抖动。本来以为弹幕很简单,真写起来才发现细节不少:比如 Canvas 尺寸要跟着视频实时变(用。
2025-10-19 11:42:33
294
原创 带你深入了解webworker
WebWorker是HTML5引入的多线程技术,解决了JavaScript单线程阻塞问题。它允许创建后台线程(Dedicated/Shared/Service Worker)处理耗时任务,通过消息机制与主线程通信,避免UI卡顿。关键特性包括独立运行、消息传递通信,但受限不能访问DOM且需同源。实战案例展示了复杂计算和跨页面数据共享的应用,并提供了Transferable Objects等优化技巧。WebWorker适用于大数据处理、复杂计算等场景,有效提升前端性能,但需注意创建开销和内存管理。
2025-10-12 09:25:36
999
原创 从切片、断点续传到实时进度监控(附完整代码)
本文介绍了一套基于前端技术栈的大文件上传方案,解决了传统上传方式的核心痛点。该方案采用React+WebWorker+IndexedDB+WebSocket技术组合,支持切片上传、断点续传和实时进度同步。 方案的技术选型包括: 使用WebWorker在子线程处理文件切片,避免主线程阻塞 通过IndexedDB本地存储分片数据,实现断点续传 利用WebSocket进行实时进度同步 采用分片上传减轻服务器压力 核心实现分为四个部分: WebWorker处理大文件切片 IndexedDB存储分片数据 WebSoc
2025-10-05 09:01:16
660
1
原创 关于全局变量和局部变量重复的问题
本文分享了一个由变量覆盖引发的bug案例。作者在修改代码时,将局部变量命名为与全局响应式变量相同的"scrollTop",导致全局变量被覆盖。由于局部变量是普通数值而非响应式对象,访问其value属性返回undefined,造成NaN比较结果,使条件判断失效。这个案例警示开发者要注意避免变量命名冲突,特别是在使用响应式数据时,要注意区分普通变量和响应式对象的命名。
2025-09-22 09:27:16
185
原创 二次封装axios(token无感刷新)
本文介绍了JWT令牌无感刷新的实现方案。通过区分短token(AccessToken)和长token(RefreshToken)实现安全性与用户体验的平衡:短token用于接口授权(有效期短),长token用于静默刷新短token(有效期长)。核心实现原理包括:自动检测token过期、使用RefreshToken刷新、重试请求队列管理。文章提供了基于axios的代码示例,包含请求拦截、响应拦截、刷新逻辑和异常处理。该方案可避免用户因token过期被迫重新登录,显著提升操作体验。
2025-09-21 10:31:01
317
原创 虚拟列表(不定高度)
本文介绍了一种动态高度虚拟列表的实现方案。核心思路是:1)初始化时使用预估高度(itemSize)计算每个元素位置;2)滚动时通过二分查找确定可视区域起始索引;3)在组件更新后获取元素实际高度,修正位置数组;4)通过transform实现滚动偏移。关键优化包括:缓冲区域渲染(buffer)、requestAnimationFrame优化重绘、防抖处理滚动事件。代码实现包含容器高度计算、位置信息维护、动态高度更新等逻辑,有效解决了长列表渲染性能问题。
2025-09-14 11:41:31
194
原创 浅谈虚拟列表(固定高度)
虚拟列表优化长列表性能 虚拟列表通过仅渲染可视区域内的元素,大幅减少DOM节点数量,解决长列表的卡顿问题。其核心原理包括:计算可见范围(start/end索引)、动态偏移量(offset)和缓冲渲染(buffer)。适用于大数据表格、聊天记录等场景。 Vue实现要点: 基于scrollTop动态计算起止索引 使用transform: translateY实现滚动偏移 通过插槽支持自定义项渲染 添加触底加载(reachEnd)和滚动定位(scrollToIndex)功能 优化建议:增加节流处理、空状态处理,并
2025-09-07 11:38:20
253
原创 Vue组件(Vue2)
Vue组件(Vue2)1、组件传值(通信)的方式?2、父组件如何直接修改子组件的值?3、子组件如何直接修改父组件的值4、如何找到父组件与根组件?5、slot
2025-07-08 16:13:07
451
原创 Vue的生命周期(Vue2)
vue的生命周期有beforeCreate、created、beforeMount、mounted、beforeUpdate、updated、beforeDestroy、destroyed。(八个)再加入keep-live时生命周期会多两个actived和deactived(十个)
2025-07-07 13:59:08
478
原创 条件渲染 v-show与v-if
v-show是通过控制css的display元素也决定元素是否要显示,而v-if则是完全销毁与重建该元素及其子元素,当v-if条件为true时则渲染该元素并将其留在dom中,当条件为false时则将其元素及其子元素从dom中移除。只有当首次条件为true时才会渲染条件块。v-if可以使用在那些不需要频繁改变状态的情境下,如用户的权限,平台区分等,需要在template上使用条件渲染,包装多个元素时,v-show适用与那些需要频繁切换显示状态的场景下,比如对话框,提示信息等。4、支持的功能也有所不同。
2025-07-06 20:29:57
325
原创 JavaScript原型,原型链。
JavaScript通过原型链实现继承机制。每个对象都有[[Prototype]]属性指向其原型对象,当访问属性时会沿着原型链向上查找。构造函数通过prototype属性共享方法和属性。实例对象的__proto__指向构造函数的prototype,形成原型链关系。例如,Man继承Person时,Man.prototype=new Person(),使Man实例可以访问Person的属性和方法。原型链最终指向Object.prototype直至null。这种机制实现了属性和方法的继承与共享。
2025-06-12 20:47:22
484
原创 typeof和instanceof的区别
操作符的返回值是一个字符串,表示未经计算的操作数的类型。无法判断(这是JavaScript的一个历史遗留问题)。可以准确判断复杂的引用数据类型,但无法判断基本数据类型。属性是否出现在某个实例对象的原型链上。判断一个对象是否存在可以使用。等引用数据类型(这些都返回。,因为若变量未声明会报错。是可以赋值的,因此也不能用。只能判断基本数据类型,但。除了基本数据类型外,返回变量的基本类型,和复杂引用数据类型(
2025-06-10 23:12:19
342
原创 JavaScript中==和===的区别,以及应用场景
true转换为1false转换为0。简单类型与引用类型比较时,对象会转换为原始类型的值再比较。两个操作数均为引用类型时,比较它们的指向。null和undefined相等。若存在NaN,则返回false。
2025-06-09 22:29:54
295
原创 浅谈JavaScript中的数据类型
对于基本数据类型它存储在栈中,变量赋值时随然两个变量的值的相等但是两个变量还是保存了不同的地址。他们之间的复制时将栈内存的地址复制一份给两一个对象,但是他们共同指向一个堆内存对象,更改任意一个对象的值都会对其产生影响。JavaScript 的数据类型分为原始类型和引用类型,原始类型不可变,引用类型可变。引用数据类型存放在堆中,每个堆内存对象都有对应的引用地址指向它,引用地址存放在栈中。原始类型是按值访问的,而引用类型是按引用访问的。基本数据类型存储在栈中,引用数据类型存储在堆中。
2025-06-01 20:10:31
883
2
原创 元素水平居中的方法有哪些?
父级设置相对定位,子级绝对定位,并且四个属性都设置0,这时候如果子级没有设置宽高,则会被拉开和父级一样的的宽高。但是这里会发现我们设置了宽高,所以会按照我们的设置来显示,但是实际上子级的虚拟占位已经撑满了整个父级盒子,在给他一个margin:auto变居中了这里会发现子级已经铺满了整个父级。css3中的flex和grid布局可以非常简单的实现水平居中并且两者的使用方法完全一样。这种的需要子元素的宽高,也可以用transform来完成两者的效果是完全一样的。可以让所有的行内块级元素居中。
2025-06-01 18:11:32
283
原创 Redis应用中的常见面试题(之前写的忘发布了,我嘞个豆儿)
因此我在项目中用的是redisson中提供的分布式锁提供方案它题供了过期时间的刷新机制,当发现业务没有执行完的时候会刷新过期时间,这个机制主要是通过看门狗机制来实现的,他每隔一段时间检查一次看该业务是否持有锁,如果持有的话就增加时间,到业务结束时释放锁就行了,它还提供了一个能够提高性能的方法就是再当前线程被锁住的时候,他会现进行几次自旋,有一个重试的次数,如果超过充实的次数才会拒绝访问,这样提高了性能。以上是我收集的一些redis应用的一些常见面试题,会持续更新,(一个字一个字敲的,更新不易点个关注)。
2025-05-25 21:39:47
447
原创 谈谈我对BFC的理解
BFC(块级格式化上下文)是CSS布局中的重要概念。它形成独立的渲染区域,具有特殊规则:垂直排列元素、处理margin重叠、包含浮动元素等。触发BFC的方法包括设置overflow非visible、float、position等属性。BFC能解决三大常见布局问题:1)防止相邻元素margin塌陷;2)清除内部浮动导致的高度塌陷;3)实现多栏自适应布局。通过给父元素添加overflow:hidden等BFC触发条件,可使浮动元素参与高度计算,避免布局异常。理解BFC机制能有效解决CSS布局中的意外问题。
2025-05-25 20:24:56
555
原创 谈谈我对盒子模型的理解
CSS盒子模型是网页布局的核心概念,包含content(内容)、padding(内边距)、border(边框)和margin(外边距)四部分。标准盒子模型(content-box)下,width/height仅定义内容区域大小,盒子总尺寸需加上padding/border/margin;而box-sizing:border-box(怪异盒子模型)会将padding和border包含在width/height内,使布局计算更直观。现代开发推荐全局设置border-box以简化尺寸控制。
2025-05-25 18:57:08
333
原创 我对ThreadLocal的理解及原理
内存泄漏产生的原因主要是因为ThreadLocal的可key是弱引用,再发生gc是会进行回收,回收之后key为null,然后再第二次调用set方法时key为null会尝试进行清理,如图当map为空的时候会将这个map给清理掉。ThreadLocal的底层就是一个Map(这里的map是一个自定义的map)以thread对象为key,set进去的变量为value的一个Map,下面是set方法。下面讲一下remove方法,remove方法是必须要加上的,否则可能会产生内存泄露的风险。
2025-04-28 21:44:45
258
原创 算法(环的检测)
该题是很著名的(弗洛伊德循环检测算法),也常被称为“龟兔赛跑算法”,因为这个算法使用了两个指针,一个慢指针(每次移动一步,像乌龟)和一个快指针(每次移动两步,像兔子)。如果不存在环,快指针会先到达链表的末尾。此题再第一题的基础上加了一个判断,就是当两者相遇时,快指针返回头节点,并且快指针有一次走两步变为一次走一步,这样他们第二次相遇的时候就是入口节点。如图判断链表中环是否有环,没有则返回false,有则返回true。
2025-04-20 08:24:17
257
原创 算法(单调栈的基本使用)
该题所用的单调栈是严格的大压小,当栈空的时候直接放入栈中,但是当栈顶元素的值大于或等于当前元素时直接将栈顶元素弹出,并求出弹出的栈顶元素可以向两边延伸的最大面积可以用(rigth-left-1)*heigth来求出最大面积。最后当所有的元素都放进栈中后,栈中的有的元素会残留在里面,这样就需要对栈中的元素进行处理,处理的条件是,当栈不为空时,就一直弹出栈顶元素,然后求栈顶元素对应的面积(rigth-left-1)*heigth唯一不同的是right边界一直为数组的长度。
2025-04-13 09:50:41
255
原创 Kafka
因此,Topic和Partition的关系是,Topic是消息的逻辑分类,用于区分和筛选数据,而Partition则是Topic的物理划分,用于将消息分配到不同的部分中以便于处理和存储。4.消息偏移:Kafka中的每个消息都会被分配到一个特定的Partition中,然后根据Partition内的Segment划分,被存储到对应的数据文件中。当发送消息失败时,生产者还会提供。总之,零拷贝是由操作系统提供的一种高效的文件读写技术,而Kafka则大量的运用了零拷贝技术,从而极大的提升了Kafka整体的工作性能。
2025-04-06 09:04:08
787
原创 Springboot集成Elasticsearch
注意依赖的兼容问题,Spring Boot 2.7.x 支持 Elasticsearch 7.x。Spring Boot 3.x 支持 Elasticsearch 8.x。Spring Data Elasticsearch 不会自动创建索引。三、创建一个与 Elasticsearch 索引对应的实体类,并使用注解定义映射关系。五、创建一个service服务层(我直接写实现类了)六、创建一个controller控制层。
2025-03-30 08:55:47
538
原创 RabbitMQ的常见面试题(三)
这些原因可能包括消息被拒绝(basic.reject或basic.nack),消息过期(TTL,Time-To-Live),或者队列达到了最大长度等。:当一条消息成为“死信”时,它会被重新路由到一个预定义的死信交换机(Dead Letter Exchange, DLX)。费者从死信队列中消费消息,从而实现延迟投递的效果。发送消息到普通队列。如果消息符合成为死信的条件,它将被转发到死信交换机,并根据其配置和路由键被分配到相应的死信队列。消费者从绑定到延迟交换机的队列中消费消息,消息会在延迟时间过后到达队列。
2025-03-23 08:46:17
332
原创 RabbitMQ常见面试题(二)
通过事务,生产者可以将一批操作(发送消息、提交/回滚)作为一个原子操作,确保所有消息要么全部成功发送到 Broker,要么全部失败。仅持久化队列和消息是不够的 即使队列和消息配置了持久化,若 RabbitMQ 服务崩溃时消息尚未从内存写入磁盘,仍可能丢失。即使服务器重启,队列依然存在(但队列中的消息需要单独配置持久化)。事务需要与 Broker 多次交互(开启事务、提交事务),增加了网络延迟,降低吞吐量因此会。提交事务,消息会被持久化到队列。回滚事务,所有未提交的消息会被丢弃。,标识消息需要持久化。
2025-03-16 09:02:51
260
1
原创 Rabbitmq的常见面试题(一)
这允许根据消息的内容、标签或路由键进行灵活的消息路由,从而实现更复杂的消息传递逻辑。:设置消息的TTL以及消费者的预取值(prefetch count),确保即使某个消费者未能及时确认消息,RabbitMQ也能将消息重新投递给其他消费者。:RabbitMQ允许消息和队列的持久性设置,确保消息在RabbitMQ重新启动后不会丢失。RabbitMQ支持消息确认机制,消费者可以确认已成功处理消息。:为消息设置合理的TTL(Time To Live),使得过期未被消费的消息自动删除,减少长时间滞留在队列中的风险。
2025-03-09 09:00:06
392
1
原创 JVM的简单介绍
(需要同时满足三个条件1、此类的所有实列对象都已经被回收,在堆中不存在该类的实列对象以及子类对象2、加载该类的类加载器已经被回收3、加载该类的Java.lang.Class对象没有在任何地方被引用。JVM本质上是一个运行在计算机上的程序,他的职责是运行Java字节码文件,Java虚拟机可以运行Java、kotlin,Scala、groovy等语言。,Oracle的Hotspot、OpenJdk的Hotspot、(云原生架构)GraalVM、OPenJ9、龙井。存放了当前线程执行的字节码指令在内存中的地址。
2025-03-02 11:18:54
379
原创 双亲委派机制与如何打破双亲委派机制
类加载器负责将类的字节码从各种来源加载到JVM中,类加载器重要包括:Bootstrap ClassLoader(启动类加载器)、Extension ClassLoader(扩展类加载器)jdk9及之后变为平台类加载器、Application ClassLoader(应用程序类加载器)、自定义加载器。例如,你可以在尝试父类加载器之前先尝试自己加载类,或者在某些条件下完全绕过父类加载器。1、当类加载器收到类加载请求时。:在你的应用程序中,使用你自定义的类加载器来加载类,而不是使用默认的应用程序类加载器。
2025-02-23 08:53:43
273
原创 Map常见的实现类的底层详解
Java中的Map接口代表了一种键值对映射的数据结构,它允许将键(key)与值(value)关联起来。实现Map接口的类提供了不同的底层实现方式,最常用的包括HashMapTreeMap和。下面我将详细解释这些实现类的底层原理。
2024-12-16 14:46:55
298
原创 集合的Set的HashSet与TreeSet的详解及其与List的比较
Java 集合框架提供了Set接口,该接口继承自Collection接口。Set接口的主要特点是它不会包含任何重复的元素(即每个元素都是唯一的)。此外,Set不保证元素的顺序,除非使用某些特定的实现类如或TreeSet来保持插入顺序或自然排序。
2024-12-08 08:50:51
814
原创 redis常见缓存问题及其解决办法
当我们客户端访问不存在的数据时,先请求redis,但是此时redis中没有数据,此时会访问到数据库,但是数据库中也没有数据,这个数据穿透了缓存,直击数据库,我们都知道数据库能够承载的并发不如redis这么高,如果大量的请求同时过来访问这种不存在的数据,这些请求就都会访问到数据库,简单的解决方案就是哪怕这个数据在数据库中也不存在,我们也把这个数据存入到redis中去,这样,下次用户过来访问这个不存在的数据,那么在redis中也能找到这个数据就不会进入到缓存了。假设布隆过滤器判断这个数据不存在,则直接返回。
2024-12-01 18:43:45
495
原创 集合的List中的ArrayLIst与LinkedList详解
ArrayList优点:支持快速随机访问,内存占用相对较小。缺点:在中间插入或删除元素时效率较低。使用场景:适用于需要频繁随机访问的场景,如缓存、数据查询等。LinkedList优点:插入和删除操作效率高,适合频繁的插入和删除操作。缺点:随机访问效率低,内存占用较大。使用场景:适用于需要频繁插入和删除元素的场景,如队列、栈等。
2024-11-25 09:39:23
340
原创 Java常见知识点
我们都知道java具有一个强大的功能,就是java具有一次编译到处运行的特点,而支持java这一特点的原因是虚拟机jvm的存在,我们在使用java文件的时候,需要把源文件通过编译器编译成字节码文件,然后将字节码文件通过jvm翻译成可以识别的机器码.我们可能使用的是不同的平台,其翻译的结果可能不同,但是jvm是运行在操作系统上的,是一样的,,与硬件没有直接的关系,这就支持了java代码实现了java代码的”一次编译,到处运行”.“==”是关系运算符,equals()是方法,同时他们的结果都返回布尔值;
2024-11-17 08:56:55
270
空空如也
空空如也
TA创建的收藏夹 TA关注的收藏夹
TA关注的人
RSS订阅