自定义博客皮肤VIP专享

*博客头图:

格式为PNG、JPG,宽度*高度大于1920*100像素,不超过2MB,主视觉建议放在右侧,请参照线上博客头图

请上传大于1920*100像素的图片!

博客底图:

图片格式为PNG、JPG,不超过1MB,可上下左右平铺至整个背景

栏目图:

图片格式为PNG、JPG,图片宽度*高度为300*38像素,不超过0.5MB

主标题颜色:

RGB颜色,例如:#AFAFAF

Hover:

RGB颜色,例如:#AFAFAF

副标题颜色:

RGB颜色,例如:#AFAFAF

自定义博客皮肤

-+
  • 博客(177)
  • 收藏
  • 关注

原创 JUC-CopyOnWrite 类集合

CopyOnWrite是Java并发包中的线程安全集合实现,包括CopyOnWriteArrayList和CopyOnWriteArraySet。核心原理是写入时拷贝:写操作加锁并创建新数组,不影响并发的读操作。它采用读写分离策略,适合读多写少场景,但存在弱一致性问题,可能出现读取到旧数据的情况。示例代码展示了它们的基本用法和并发读写特性。相比单线程集合,这些并发集合提供了线程安全保障,但需要权衡性能与一致性的关系。

2025-09-15 15:13:24 376

原创 JUC-BlockingQueue 类集合

阻塞队列概述与应用 阻塞队列是Java并发包中的一种线程安全队列,支持阻塞式插入和获取操作,常用于生产者-消费者模式。主要实现包括: ArrayBlockingQueue:基于数组的有界队列,容量固定 LinkedBlockingQueue:基于链表,可指定容量或无界 PriorityBlockingQueue:支持优先级的无界队列 DelayQueue:延迟队列,元素到期才能获取 SynchronousQueue:不存储元素,直接传递数据 LinkedTransferQueue:支持直接传递的无界队列 L

2025-09-15 15:12:46 1063

原创 JUC-Concurrent类集合-ConcurrentLinkedQueue

ConcurrentLinkedQueue和ConcurrentLinkedDeque是Java中的无界线程安全队列实现,采用非阻塞算法和CAS操作实现高并发性能。ConcurrentLinkedQueue是FIFO队列,提供offer/poll/peek等方法;ConcurrentLinkedDeque支持双端操作,具备offerFirst/offerLast等特性。两者均基于链表结构,适合高并发场景如生产者-消费者模式、实时数据处理等。文中还给出了使用示例和一个简化版的ConcurrentLinkedQ

2025-09-15 15:10:20 493

原创 JUC-Concurrent类集合-ConcurrentSkipListMap

ConcurrentSkipListMap是Java并发包中的线程安全有序映射,基于跳表数据结构实现。它具有O(log n)时间复杂度的读写操作,支持高效并发访问和范围查询。核心特点包括:读操作无锁,写操作采用CAS和细粒度锁;适用于需要有序存储的高并发场景如排行榜。与ConcurrentHashMap相比,它牺牲部分性能(O(1)→O(log n))换取有序性。典型应用包括时间序列存储和优先级队列。开发者应根据有序性需求在ConcurrentSkipListMap和ConcurrentHashMap间选择

2025-09-15 15:09:39 445

原创 JUC-Concurrent类集合-ConcurrentHashMap

本文分析了JDK 1.8中ConcurrentHashMap的核心实现。主要内容包括: 容器初始化:ConcurrentHashMap有5种构造方法,初始化采用懒加载模式,在第一次添加元素时才真正初始化数组。sizeCtl变量用于控制初始化和扩容,其值不同代表不同状态。 添加元素: 使用CAS+自旋保证线程安全 对空桶直接CAS插入 遇到扩容中的桶会协助扩容 非空桶使用synchronized加锁后处理 链表转红黑树的阈值为8 关键设计: 采用分段锁思想提高并发度 通过sizeCtl变量实现多线程协同扩容

2025-09-15 10:43:16 1046

原创 JUC-同步器

AQS(AbstractQueuedSynchronizer)是Java并发包中实现锁和同步器的核心框架。它通过维护一个volatile的state状态和CLH队列来管理线程的阻塞与唤醒。AQS支持独占模式(如ReentrantLock)和共享模式(如Semaphore),子类通过重写tryAcquire、tryRelease等方法实现特定同步逻辑。AQS采用模板方法设计模式,提供了获取锁、释放锁的标准流程,同时使用park/unpark机制实现线程阻塞与恢复。其内部通过双向链表实现同步队列,单向链表实现条

