架构师训练营 week7 作业
作业一
性能压测的时候,随着并发压力的增加,系统响应时间和吞吐量如何变化,为什么?
三个阶段。
横轴是系统资源,也可以是并发数。
纵轴是TPS,也就是处理能力。
不断的增加并发数,会形成一个抛物线。
客户端用多线程的方式模拟并发。100个线程是模拟100个并发。然后不断增加测试的线程。300个,500个。。。然后观察。
a-b 阶段
近似线性的增加。
此阶段资源空闲充足,所以会以近似线性的速率增加。
b-c阶段
缓慢增加,达到最大值。
主要还是资源的消耗。一开始空闲的,可以创建足够的资源处理。并发数增加这些资源还是够用的,单位时间内处理的请求书也越多。过了某个点,比如48核CPU创建了200个线程,就有线程在等待的状态,响应时间就变长了,然后增加就慢了。
c-d阶段
TPS反而下降。为什么呢?
资源耗尽了,比如内存用磁盘置换了,处理能力急剧下降。到了最后什么都处理不了了,一堆线程都在等待,所有请求都无法响应了。
应该让系统运行在a->b 还是 b->c点?
a->b,安全,但是成本高。 b->c,节约资源。
而且头脑要清晰的知道为什么这么决策。依据是什么的。
总结
性能测试
基础
要优化的点是什么?优化后达到什么效果?
--- 性能测试是性能优化的基础。
最终目的
目的是让用户感受快,好。目的是提升体验,主观感受。
主观视角: 用户感受的性能。体验。
用户点了提交按钮,有个进度条,提升体验
客观视角: 实际的性能,性能指标衡量的性能。
主要关注的是客观的指标。
性能测试指标
响应时间
发出请求,到收到最后响应的时间。直观的反应了快慢。
并发数
同时处理的请求的数目。某一个时间点同时在处理的请求数目。
经常会和在线用户数混淆,比如描述成并发数有几个亿。通常并不是很大的数字。淘宝最高峰也就是百万级的并发数。
吞吐量
单位时间内系统处理的请求数目。比如每秒钟处理的请求数目
TPS:每秒事务数
HPS:每秒Http请求数
QPS:每秒查询数
吞吐量 = (1000 * 响应时间ms) * 并发数
性能计数器
一类数据指标。System Load,对象与线程数,内存,CPU,磁盘和网络IO等。
通常会设置一些阈值,超过时候说明负载太大了,上报告警。
性能测试方法
这些指标怎么得到的?
性能测试是一个总称,具体分类:
性能测试
对系统不断施加压力,验证系统在资源可接受范围内,是否达到性能瓶颈
负载测试
继续施加压力。看性能指标是什么样,最大是什么样。什么时候会耗尽。耗尽的时候其他指标是什么样子。
压力测试
达到处理能力最大后,继续施加压力,直到崩溃。从而知道系统的极限能力。即最大压力承受能力。
稳定性测试
系统在特定硬件,软件,网络环境下。给系统加载一定业务压力,让系统运行较长的时间,以检测系统是否稳定。
在生成环境,压力通常不是均匀的,是波浪形的。需要模拟这种不均匀对系统的压力。
有时候高并发的压力,并不一定会有问题,一直高压反而没问题。
测试曲线
随着压力的增加,响应时间和吞吐量如何变化
三个阶段。
横轴是系统资源,也可以是并发数。
纵轴是TPS,也就是处理能力。
不断的增加并发数,会形成一个抛物线。
客户端用多线程的方式模拟并发。100个线程是模拟100个并发。然后不断增加测试的线程。300个,500个。。。然后观察。
a-b 阶段
近似线性的增加。
b-c阶段
缓慢增加,达到最大值。
c-d阶段
TPS反而下降。为什么呢?
主要还是资源的消耗。一开始空闲的,可以创建足够的资源处理。并发数增加这些资源还是够用的,单位时间内处理的请求书也越多。过了某个点,比如48核CPU创建了200个线程,就有线程在等待的状态,响应时间就变长了,然后增加就慢了。
资源耗尽了,比如内存用磁盘置换了,处理能力急剧下降。到了最后什么都处理不了了,一堆线程都在等待,所有请求都无法响应了。
应该让系统运行在a->b 还是 b->c点?
a->b,安全,但是成本高。 b->c,节约资源。
而且头脑要清晰的知道为什么这么决策。依据是什么的。
性能测试怎么做?
客户端模拟并发请求,测试那些性能指标。
全链路压测
数据隔离
逻辑隔离
正常数据和测试数据写到一起,用特殊标志位来区分用户数据和测试数据。
虚拟隔离
通过mock,写时不真写,但是mock会影响测试结果。
物理隔离
写的时候区分,写道不同物理环境。包括存储,缓存,搜索引擎等。
流量构造
如何模拟高并发的请求。
天猫双十一模拟数y流量,利用CDN服务器。CDN节点部署流量引擎,CDN部署在全国各地各个运营商里,通过流量控制台管理。可以稳定输出每秒一千万请求。
压测平台化
场景越来越多,可以向整个资源池申请流量。
性能优化:分层思想
两个基本原则
你不能优化一个没有测试的系统
你不能优化一个你不了解的软件
Spark 应用性能测试
CPU,内存,网络吞吐量,磁盘吞吐量,task time等指标
一般方法
性能测试,获得性能指标
指标分析,活得瓶颈点,性能和资源瓶颈点
架构和代码分析,寻找性能和资源瓶关键所在
架构和代码优化,优化关键技术点,平衡资源利用
性能测试,验证成果,进行闭环
系统性能优化的分层思想
直观的思路,就是看看代码怎么写的。
由上到下:
1.机房与骨干网络的性能优化
异地多活是标配--特点:高可用。也能提高性能。
专线网络和自主CDN--在自主CDN进行专项优化。
2.服务器和硬件
使用更好的CPU,内存,硬盘等。
Spark例子-》发现大量在处理网络传输。
进行压缩后,消耗了CPU时间,相互抵消。
优化方案:优化网卡,10G网卡替换1G网卡。
3.操作系统的性能优化
4.虚拟机
5.基础组件,缓存,连接池
6.软件架构
三板斧
缓存
异步
集群
7.软件代码
遵循设计模式和设计原则。很多时候代码性能问题不是因为有什么技术挑战,而是单纯的代码太烂了。
并发编程,多线程和锁
资源复用,资源池与对象池
异步编程,生产者/消费者
数据结构
锁原语CAS
CAS 概念
CAS (V,E,N)
V 内存地址E 表示预期值N 表示新值
if (&V == E) V -> N;else do nothing
CAS 是一种系统原语,执行必须连续,在执行过程中不允许被中断。
一个例子:
1.在内存地址V当中,存储着值为10的变量。2.此时线程1想要把变量的值增加1。对线程1来说,旧的预期值A=10,要修改的新值B=11。3.在线程1要提交更新之前,另一个线程2抢先一步,把内存地址V中的变量值率先更新成了11。4.线程1开始提交更新,首先进行A和地址V的实际值比较(Compare),发现A不等于V的实际值,提交失败。5.线程1重新获取内存地址V的当前值,并重新计算想要修改的新值。此时对线程1来说,A=11,B=12。这个重新尝试的过程被称为自旋。
乐观锁 ¥ 悲观锁
从思想上来说,Synchronized属于悲观锁,悲观地认为程序中的并发情况严重,所以严防死守。CAS属于乐观锁,乐观地认为程序中的并发情况不那么严重,所以让线程不断去尝试更新。
CAS的优缺点
优点
非阻塞的轻量级的乐观锁,通过CPU指令实现,在资源竞争不激烈的情况下性能高,相比synchronized重量锁,synchronized会进行比较复杂的加锁、解锁和唤醒操作。
缺点
ABA问题: 线程C、D;线程D将A修改为B后又修改为A,此时C线程以为A没有改变过,java的原子类AtomicStampedReference,通过控制变量值的版本号来保证CAS的正确性。具体解决思路就是在变量前追加上版本号,每次变量更新的时候把版本号加一,那么A - B - A就会变成1A - 2B - 3A。自旋时间过长,消耗CPU资源,如果资源竞争激烈,多线程自旋长时间消耗资源
CAS in java
锁的记录是记录在对象头里,Mark word里。一个对象的锁是相同的。如果想要进入某个方法,一定要先获得锁。正常的时候Mark word是64位,lock标记位是0。
锁状态
偏向锁一段同步代码一直被一个线程访问,那么该线程自动获取锁,降低获取锁的代价。
轻量级锁当锁是偏向锁时,被另一个线程所访问,偏向锁会升级为轻量级锁,其他线程会通过自旋的形式尝试获取锁,不会阻塞,提高性能。
重量级锁当自旋的次数达到一定次数时,膨胀为重量级锁,此时会阻塞其他线程。
评论