架构师训练营第九章总结
JVM
JVM组成架构
Java是一种跨平台的语言,JVM屏蔽了底层系统的不同,为Java字节码文件构造了个统一的运行环境。
字节码
Java所有的指令有200个左右,一个字节(8位)可以存储256种不同的指令信息, 个这样的字节称为字节码( Bytecode)。在代码的执行过程中,JM将字节码解释执行屏蔽对底层操作系统的依赖,JVM也可以将字节码编译执行,如果是热点代码,会通过JIT动态地编译为机器码,提高执行效率。
执行流程
编译流程
类加载器的双亲委托模型
低层次的当前类加载器,不能覆盖更高层次类加载器已经加载的类。如果低层次的类加载器想加载个未知类,需要上级类加载器确认,只有当上级类加载器没有加载过这个类,也允许加载的时候, 才让当前类加载器加载这个未知类
堆 栈
堆:每个JVM实例唯一对应一个堆。应用程序在运行中所创建的所有类实例或数组都放在这个堆中,并由应用所有的线程共享
堆栈:JVM为每个新创建的线程都分配一个堆栈。也就是说,对于一个Java程序来说它的运行就是通过对堆栈的操作来完成的。
Java中所有对象的存储空间都是在堆中分配的,但是这个对象的引用却是在堆栈中分配, 也就是说在建立一个对象时从两个地方都分配内存,在堆中分配的内存实际建立这个对象,而在堆栈中分配的内存只是一个指向这个堆对象的引用而已。
方法区 程序计数器
方法区主要存放从磁盘加载进来的类字节码,而在程序运行过程中创建的类实例则存放在堆里。程序运行的时候,实际上是以线程为单位运行的,当JVM进入启动类的main 方法的时候,就会为应用程序创建一个主线程,main方法里的代码就会被这个主线程执每个线程有自己的Java栈,栈里存放着方法运行期的局部变量。而当前线程执到哪一行字节码指令,这个信息则被存放在程序计数寄存器。
Java(线程)栈
所有在方法内定义的基本类型変量,都会被每个运行这个方法的线程放入自己的機中线程的栈彼此隔离,所以这些变量一定是线程安全的。
线程工作内存 & volatile
Java内存模型规定在多线程情况下,线程操作主内存変量,需要通过线程独有的工作内存拷贝主内存变量副本来进行。
被volatile修饰的共享变量:
保证了不同线程对这个变量进行操作时的可见性,即一个线程修改了某个变量的值,这新值对其他线程来说是立即可见的。
禁止进行指令重排序。
JVM垃圾回收
把堆中的已经不再被使用的对象清理掉。
通过一种可达性分析算法进行垃圾对象的识别,具体过程是:从线程栈帧中的局部量,或者是方法区的静态变量出发,将这些变量引用的对象进行标记,然后看这些被标记的对象是否引用了其他对象,继续进行标记,所有被标记过的对象都是被使用的对象,而那些没有被标记的对象就是可回收的垃圾对象了。
回收方法
清理:将这些垃圾对象占用的内存空间标记为空闲记录在一个空闲列表里,当应用程序需要创建新对象的时候,就从空闲列表中找一段空闲内存分配给这个新对象
压缩:从堆空间的头部开始,将存活的对象拷贝放在一段连续的内存空间中,那么其余的空间就是连续的空闲空间
复制:将空间分成两部分,只在其中一部分创建对象,当这个部分空间用完的时候,将标记过的可用对象复制到另一个空间中
分代垃圾回收
垃圾回收器算法
G1垃圾回收
Java启动参数
标准参数
所有JVM都必须实现的参数
运行模式 -server -client
类加载路径 -cp -classpath
运行调试 -verbose
系统变量 -D
非标准参数
默认jvm实现这些参数,但不保证所有jvm都实现
-Xms 初始堆大小
-Xmx 最大堆大小
-Xmn 新生代大小
-Xss 线程堆栈大小
非Stable参数
各jvm实现会有不同
-XX:-UseConcMarkSweepGC 启用CMS垃圾回收
JVM性能诊断工具
jps:查看所有java进程
jstat:对应用程序的资源和性能进行实时的命令行的监控
jmap:输出内存中的所有对象
jstat:查看堆栈信息
jconsole:可视化工具
Java代码优化
合理谨慎使用多线程
启动线程数= (任务执行时间/(任务执行时间-IO等待时间))*CPU核心数
竞态条件与临界区
Java线程安全
允许被多个线程安全执行的代码称作线程安全的代码
局部变量局部变量存储在线程自己的栈中。也就是说,局部变量永远也不会被多个线程共享。所以, 基础类型的局部变量是线程安全的。局部的对象引用如果在某个方法中创建的对象不会逃逸出该方法,那么它就是线程安全的。对象成员变量对象成员存储在堆上。如果两个线程同时更新同一个对象的同一个成员,那这个代码就不是线程安全的。
秒杀
秒杀的挑战
1.高并发:宽带耗尽、服务器load高,响应缓慢、数据库瘫痪
2.秒杀器:直接下单
应对
服务器准备、宽带准备
新系统;
图片出口带宽估算;CDN准备
架构目标
图片网络带宽;网站并发
系统组成
秒杀列表、详情、下单页面
设计原则
静态化
并发控制、防秒杀器
简化流程
前端优化
秒杀系统
静态化:定时器将动态页面生成静态页面,推送到静态文件系统
秒杀开始判断:js获取秒杀ID、下单URL
浏览控制器:计数器
秒杀器预防
秒杀URL随机生成;计数器限制访问人数
性能优化
中间件(apache,jboss)调优;页面优化;
应急预案
域名分离;保护核心功能;出错页面
持续优化
采用更轻量/快速的服务器;反向代理;数据分片
宅米性能优化
性能测试
性能评估(推算峰值流量);找出调用高的接口;压测接口 (找到要压测的接口;压测接口;优化到可以承受峰值流量)
性能分析
慢SQL、服务器指标、JVM等资源参数
架构优化
订单冷热分离;性能监控(业务监控);
评论 (1 条评论)