2025-09-15 10:32:54 764

原创 JUC-线程池

线程池是一种复用线程资源的技术,通过预先创建一定数量的线程并重复使用,避免频繁创建和销毁线程带来的性能开销。其核心作用包括降低资源消耗、提高响应速度及增强线程管理性。文章通过自定义线程池实现,展示了任务队列、工作线程、拒绝策略等关键组件。拒绝策略支持多种处理方式(如阻塞等待、超时放弃、调用者执行等),任务队列采用阻塞机制实现生产-消费模型。线程池通过复用Worker线程处理任务队列中的任务,超出核心线程数时根据策略处理新任务,有效提升系统性能和稳定性。

2025-09-15 10:11:22 961

原创 JUC-无锁

本文介绍了CAS(Compare-And-Swap)原理及其在Java中的应用。CAS是一种无锁编程技术,通过CPU指令实现原子操作,具有线程安全、无阻塞并发等特点。其核心思想是乐观锁,通过比较内存值与期望值来决定是否更新数据。Java中的原子类(如AtomicInteger)基于CAS实现,提供了getAndSet、incrementAndGet等原子操作方法。文章还分析了CAS的底层实现(lock cmpxchg指令)及其优缺点,包括ABA问题、只能保证单一变量原子性等限制。此外,介绍了原子引用(Ato

2025-09-15 10:08:13 825

原创 JUC-内存

Java内存模型(JMM)定义了线程与内存之间的交互规则,确保多线程程序在不同平台上的内存访问一致性。JMM抽象出主内存和工作内存概念,线程通过8种原子操作实现数据同步。JMM三大特性包括可见性(保证线程能及时感知共享变量修改)、原子性(确保指令执行的完整性)和有序性(防止指令重排序导致逻辑错误)。CPU多级缓存机制通过空间和时间局部性提升性能,但缓存行可能导致伪共享问题,即一个核心修改数据会使其他核心的整个缓存行失效。理解JMM和缓存机制对编写高效并发程序至关重要。

2025-09-15 09:56:44 1026

原创 JUC-同步

摘要 本文主要介绍了Java多线程编程中的临界区、线程安全问题及解决方案。临界区指访问临界资源的代码块,多个线程同时访问可能导致竞态条件。解决线程安全问题的方法包括阻塞式(synchronized、lock)和非阻塞式(原子变量)。synchronized通过对象锁保证临界区代码的原子性,实现互斥和同步。文章详细讲解了synchronized的使用方法(同步块和同步方法)、锁原理、多把锁应用以及死锁的形成条件和避免策略。此外还介绍了活跃性问题如死锁的检测与解决,为Java多线程编程提供了实用指导。

2025-09-12 18:25:34 999

原创 JUC-进程&线程

摘要 本文介绍了进程与线程的基本概念及其对比。进程具有并发性、动态性等特征,而线程是进程中的执行单元,共享进程资源但独立调度。一个进程可包含多个线程实现并发执行。线程相比进程更轻量,通信更简单,但进程间通信较为复杂,涉及信号量、共享存储、管道等方式。文章还详细阐述了Java中创建线程的三种方法:继承Thread类、实现Runnable接口和使用Callable接口,分析了各自的优缺点,并介绍了Thread类的常用API方法。

2025-09-12 16:29:28 604

原创 mysql的各种锁

本文系统介绍了MySQL中的三种锁机制:全局锁、表级锁和行级锁。全局锁锁定整个数据库实例,主要用于数据备份;表级锁分为表锁、元数据锁和意向锁,其中意向锁通过"挂牌告知"机制解决行锁与表锁的冲突问题;行级锁包括记录锁、间隙锁和临键锁,详细分析了不同查询条件下的加锁规则,特别解释了唯一索引等值查询和范围查询时的锁退化机制。文章还通过具体SQL示例演示了各种锁的应用场景和工作原理,帮助理解MySQL锁机制在并发控制中的重要作用。

2025-09-11 19:20:48 894

原创 MVCC讲解

本文介绍了MySQL中的当前读和快照读机制。当前读会锁定记录(如update/delete/select for update操作),保证读取最新数据;快照读则基于MVCC机制读取历史快照(普通select操作),提高并发性能。通过版本链(undo日志)和ReadView实现事务隔离:READ COMMITTED每次查询生成新ReadView,读取已提交的最新数据;REPEATABLE READ首次查询生成ReadView后保持不变,保证事务内读取一致性。文章详细说明了版本链形成过程及不同隔离级别下Read

2025-09-11 19:18:19 1117

原创 mysql事务

MySQL事务是数据库逻辑处理单元,具有ACID特性:原子性(undo log实现)、一致性、隔离性(默认REPEATABLE READ级别)和持久性(redo log实现)。事务隔离级别包括:READ UNCOMMITTED(可能脏读)、READ COMMITTED(不可重复读)、REPEATABLE READ(避免不可重复读)、SERIALIZABLE(完全隔离)。不同级别在并发控制与性能间做出权衡,MySQL通过undo log和redo log机制确保事务的原子性和持久性,MVCC实现多版本并发控制

2025-09-11 19:13:58 1399

原创 索引失效&索引设计

索引失效常见场景包括:1)联合索引不符合最左原则;2)索引字段类型转换;3)LIKE以%开头;4)数据量小优化器选择全表扫描;5)对索引列使用函数或运算;6)OR连接非索引列。设计索引的黄金法则:1)为WHERE条件和ORDER BY字段创建索引;2)注意复合索引顺序(筛选性强的在前);3)使用覆盖索引减少回表操作。合理设计索引可显著提升查询性能,避免全表扫描。

