![](https://img-blog.csdnimg.cn/20201014180756928.png?x-oss-process=image/resize,m_fixed,h_64,w_64)
jvm
文章平均质量分 56
Azadoo
这个作者很懒,什么都没留下…
展开
-
锁优化 适应性自旋锁消除(Lock Elimination)锁膨胀(Lock Coarsening) 轻量级锁(Lightweight Locking) 偏向锁(Biased Locking)
本文将介绍 适应性自旋锁消除(Lock Elimination)锁膨胀(Lock Coarsening) 轻量级锁(Lightweight Locking) 偏向锁(Biased Locking)等锁优化技术自旋锁与自适应自旋互斥同步对性能最大的影响就是阻塞的实现 挂起线程和恢复线程的操作都是需要转入内核态中完成 这些给java虚拟机的并发性能带来了很大压力 同时在许多应用上 共享数据的锁定状态只会持续很短一段时间 为了这段时间去挂起和恢复线程挺不值得 而绝大多数的电脑与服务器都是多核处理器系统 可以让原创 2020-06-17 22:02:24 · 438 阅读 · 0 评论 -
线程安全及实现方法
何为线程安全当多个线程同时访问一个对象时 如果不考虑这些线程在运行时环境下的调度和交替执行 也不需要进行额外的同步 或者在调用方进行任何其他的协调操作 调用这个对象的行为都可以获得正确的结果 那就称这个对象是线程安全的java中的线程安全按照线程安全的“安全程度”由强到弱来排序 可以将java语言中各种操作共享的数据分为以下五类:不可变 绝对线程安全 相对线程安全 线程兼容 线程对立不可变一定是线程安全的如果对线程共享的数据是一个基本数据类型 只要在定义时使用final关键字修饰 就可以保证是原创 2020-06-16 22:46:36 · 259 阅读 · 0 评论 -
协程 进程与线程区别
最初多数的用户线程被设计成协同式调度 所以有了别名“协程” 又由于此时的协程会完整的调用栈保护 恢复工作 也被称为“有栈协程” 与后来的“无栈协程”区分开无栈协程的典型应用即各种语言中await async yield这类关键字 本质上是一种有限状态机 状态保存在包里 比有栈线程调用栈要轻量很多 功能也相对更有限协程的主要优势是轻量 无论是有栈协程还是无栈协程都比传统内核线程要轻量的多 但是协程也有他的局限 需要在应用层面实现的内容特别多(调用栈 调度器等)有栈协程有一种特例实现名为纤程(典型的有栈协原创 2020-06-16 16:34:37 · 149 阅读 · 0 评论 -
线程的实现
主要有三种方式: 1. 使用内核线程实现(1:1实现) 2. 使用用户线程实现(1:N实现)3. 使用用户线程加轻量级进程混合实现(N:M实现)内核线程实现内核线程就是直接由操作系统内核(下称内核)支持的线程由内核来完成线程切换 内核通过操纵调度器对线程进行调度 并负责将现成的任务映射到各个处理器上程序一般不会直接使用内核线程 而是使用内核线程的一种高级接口——轻量级进程 (通俗意义上说的线程) 由于每个轻量级进程都是由一个内核线程支持 因此只有先支持内核线程 才能有轻量级进程 这种轻量级进程与原创 2020-06-15 22:41:30 · 270 阅读 · 0 评论 -
内存间交互操作 与 针对long和double型变量的特殊规则 与 原子性 可见性 有序性
内存间交互操作java内存中定义了以下八种操作实现一个变量从主内存拷贝到工作内存 从工作内存同步回主内存lock (锁定):作用于主内存的变量,它把一个变量标识为一 - 条线程独占的状态。unlock (解锁):作用于主内存的变量,它把个处 于锁定状态的变量释放出来,释放后的变量才可以被其他线程锁定。read (读取):作用于主内存的变量,它把一个变 量的值从主内存传输到线程的工作内存中,以便随后的load动作使用。load (载入):作用于工作内存的变量,它把read操作从主内存中得到的变量值放原创 2020-06-15 20:23:22 · 178 阅读 · 0 评论 -
volatile关键字
是Java虚拟机提供的最轻量级的同步机制当一个变量被定义成volatile后 具备两种特性:保证此变量对所有线程的可见性(当一条线程修改了这个变量的值 新值对于其他线程来说是可以立即得知的) 但是volatile变量的运算在并发下并不是安全的在不符合这两种规则的场景下仍需要加锁来保证原子性运算结果并不依赖变量的当前值 或者能够确保只有单一的线程修改变量的值变量不需要与其他的状态变量共同参与不变约束禁止指令重排序优化 普通的变量仅会保证在该方法的执行过程中所有依赖赋值结果的地方都能获取到正原创 2020-06-15 17:20:37 · 94 阅读 · 0 评论 -
虚拟机字节码执行引擎
执行引擎是java虚拟机核心的组成部分之一运行时栈帧的结构jvm以方法作为最基本的执行单元 栈帧则是用于支持虚拟机进行方法调用和方法执行背后的数据结构 也是虚拟机运行时数据区中的虚拟机栈的栈元素栈帧存储了方法的局部变量表 操作数栈 动态链接 和方法返回地址 附加信息 每一个方法从调用开始到执行结束的过程都对应着一个栈帧在虚拟机栈里从入栈到出栈的过程局部变量表是一组变量值的存储空间 用于存放方法参数和方法内部定义的局部变量在java程序被编译成Class文件时 在方法的Code属性中确定了该方法所原创 2020-06-14 20:09:52 · 136 阅读 · 0 评论 -
虚拟机类加载机制
把描述类的数据从Class文件加载到内存中 并对数据进行校验 转换解析和初始化 最终形成可以被虚拟机直接使用的java类型 这个过程称为虚拟机的类加载机制在java语言中类型的加载 连接 初始化过程都是在程序运行期间完成的 这种策略让类加载时增加了一些性能开销 但是却为java应用提高了极高的扩展性和灵活性 java天生可以动态扩展的语言特性就是依赖运行期间动态加载和动态连接这个特点实现的例如:编写一个面向接口的应用程序 可以等到运行时再指定其实际的实现类 用户通过java预置的或自定义的类加载器让某个原创 2020-06-14 17:01:46 · 218 阅读 · 0 评论 -
HotSpot虚拟机的垃圾收集器
两个名词解释并发:多条垃圾收集器线程间的关系 通常默认此时用户线程处于等待状态并发: 指垃圾收集器线程与用户线程的关系连线表示可以搭配使用 上为新生代收集器 下为老年代收集器Serial收集器新生代收集器 最早出现 现在仍是Hotspot默认新生代收集器 单线程工作 在进行垃圾收集时必须暂停其他所有线程简单而高效ParNew收集器新生代收集器 是Serial收集器的多线程并行版本 其他与Serial基本相同 只有它能与CMS收集器配合使用ParallelScavenge收集器新生代收原创 2020-06-12 21:48:14 · 192 阅读 · 0 评论 -
垃圾收集算法
垃圾收集算法分为两大类:“引用计数式垃圾收集”与“追踪式垃圾收集” 也常被称为“直接垃圾收集”与“间接垃圾收集”两大类本文主要讲追踪式垃圾收集分代收集理论大多数虚拟机都遵循了“分代收集”的理论进行设计 该理论建立在两个分代假说上弱分代假说:绝大多数对象都是朝生夕灭的强分代假说:熬过越多次垃圾收集过程的对象就越难以消亡两个分代假说共同奠定了垃圾收集器的一致设计原则:收集器应该将java堆划分出不同的区域 然后将回收对象根据其年龄(即对象熬过垃圾收集过程的次数)分配到不同的区域中进行存储这样如原创 2020-06-12 17:32:13 · 120 阅读 · 0 评论 -
JVM垃圾收集器与内存分配策略——对象的死亡
概述java内存运行时 程序计数器 虚拟机栈 本地方法栈三个区域随线程生或灭 栈中的栈帧随方法的进入和退出而有条不紊的执行着出栈和入栈 因此这几个区域的内存分配和回收都具备确定性而java堆和方法区这两个区域则有不确定性: 一个接口的多个实现类需要的内存不同 一个方法所执行的不同条件分支所需要的内存也不同 这部分内存的分配和回收是动态的 垃圾收集器所关注的也是这方面内存如何管理堆里存放着java中所有对象的实例 垃圾收集器对堆进行回收前 需要确定哪些对象还“活着” 哪些“死去”(即不可能在被任何途径使原创 2020-06-12 16:05:09 · 131 阅读 · 0 评论 -
java堆中对象的分配布局访问全过程
对象的创建jvm遇到字节码new指令时 先检查该指令参数能否在常量池找那个定位到一个类的符号引用并检查该符号代表的类是否已经被加载解析和初始化过 如果没有则先执行类加载过程 接下来分配内存(可直接确定大小)分配内存就是把指针向空闲内存移动一段对象大小相同的距离 该分配模式成为“指针碰撞” (前提是内存绝对规整) (Serial ParNew等带压缩整理过程的收集器采用该分配模式)所以虚拟机必须维护一个列表 记录哪块内存是可用的 划分给对象实例并更新列表的记录 这种分配方式称为**“空闲列表”(CMS原创 2020-06-10 23:11:23 · 197 阅读 · 0 评论 -
java内存区域
运行时数据区方法区 堆 (由所有线程共享的数据区)虚拟机栈 本地方法栈 程序计数器 (线程隔离的数据区)程序计数器 线程私有是一块较小的内存空间 可以看做是当前线程所执行的字节码的行号指示器字节码解释器工作时通过改变计数器的值来选去下一条命令jvm的多线程是通过线程轮流切换 分配处理器执行时间的方式来实现 在任一时刻一个处理器(或者多核处理器的一个内核)只会执行一条线程中的指令 为了线程切换后能恢复到正确的执行位置 每条线程都有一个独立的程序计数器 且彼此互不影响 独立储存唯一一个没有规定任原创 2020-06-10 16:51:51 · 136 阅读 · 0 评论 -
对象在内存中的存储分布
对象头:关于锁的信息 8个字节类型指针: 属于哪个类 4个字节实例数据:成员变量存储位置 空则为0对齐:将整体字节数补成能被8整除 读取更快更顺如 Object o = new Object();前两个为头部8字节 类型指针4字节(压缩后 不压缩为8字节) 补充4字节凑成能被8整除上锁后很明显 对象头的value变化 储存了锁的信息锁升级...原创 2020-06-08 00:05:38 · 371 阅读 · 0 评论