![](https://img-blog.csdnimg.cn/direct/422634e133ee4e0fbae4ba5f267f7257.png?x-oss-process=image/resize,m_fixed,h_224,w_224)
Java核心技术精讲
文章平均质量分 95
你好,我叫sharkchili,目前还是在一线奋斗的Java开发,经历过很多有意思的项目,也写过很多有意思的文章,是CSDN Java领域的博客专家,也是Java Guide的维护者之一,本专栏是我结合面试和被面试整理的一套涵盖Java核心的技术的技术博文。
shark-chili
这个作者很懒,什么都没留下…
展开
-
聊聊redis中的字典的实现
的字典采用的双数组的方式管理键值对,如下图所示,可以看到dict的数据结构定义了大小为2的哈希表数组,当某个哈希表碰撞激烈需要进行调整时就调整算法将对应的键值对存到。随着我们不断的新增键值对,当前的哈希算法得到的索引位置很大概率会出现哈希冲突,即每次定位到的索引位置都很大概率存在元素,这也就是我们的常说的哈希冲突,这就是。因为近期收到很多读者的私信,所以也专门创建了一个交流群,感兴趣的读者可以通过上方的公众号获取笔者的联系方式完成好友添加,点击备注。原创 2024-06-17 10:21:23 · 46 阅读 · 0 评论 -
详解redis单线程设计思路
的设计者就采用单线程来处理十万级别的内存操作,通过单线程极致的压榨和利用多路复用机制,简化的实现的复杂度确保redis的实现更专注的数据结构设计的单个动作操作的优化,也保证后续的问题追踪和排查难度大大降低,后续也可以针对性的对单个慢操作点进行针对性定位和优化,由此思路实现一个综合性的网络内存数据库最佳方案。因为近期收到很多读者的私信,所以也专门创建了一个交流群,感兴趣的读者可以通过上方的公众号获取笔者的联系方式完成好友添加,点击备注。和键值对读写操作的内存数据库,本文将从源码的角度剖析一下。原创 2024-06-04 08:41:38 · 41 阅读 · 0 评论 -
来聊聊Redis中的字符串对象的设计
因为近期收到很多读者的私信,所以也专门创建了一个交流群,感兴趣的读者可以通过上方的公众号获取笔者的联系方式完成好友添加,点击备注。因为近期收到很多读者的私信,所以也专门创建了一个交流群,感兴趣的读者可以通过上方的公众号获取笔者的联系方式完成好友添加,点击备注。这种编码格式的字符串就是专门用于存储这种短字符串的,进行字符串足够小,所以在进行内存空间分配时,类型的字符串,进行内存空间时需要两次的分配过程,无论在内存管理还是对象操作上都没有。进行了详细的介绍了,而本文我将从顶层的视角来聊聊。原创 2024-05-31 09:18:17 · 30 阅读 · 0 评论 -
来聊聊Redis简单动态字符串SDS
sds数组自身通过buf字段记录字符数组,通过len记录当前字符串长度,以及通过free记录当前buf数组的空闲空间,那么问题来了为什么会有free这个字段呢?假设我们使用sds创建一个空间为5的数组,操作过程中修改了字符串内容将字符串Redis改为Res,sds的做法除了修改buf数组的字符串以外,还会同步的维护长度len和free字段,通过free字段的维护确保后续分配2个字符串可以直接利用现有内存而无需在创建全新的数组存放字符的操作,这也就是所谓的惰性释放的设计思想:对于这段结构的定义,我们可以。原创 2024-05-29 09:05:45 · 37 阅读 · 0 评论 -
聊一聊Spring为什么需要三级缓存
我们可以在:即单例缓存Map,其内部存储的都是以bean的名称为key,已经完全创建的bean作为value的Map。:该缓存都bean的工厂方法,可能有些读者不太理解,我们就以上文的AService为例,在Spring进行每一个bean初始化时,都会为这个bean封装一个工厂方法用于bean的创建,这一点笔者也会在后续的代码中提及,这里我们只需要知道这个缓存是以bean的名称作为key,创建该bean的工厂方法为value的Map即可。:其内部缓存的都是未完全完成创建的bean,就比如某个。原创 2024-05-15 08:43:07 · 328 阅读 · 0 评论 -
聊聊大厂面试中一道库存管理问题
以上便是笔者关于6个库存管理线程进行库存操作的设计思路,即通过将商品的互斥操作进行水平拆分,从而降低6个线程间的冲突以提升程序的执行性能,当然这个问题可能还会涉及内存操作的拓展,例如假如我们的商品操作会从多个维度查询定位,为保证查询和扣减的性能,我们可能会将商品信息加载到内存中,此时我们就需要通过。基于这个锁的方案我们给出新的一套代码示例,最终执行时间变成3秒,当然从目前来看性能提升不算是特别明显,因为当前管理的商品不是很多,随着库存商品的增加,我们的。假定我们认为商品是多个,且不定时新增,对应的库存表。原创 2024-04-22 08:30:00 · 32 阅读 · 0 评论 -
来聊聊某大厂面试常聊的Spring生命周期
因为近期收到很多读者的私信,所以也专门创建了一个交流群,感兴趣的读者可以通过上方的公众号获取笔者的联系方式完成好友添加,点击备注。因为近期收到很多读者的私信,所以也专门创建了一个交流群,感兴趣的读者可以通过上方的公众号获取笔者的联系方式完成好友添加,点击备注。生命周期的文章,文章行为生涩,于是抽空再次进行复盘整理了这篇关于。对于源码的阅读,大部分答案其实都可以在注释中得到答案,所以对于。对应的我们也给出整个生命周期的核心图解,可以看到实例化会调用。即可和笔者和笔者的朋友们进行深入交流。原创 2024-04-15 09:23:55 · 3381 阅读 · 0 评论 -
主键自增是否会降低数据库insert性能?
的默认模式,在这种模式下进行插入时插入语句不会一致持有auto_inc锁到语句结束,而是一拿到锁就释放,这就是为什么插入11的语句因为gap锁阻塞不影响插入语句2自增id的获取。锁,它会在语句结束之后释放当前锁,注意这里所说的是语句级别下的锁,而不是事务级的锁(一个事务可能存在多个插入语句)。的插入不会导致任何性能问题,作为开发者我们更应该关心的是进行插入期间,业务上是否会存在那些干扰插入的间隙锁的情况。我们再设置为1,还是以上述的SQL为例,进行3个会话操作,首先会话1的范围删除,持有。原创 2024-04-09 08:30:00 · 220 阅读 · 0 评论 -
某大厂线程池拒绝策略连环问
随着任务的递增,任务队列无法容纳最新的任务,线程池就会认为现处于高峰期,便临时增加应急线程处理任务。我们先来复习一下线程池的工作流程,每次任务提交时,线程池都会尝试将任务提交到核心线程上,如果线程数小于核心线程数,线程池就会添加工作线程并执行当前任务。是希望所有的任务都能够被执行,按照笔者的经验,假如我们的场景是偶发这种突发场景,在内存允许的情况下,我们建议增加阻塞队列。这个拒绝策略,导致耗时的任务用了主线程执行,导致线程池阻塞,进而导致后续任务无法及时执行,严重的情况下很可能导致。原创 2024-04-03 08:30:00 · 36 阅读 · 0 评论 -
线程池大小设置多少合理
每个人都有每个人的看法,有的人说通过压测得到一个TPS并基于这个结果设置线程数,有的说需要结合一定的一套规范去推算大概的范围,最后通过公式获得较为准确的结果。因为近期收到很多读者的私信,所以也专门创建了一个交流群,感兴趣的读者可以通过上方的公众号获取笔者的联系方式完成好友添加,点击备注。因为近期收到很多读者的私信,所以也专门创建了一个交流群,感兴趣的读者可以通过上方的公众号获取笔者的联系方式完成好友添加,点击备注。核心,由此也可推出,对于计算密集型的任务,满载情况下,所有的。原创 2024-03-25 08:30:00 · 281 阅读 · 1 评论 -
深入剖析源码速通Spring多数据源问题
我们后续可能用到不止两个的数据库,所以我们可能会将数据源的信息保存到数据源中,考虑到这一点,我们编写了一个数据源管理类,负责将用户从数据库中查出来的数据源信息存到容器中。之前写过一篇关于多数据源的实践,虽然写的很详细,但是个人认为没有把多数据源的原理和设计讲透彻,所以再次拾起这篇文章进行修饰加工,希望对你有帮助。因为近期收到很多读者的私信,所以也专门创建了一个交流群,感兴趣的读者可以通过上方的公众号获取笔者的联系方式完成好友添加,点击备注。的设计思路之后,我们现在就不妨设计一下多数据源切换的实现思路。原创 2023-12-18 14:33:17 · 1651 阅读 · 0 评论 -
JVM内存问题排错最佳实践
因为近期收到很多读者的私信,所以也专门创建了一个交流群,感兴趣的读者可以通过上方的公众号获取笔者的联系方式完成好友添加,点击备注。因为近期收到很多读者的私信,所以也专门创建了一个交流群,感兴趣的读者可以通过上方的公众号获取笔者的联系方式完成好友添加,点击备注。上一篇的文章中分享了一个入门级别的调优实践,收到很多读者的好评,所以笔者今天再次分享一个进阶一点的案例,希望对近期在面试的读者对于。正是因为这样一个为了保证数据散列均摊且还能顺序遍历的数据结构,导致仅仅10w条的数据占用了大量的内存,从而导致了。原创 2024-03-10 08:30:00 · 1509 阅读 · 0 评论 -
写给新手的一个JVM调优入门级案例
Hi,我是sharkChili,是个不断在硬核技术上作死的java coder,是CSDN的博客专家,也是开源项目Java Guide的维护者之一,熟悉Java也会一点Go,偶尔也会在C源码边缘徘徊。自此我们大概知道因为大数据文件导入内存导致堆内存被打满,对于这类问题,我们首先要考虑单位时间内的内存使用率不会超过设置的堆内存大小,对于上述代码,我们对文件采用逐行批次读取一次然后解析插入的方式。接口将文件提交到文件服务器上,完成所有文件上传之后,用户会通过。接口会根据接口传入的文件名将数据导入的数据库中。原创 2024-03-06 08:30:00 · 717 阅读 · 0 评论 -
万字长文带你详聊Java注解本质
Target@Retention@Inherited首先定义check注解Retention;Target;原创 2022-01-25 21:37:01 · 731 阅读 · 0 评论 -
一文带你速通Java集合核心面试题
从Java存放单元素的Collection。存放键值对的Map类型。Collection有序不重复的Set。有序可重复的LIst。FIFO的队列类型Queue。另一大类就是映射集,他的特点就是每一个元素都是由键值对组成,我们可以通过key找到对应的value,类图如下,集合具体详情笔者会在后文阐述。原创 2023-12-14 08:58:03 · 1379 阅读 · 1 评论 -
JVM日常故障排查小结
jstack是JVM自带的工具,用于追踪Java进程线程id的堆栈信息、锁信息,或者打印core file,远程调试Java堆栈信息等。# 打印对应java进程的堆栈信息option常见选项-F 当正常输出的请求不被响应时,强制输出线程堆栈-m 如果调用到本地方法的话,可以显示C/C++的堆栈-l 除堆栈外,显示关于锁的附加信息,在发生死锁时可以用jstack -l pid来观察锁持有情况导致CPU 100%定位进程号,如果是Java进程则查看是哪个线程导致的。原创 2023-12-18 14:32:09 · 1085 阅读 · 4 评论 -
一文带你速通HashMap底层核心数据结构红黑树
每个节点或者红色,或者是黑色。根节点为黑色。每一个叶子节点都是黑色。如果一个节点是红色,那么他的孩子节点都是黑色。从任意一个节点,经过的黑色节点是一样的。在《算法4》一书中认为红黑树和2-3树是等价的。原创 2020-09-03 15:23:46 · 1856 阅读 · 0 评论 -
10亿数据高效插入MySQL最佳方案
每条数据转为数据库数据大约1k。数据都存在txt文档中,需要进行解析后才能存到数据库中。所有数据对应的文档都存在Hdfs或S3分布式文件存储里。数据被分到100个文件中,通过文件的后缀确定这些数据的批次。要求保证有序导入,数据尽可能不重复。存储的数据库是MySQL。原创 2024-01-09 08:30:00 · 1772 阅读 · 0 评论 -
一文带你了解Quartz
在调度进行任务争抢时先对数据库表上锁,只有拿到锁的节点才可以进行获取任务并调度,这种是常规情况下的解决方案,但这种实现方式有着很强的倾入性,且在高并发的场景性能表现也不是很出色,所以大部分情况下,我们不是很推荐通过数据表的形式实现分布式任务调度一致性。框架分布式任务调度的较好解决方案,通过在内存中进行任务争抢,大大提分布式调度性能,但还是存调度空跑问题,即先抢到锁的节点获取仅有的任务,而其他节点随后得锁后却没有执行任务,造成一次空跑。为工作内容,并按照触发器的安排进行任务的调度的任务定时被调度器执行。原创 2024-01-08 08:30:00 · 1812 阅读 · 0 评论 -
一文上手ThreadLocal使用和原理
当我们某个类需要被多线程共享的时候,我们就可以使用ThreadLocal关键字,ThreadLocal可以为每个线程创建这个变量的副本并存到每个线程的存储空间中(关于这个存储空间后文会展开讲述),从而确保共享变量对每个线程隔离,实现线程安全。//静态变量,所有线程共享一个connect//= null)代码很简单,问题也很明显,假如我们1000个线程同时去调用这个工具类建立数据库连接,很可能在同一个时间,同时指向getConnection方法。原创 2024-01-04 09:00:03 · 2841 阅读 · 1 评论 -
你一定用得上的MySQL批量插入技巧
你好,我叫sharkchili,目前还是在一线奋斗的Java开发,经历过很多有意思的项目,也写过很多有意思的文章,是CSDN Java领域的博客专家,也是Java Guide的维护者之一,非常欢迎你关注我的公众号:写代码的SharkChili,这里面会有笔者精心挑选的并发、JVM、MySQL数据库专栏,也有笔者日常分享的硬核技术小文。文章的稿子是写在2023年的12月,累觉不爱,忙碌的工作一直无法抽身来梳理这篇文章,终于在2024的1月的深夜开始着手整理这篇文章。插入的性能的性能表现最出色。原创 2024-01-03 09:10:51 · 1967 阅读 · 0 评论 -
Java8流式编程入门
声明性:流式编程的所有操作都是语义化的,我们完全可以通过方法名大致猜出操作目的。可复合:流式编程无需像jdk8之前的版本为了实现组合操作而取创建各种临时集合,取而代之的是基于一段连续的流自顶而下的实现组合操作。可并行:当我们需要提高计算密集型任务的性能时,只需将stream改为,就可以开启并行流开启多个线程一起工作(默认情况下,线程数和计算机的CPU核心数是一样的)。//找出低于400卡的菜肴//按照升序排列//得到这些菜肴的名称//组成list。原创 2022-03-28 00:01:31 · 742 阅读 · 2 评论 -
CompletableFuture组合流水线任务最佳实践
这一步我们采用CompletableFuture的组合方式,将获取售价、生成商品信息、计算最终折扣价以流的方式封装成CompletableFuture的列表,再通过join阻塞顺序获取列表中各个任务的结果。本文所有案例都会基于这样的一个需求,用户会在不同的店铺查看同一件商品,只要用户在提供给商店对应的产品名称,商店就会返回对应产品的价格和折扣、以及最终折后价。最终我们的代码改造成这样,改造也很简单,将转换quote的异步任何用thenCombine和获取汇率的异步任何组合起来,用各自的结果封装成一个函数。原创 2022-03-28 00:01:23 · 784 阅读 · 1 评论 -
CompletableFuture基础实践小结
thenCompose方法会在某个任务执行完成后,将该任务的执行结果作为方法入参然后执行指定的方法,该方法会返回一个新的CompletableFuture实例,例如我们希望任务1执行完成后执行任务2,任务2执行完成后返回执行任务3,最终结果是从任务3中获取。thenApplyAsync与thenApply不同的是,在第一个异步任务有指定线程池的情况下,第二个异步任务会被提交到其他线程池中,所以这里我们可以说明一个规律,带有Async关键字的方法支持组合任务时,将任务提交到不同的线程池中。原创 2023-12-11 12:36:35 · 1357 阅读 · 1 评论 -
PriorityQueue源码分析
提到队列我们优先想到的特性肯定是"先进先出",而本篇文章所介绍的优先队列则和普通队列有所区别,它是一种按照"优先级"进行排列的数据结构。如下图所示,如果是普通队列,我们按照元素1到元素4的顺序依次入队的话,那么出队的顺序则也是元素1到4。而优先队列的逻辑存储结构和普通队列有所不同,以JDK源码为例,优先队列底层实际上是使用小顶堆形式的二叉堆,即值最小的元素优先出队。可能很多读者对二叉堆的不是很理解,这里笔者以小顶堆为例。假如我们的元素1到元素4的优先级分别是:2、1、3、4。原创 2020-07-28 13:31:06 · 110 阅读 · 0 评论 -
JavaIO模型小结
BIO是同步阻塞IO模型,当应用程序发起IO操作后,必须等待IO操作完成后,线程才能继续运行。NIO是同步非阻IO模型,当进程发起IO后,会直接返回感兴趣的IO事件是否已完成,并不会阻塞当前线程,但NIO这种往复的轮询IO的工作方式,可能会造成不必要的CPU资源浪费。原创 2020-09-20 11:05:30 · 385 阅读 · 1 评论 -
LongAdder源码分析
JDK1.5开始就提供基本数据类型操作的原子类,通过CAS实现线程安全的数据累加,在高并发场景下,这些原子类会因为竞争的激烈导致大量线程频繁的CAS频繁失败,影响程序执行效率。所以JDK1.8提供了线程安全的计数器LongAdder,它底层是由一个数组进行计数,不同线程会根据哈希算法会得到底层数组的某个索引位置,然后将累加的值通过CAS的方式累加到该索引位置上。因为LongAdder底层的数组最大容量为CPU核心数,所以在高并发场景下的CAS操作成功率远高于JDK1.5的原子类,所以在JDK8。原创 2020-11-20 11:01:31 · 1711 阅读 · 0 评论 -
ConcurrentSkipListMap源码分析
是JDK1.6提供的又一个线程安全有序的map集合,在高并发场景下有着不错的存取效率。使用起来和TreeMap由跳表实现,支持多线程场景下的增删改查操作,是一个线程安全的并发容器。TreeMap是由红黑树实现的,不支持多线程操作,是线程非安全的容器。此外存取操作时间复杂度都是O(log n),并且存取效率和线程数并没有关系,这意味着在高并发场景下,它的执行效率远高于,这一点我们用下面这段代码即可印证。//创建1w个线程//插入1000w条数据i++) {while (!原创 2021-10-06 14:15:28 · 290 阅读 · 0 评论 -
ArrayBlockingQueue源码分析
Java阻塞队列的历史可以追溯到JDK1.5版本,Java平台增加了java.util.concurrent(即我们常说的JUC包),这其中包含了各种并发流程控制工具、并发容器等。这其中自然也包含了我们这篇文章所讨论的阻塞队列。为了实现在高并发场景下,多线程之间数据共享的问题,在JDK1.5版本,出现了我们所熟知的ArrayBlockingQueue和LinkedBlockingQueue,一种带有生产者-消费者模式所实现的并发容器。原创 2022-02-19 14:38:07 · 247 阅读 · 0 评论 -
Redis的有序集合底层为什么要用跳表?
有了整体的思路之后,我们可以开始实现一个跳表了,首先定义一下跳表中的节点Node,从上文的演示中可以看出每一个Node存储的value值。后继节点的地址。多级索引。为了更方便统一管理Node后继节点地址和多级索引指向的元素地址,笔者在Node中设置了一个forwards数组,用于记录原始链表节点的后继节点和多级索引的后继节点指向。以下图为例,我们forwards数组长度为5,其中索引0记录的是原始链表节点的后继节点地址,而其余自底向上表示从1级索引到4级索引的后继节点指向。原创 2024-01-21 21:27:30 · 15 阅读 · 0 评论 -
来聊聊守护线程
很多人对守护线程都不陌生,对于守护线程大部分读者都停留在JDK官方文档所介绍的概念:文档的意思是当JVM中不存在任何一个正在运行的非守护线程时,JVM进程会直接退出。读起来很拗口对不对,没关系,本文就会基于几个代码示例,让你更深层次的理解守护线程。守护线程和普通线程有什么区别?守护线程默认优先级是多少?若父线程为守护线程,在其内部创建一个普通线程,父线程停止,子线程是否也会停止呢?如何创建守护线程池?守护线程使用有哪些注意事项?原创 2024-01-10 08:30:00 · 878 阅读 · 0 评论 -
来聊聊分库分表
range法hash法range+hash法进行分表后,对于非partition key的查询就由为的复杂,因为非partition key和没有任何关联如果没有采取任何措施的话,查询效率就会十分低下。最简单的例子就是上文600w那条数据,他记录着一个用户的个人信息,假如我们希望通过用户名定位到他又该如何做呢?很明显在没有任何措施的情况下,只能通过逐表遍历查询解决了。因为各种原有我们需要对旧有数据表进行扩容,对此数据迁移就是一个很麻烦的问题,有没有什么比较安全且易实现的方案呢?原创 2024-01-12 08:30:00 · 3915 阅读 · 1 评论 -
聊点硬核的逃逸分析技术
逃逸分析技术是JVM用于提高性能以及节省内存的手段,在JVM编译语境下也就是我们常说的JIT阶段该对象是否分配在堆上(static关键字或者成员变量)。该对象是否会传给未知代码,比如return到外部给别的类使用。只要编译阶段判定当前对象并没有发生逃逸,那么它就会采用栈上分配标量替换同步锁消除等手段提升程序执行性能和节省内存开销。那么我们又该如何判断对象是否逃逸呢?@Data我们通过UserService进行初始化,那么请问这段代码是否发生逃逸呢?原创 2024-01-16 08:30:00 · 1243 阅读 · 0 评论 -
实现一个简单实用的并发同步模型
日常开发后端接口时,总是会遇到一些和业务关联性不是很大却又很耗时的操作,由于功能的重要性和体量远达不到要上消息中间件的情况,这时候我们就可以实现一个简单的生产者消费者模型来实现异步消费。笔者在这里仅仅是实现了一个比较简单的并发同步模型,该模型只能算是一个比较实用的示例版本,后续笔者会考虑补充异步消费失败等兜底策略,感兴趣的读者可以点点关注。本文整体结构如下,通过笔者的代码示例,你会对生产者消费者这种并发同步的设计模式的开发模型和使用场景有着更进一步的理解。进行管理,注意笔者这里声明的阻塞队列的容量为。原创 2024-01-17 08:30:00 · 1337 阅读 · 0 评论 -
来聊聊大厂常问的SPI工作原理
在我们日常的web开发或者第三方服务调用时,会根据接口要求传入指定参数得到相应结果,这种为用户提供服务的服务方我们统称为API。而SPI则是另一种设计理念,它全称是,即服务提供接口,它更强调定义一组规范,让服务提供者根据规范实现接口的个性化功能。然后服务调用方调用时通过调用接口,让提供方通过某种服务发现机制得到接口的实现类为从而响应结果,这种解耦调用者和服务提供者的方式也正是人们常说的面向接口编程。是不是觉得很抽象呢?没有关系,本文的整体结构如下,笔者会通过一段代码示例和并基于源码剖析。原创 2024-01-18 08:30:00 · 6522 阅读 · 0 评论 -
来聊聊session与token的区别
我们都知道web应用都采用HTTP协议进行通信,而HTTP协议是一种无状态协议,而用户常常因为简单业务上的操作而需要不断请求web系统的接口,为了让web系统可以感知到当前请求的是否是同一个用户,于是就有session机制。当用户第一次发起web请求时,服务端会为其生成一个唯一ID缓存在服务器上(通常会存储到内存、数据库里),然后通过响应头的方式将这个sessionId交给用户,让用户缓存到cookie中,后续的请求只需携带这个sessionId,服务器即可快速的完成用户的认证。token。原创 2024-01-19 08:30:00 · 892 阅读 · 0 评论 -
百万级别数据导出最佳实践
以上便是笔者的百万级别数据导出的落地方案,可以看出笔者着重在分页查询大小和分页查询sql上进行重点优化,通过平衡分页查询的数据量和IO次数找到合适的pageSize,再通过上一次分页查询结果定位下一次查询的id作为where条件,避免分页查询时的全秒扫描以得到符合业务需求的高性能sql,从而完成百万级别数据的高效导出。这里需要注意一点,因为我们分页查询面对的是百万级别的数据,所以随着分页的推进势必出现深分页导致查询效率势降低,所以为了提高分页查询的效率,我们可以利用查询数据有序的特性,通过。原创 2024-01-22 08:30:00 · 1575 阅读 · 0 评论 -
深入HashMap底层理解阿里手册的遍历守则
这里面会有笔者精心挑选的并发、JVM、MySQL数据库专栏,也有笔者日常分享的硬核技术小文。在论证为什么之前,我们必须先印证是不是,所以笔者针对这一守则给出两段示例代码,先来看看基于。定位到索引1的位置,再经过一次a节点找到key为b的节点,自此我们也就直到了为什么使用。的底层实现和遍历技巧有着更进一步的理解和掌握,基于此文笔者也顺便总结一下。时无需再回过头到数组中定位元素,避免了一次扫描,这也是为什么是使用。,若这个key对应的节点在链表或者红黑树的话,又需要进行一次。原创 2024-01-23 08:30:00 · 3224 阅读 · 1 评论 -
来聊聊JVM的方法区
方法区其实是一个**《Java虚拟机规范》一个逻辑上的概念,对于不同版本的JVM都有不同的实现,就以我们常用的HotSpotJVM而言,方法区还有一个别名叫Non-Heap**,即非堆内存,这么定义的目的自然是要让Java开发者明白方法区和堆是一块独立于Java方法区和Java堆内存一样也是属于各个线程共享的内存区域。方法区在JVM启动就时创建,并且它实际的物理内存空间和Java堆内存一样可以是不连续的,注意笔者所说,可以是不连续的。方法区内存大小也可以选择固定大小或者可扩展。原创 2024-01-24 08:30:00 · 2596 阅读 · 0 评论 -
关于元空间是否会触发GC
需要注意的是,在判断是否有实例还在使用当前类以及是否有类加载器引用这个类这两个步骤的时候,为了能够明确这两点,可能需要扫描全部堆空间的,这也就意味着元空间的回收可能伴随着。原因很简单,方法区进行垃圾收集的回收的收益不是很大,它并不像堆内存的新生代那样,在一次新生代的垃圾回收就能回收。的文章时,引发读者的探讨,有读者认为元空间实际上是可能触发垃圾回收,遂笔者就以这篇文章来探讨一下这个问题。等增强技术的使用是否得当,如果发现大量的增强类出现在元空间时,需要及时定位并解决。,同时我的公众号也有我精心整理的。原创 2024-01-25 08:30:00 · 992 阅读 · 0 评论