2025-09-11 19:11:51 454

原创 联合索引&最左前缀原则原理&索引下推

本文介绍了MySQL中的联合索引、最左前缀原则和索引下推技术。联合索引是辅助索引的一种,按照字段顺序排序存储数据,支持多字段查询优化。最左前缀原则指出只有查询联合索引最左N个字段时才能利用该索引。对于联合索引设计,应优先考虑减少索引数量并合理分配字段顺序。索引下推是MySQL5.6引入的优化技术,在索引遍历时提前过滤不符合条件的记录,减少回表操作次数,提升查询效率。这些技术相互配合,共同提升数据库查询性能。

2025-09-11 19:09:51 993

原创 覆盖索引优化回表查询

回表查询是指当使用非聚集索引(辅助索引)查询时,需要先通过辅助索引找到主键值,再通过主键到聚集索引中查找完整行记录的过程,这会降低查询性能。覆盖索引是一种优化手段,通过创建包含查询所需所有字段的联合索引,避免回表操作,只需扫描一次索引树即可获取结果。常见应用场景包括:优化列查询、全表count查询和分页查询。例如,将单列索引升级为联合索引,或为分页查询创建包含排序字段的联合索引,都能显著提升查询效率。

2025-09-11 19:05:44 1143

原创 深入学习并发编程中的volatile

volatile关键字在Java并发编程中主要有两个作用:保证内存可见性和禁止指令重排序。它通过强制线程从主内存读取最新值,并在修改后立即写回主内存,确保多线程环境下的变量可见性。此外,volatile修饰的变量会插入内存屏障,防止编译器和处理器对其进行指令重排序优化。相比synchronized锁,volatile更轻量但无法保证原子性,适用于单一写多读的场景,但过度使用可能导致总线风暴问题。

2025-09-04 16:38:36 876

原创 深入学习并发编程中的synchronized

本文介绍了并发编程中的三个核心问题:可见性、原子性和有序性,并探讨了Java内存模型(JMM)的概念。 可见性问题:当一个线程修改共享变量时,其他线程可能无法立即看到最新值。通过示例展示了即使一个线程修改了标志变量,另一个线程仍可能继续循环的情况。 原子性问题:多线程操作共享变量时可能被中断,导致操作不完整。通过5个线程各执行1000次i++的示例,说明number++操作不是原子性的。 有序性问题:编译器和运行时优化可能导致代码执行顺序与编写顺序不一致。使用jcstress工具演示了指令重排可能导致的意外

2025-09-02 08:47:03 1035

原创 线程六种状态的转换

线程生命周期包含六种状态:New(新建)、Runnable(可运行)、Blocked(阻塞)、Waiting(等待)、Timed Waiting(计时等待)和Terminated(终止)。新建线程处于New状态,调用start()后进入Runnable状态。Runnable状态可能正在执行或等待CPU调度。当线程获取锁失败时进入Blocked状态;调用wait()或join()会进入Waiting状态;带超时参数的等待方法会进入Timed Waiting状态。线程终止可能因正常执行完成或异常中断。状态转换是

2025-09-01 17:15:47 765

原创 单例模式(Singleton Pattern)

单例模式是保证一个类仅有一个实例的设计模式,主要用于全局信息类和无状态工具类场景。实现方式分为饿汉式(对象预先创建)和懒汉式(使用时创建)。饿汉式包括静态常量和静态代码块两种线程安全写法。懒汉式有四种实现:线程不安全的基础版、同步方法版(性能差)、双重检查版(线程不安全)以及推荐使用的volatile双重检查模式(保证线程安全与可见性)。此外,静态内部类方式利用JVM类加载机制实现延迟加载和线程安全,而枚举方式则天然防止反射和反序列化破坏单例,是最简洁安全的实现方案。

2025-09-01 17:08:16 840

原创 HashMap集合(高级)

本文摘要: HashMap是Java中基于哈希表的Map实现,采用键值对存储方式,允许null键值但键唯一。JDK1.8前使用数组+链表结构,1.8后引入红黑树优化性能,当链表长度>8且数组长度>64时转为红黑树存储。其核心特性包括:无序存储、非线程安全、动态扩容(默认2倍)等。底层通过扰动函数计算哈希值,采用拉链法解决哈希冲突。文章详细剖析了put/get方法的执行流程,包括初始化、哈希计算、冲突处理、树化条件等关键机制,并解答了常见面试问题,如哈希碰撞处理、红黑树引入原因等,是深入理解Has

2025-09-01 16:59:32 525

原创 Map接口

Map集合概述interface Map<K,V> K:键的类型;V:值的类型Map集合的特点双列集合,一个键对应一个值键不可以重复,值可以重复Map集合的基本使用//创建集合对象//V put(K key, V value) 将指定的值与该映射中的指定键相关联map.put("itheima001","林青霞");map.put("itheima002","张曼玉");map.put("itheima003","王祖贤");map.put("itheima003","柳岩");

2025-09-01 16:48:05 741

原创 Queue接口

本文介绍了Java中的Queue接口及其实现类。Queue是FIFO队列,Deque是其子接口的双向队列。Queue提供了add/offer、remove/poll、element/peek三组方法,其中带"offer/poll/peek"的方法更安全。主要实现类有:1)LinkedList基于链表,支持队列和双端队列;2)ArrayDeque基于动态数组,性能更高;3)PriorityQueue基于优先堆实现优先级队列。三者均非线程安全,其中ArrayDeque和PriorityQue

2025-09-01 16:43:52 325

原创 Set接口

本文介绍了Java中Set集合和TreeSet集合的基本用法和特性。Set集合不存储重复元素且无索引,不能使用普通for循环遍历。TreeSet基于红黑树实现,能自动排序且保证元素唯一性,支持自然排序(实现Comparable接口)和比较器排序(通过Comparator)。文章通过代码示例演示了如何存储字符串、整数以及自定义对象(学生和教师类),并实现按年龄和姓名排序的功能。

2025-09-01 16:40:39 882

原创 ArrayList源码解析

摘要: ArrayList基于动态数组实现,核心字段包括存储数组elementData和元素数量size。添加元素时,若容量不足会触发1.5倍扩容(均摊O(1)),指定位置插入需移动元素(O(n))。删除元素同样需要移动数据(O(n)),但随机访问效率高(O(1))。迭代器采用快速失败机制,检测并发修改。ArrayList非线程安全,多线程场景可使用Collections.synchronizedList或CopyOnWriteArrayList。其优势是随机访问,但插入/删除效率较低,适合查询频繁的场景。

2025-09-01 16:35:47 427

原创 LinkedList源码解析

本文分析了Java中LinkedList的核心实现与设计要点。其底层采用双向链表结构,每个节点存储前驱和后继指针,支持高效的头尾操作(O(1)时间复杂度),但随机访问需遍历(O(n))。相比ArrayList,LinkedList在插入删除操作上更优,但内存占用更高且缓存不友好。文章详细介绍了添加、删除元素的具体实现,迭代器设计以及线程安全问题,并通过对比表格总结了两种数据结构的适用场景:LinkedList适合频繁插入删除,而ArrayList更适合随机访问和内存敏感场景。

2025-09-01 16:29:49 355

原创 List接口

本文摘要: 文章主要介绍了Java中Collection集合的基础知识,包括: 数组与集合的区别:集合长度可变,只能存储引用类型数据 集合类体系结构:Collection是单例集合顶层接口,包含List和Set子接口 Collection常用方法:add、remove、contains、size等基本操作 三种遍历方式: 迭代器遍历(Iterator) 增强for循环 Lambda表达式遍历 使用细节:迭代器遍历时不能直接修改集合,需使用迭代器的remove方法 文章通过代码示例展示了各种集合操作的实际应用

2025-09-01 16:22:10 801

原创 跳表(为什么Mysql的索引使用B+树、redis的ZSET使用跳表)

本文比较了B+树和跳表两种数据结构在数据库索引中的应用区别。B+树作为多叉平衡树,通过分裂调整数据页来维持平衡,通常3层即可存储2000万数据,查询最多3次磁盘IO。跳表采用随机分层策略,存储同等数据量需要约24层,导致更多磁盘IO。因此,B+树在查询性能(IO次数更少)上显著优于跳表,更适合作为数据库索引结构。虽然跳表插入操作更简单,但B+树通过精心设计的分裂合并机制,仍能保持较好的写入性能。

2025-08-30 19:10:53 882

原创 MySQL索引

本文介绍了MySQL索引的概念、分类、底层原理及聚簇/非聚簇索引的区别。索引是帮助MySQL提高查询效率的数据结构,分为主键索引、单值索引、复合索引和唯一索引等类型。索引底层采用B+树结构,通过多级页目录实现高效查询。InnoDB使用聚簇索引(数据与索引存储在一起)和非聚簇索引(需回表查询),而MyISAM全部使用非聚簇索引。索引虽能加速查询,但会占用存储空间并影响数据修改性能。

2025-08-07 17:21:06 1029

原创 B-树与B+树

B树和B+树是数据库索引的核心数据结构。B树通过多路平衡特性减少磁盘IO次数,但存在非叶子节点存储数据导致树高较高、范围查询效率低等问题。B+树针对这些缺陷进行了优化:非叶子节点仅存储索引键,增加分支数降低树高;所有数据存储在叶子节点并通过双向链表连接,大幅提升范围查询效率;查询路径长度一致保证性能稳定。B+树的这些特性使其成为数据库系统的首选索引结构,尤其适合处理海量数据的高效查询和范围操作。

2025-08-07 14:46:44 1039

原创 平衡二叉树 AVL

平衡二叉树(AVL树)是一种特殊的二叉排序树,要求每个结点的左右子树高度差绝对值不超过1,且平衡因子只能是-1、0或1。当插入新结点导致失衡时,需要通过LL、RR、LR、RL四种旋转类型调整最小不平衡子树,以保持平衡性和排序性质。通过示例展示了如何逐步构建AVL树并处理失衡情况,关键原则是降低高度同时维护二叉排序树特性。调整过程需确保每次操作后整棵树重新达到平衡状态。

2025-08-07 14:41:23 311

原创 二叉排序树 BST

二叉排序树(BST)是一种动态查找结构,其特点是左子树结点值均小于根结点,右子树结点值均大于根结点。通过中序遍历BST可获得有序序列。查找性能取决于树的形态,最好情况下查找时间为O(log₂n),最坏情况下退化为O(n)。BST的插入操作总是作为新叶子结点完成,无需移动其他结点。删除操作分三种情况处理:删除叶子结点直接移除;删除单子树结点用其子树替换;删除双子树结点可用其前驱或后继结点替代。BST适用于频繁查找和插入的场景,但需要平衡化处理以避免性能退化。

2025-08-07 14:32:22 735

原创 重写equals为何要重写hashcode

Java中hashCode()是Object类的一个native方法,由C/C++实现。对象不同时hashCode通常不同,但equals相同的对象hashCode必须相同。HashMap通过hashCode定位存储位置,使用数组+链表结构。重写equals时必须同时重写hashCode,否则在HashMap中会出现逻辑错误。HashMap查找时先计算hash值确定位置,再用equals匹配具体对象。hashCode的存在极大提高了哈希表类集合的存取效率。

2025-07-31 10:39:35 279

原创 equals和==的区别

本文分析了Java中equals方法的实现机制。Object类中equals方法默认使用==比较内存地址,而包装类如Integer重写了该方法实现值比较。对于自定义类,需重写equals方法定义比较规则:1)先比较地址;2)检查null和类型;3)类型转换后比较关键字段。推荐使用Objects.equals()避免空指针异常。最后强调重写equals时必须重写hashCode,以保持对象在哈希集合中的一致性。文章通过源码解析和示例代码详细说明了equals方法的正确实现方式。

2025-07-31 10:38:10 280

原创 Java中的基本类型与包装类型

本文讲解了Java基本类型和包装类的区别。Java为8种基本类型提供了对应的包装类,使其能够以对象形式使用。通过示例代码分析了"=="运算符在基本类型和对象类型比较时的不同行为:基本类型比较值,对象类型比较地址。重点说明了Integer的缓存机制(-128到127)和自动拆装箱原理,解释了不同比较结果的原因。最后总结出4点注意事项:包装类的缓存机制、"=="的比较规则、自动拆装箱可能导致的空指针异常,以及建议使用equals()方法比较包装类对象。

2025-07-31 10:36:47 253

原创 红黑树 Red Black Tree

红黑树是一种自平衡二叉搜索树,通过在二叉搜索树基础上增加五大性质来维持平衡:1)节点有红黑两色;2)根节点为黑;3)叶子节点为黑;4)无连续红节点;5)各路径黑节点数相同。相比AVL树,红黑树的平衡条件更宽松,降低了调整频率,在频繁插入删除场景下效率更高。插入操作分为四种情况处理:父节点为黑时直接插入;父红叔黑时旋转变色;父叔皆红时变色向上递归;父红叔黑且为"左右"或"右左"类型时先旋转转为"左左"或"右右"类型再处理。红黑树在

2025-07-31 10:35:40 1086

原创 方法字节码执行流程解析

本文通过图解方式展示了Java方法执行流程,以Demo3_1类为例详细解析了字节码执行过程。原始代码包含变量赋值、运算和打印操作,对应的字节码文件展示了常量池结构和方法指令。执行过程包括:运行时常量池加载、方法区存储字节码、线程栈帧分配,以及具体的指令执行步骤(如bipush压栈、istore存储、iadd运算等)。每步操作都配有内存状态示意图,清晰呈现了操作数栈和局部变量表的变化,完整演示了从字节码到机器指令的执行细节。

2025-06-21 14:50:04 856

原创 JVM-类加载机制

Java类加载机制解析:从加载到双亲委派 摘要: 本文系统介绍了Java类加载过程与双亲委派机制。类加载分为加载、链接(验证/准备/解析)、初始化三阶段,其中静态变量在准备阶段分配默认值,初始化阶段才显式赋值。通过案例演示了类动态加载特性。类加载器分为启动类(核心库)、扩展类(ext目录)、应用类(ClassPath)和自定义类加载器,采用双亲委派模式确保安全性和避免重复加载。重点分析了双亲委派实现原理(通过组合复用父加载器)及避免核心API篡改的安全机制,并给出不破坏双亲委派的自定义类加载器实现方案,只需

2025-06-18 16:45:45 761

原创 JVM-垃圾回收

本文介绍了垃圾回收的核心算法和实现技术。主要内容包括: 对象回收判定方法: 引用计数法(存在循环引用问题) 可达性分析算法(JVM采用,解决循环引用) 四种引用类型(强、软、弱、虚)及其回收策略 垃圾回收算法: 标记-清除(简单但产生碎片) 复制算法(无碎片但浪费空间) 标记-整理(无碎片但耗时) 分代回收机制: 新生代(Eden+Survivor)采用复制算法 老年代采用标记-清除/整理算法 对象晋升规则和回收触发条件 常见垃圾回收器组合: 单线程组合(Serial+Serial Old) 高吞吐组合(P

2025-06-13 08:09:59 981

空空如也

空空如也

TA创建的收藏夹 TA关注的收藏夹

TA关注的人

提示
确定要删除当前文章?
取消 删除