00:00
诶下边咱们就重点的看其中这两个啊,一个呢叫做这个吞吐量,一个呢叫做暂停时间,诶这也是咱们后边呢,叫GM调优的时候呢,重点关注的两大指标,诶首先呢,我们看这个叫吞吐量,吞吐量呢,呃,它这个概念咱们刚才已经介绍过了,就是呢用户呃它这个线程呃执行所花费的时间除以呢叫呃用户线程花费的时间加上垃圾回收的呃线程花费的这个时间,比如说我们这个虚拟呢,总共运行了100分钟,那么垃圾回收呢,花掉了一分钟。哎,那么吞吐量呢,我们认为九十九十九,那因为呢,这个99分钟呢,实际上都在这个执行用户线上对吧,再除以这个一加上99,哎,我们这个结果呢,就是99%,但吞吐量呢,就99%,这个数呢,当然当然咱们说越大越好对吧?诶越大越好哈,那如果说呢,我这只是随便举个例子啊,如果说真能达到这个数的话,那这个性能实际上是非常不错的哈,哎,性能那就太好了。行,那么下边说在这种情况呢,情况下呢,说应用程序呢,能够容忍较高的暂停时间,哎,能容忍较高的暂停时间,因此呢,高吞吐量的应用程序呢,有更长的这个时间基准快速响应呢,是我们不必考虑的。
01:10
哎,这个快速响应呢,就是我们关注呢,它的这个暂停时间,咱不用过多的去去关注这个事儿,诶我们在一个诶时间段之内,我们希望呢,这个呃,充作量越大越好。啊,吞吐量越大越好,那这时候的话,你可能一次性这个暂停时间呢,会稍微的长一些,那那如何呢,拿它跟我们说的暂停时间做对比,我这呢画了一个图啊,这呢也是在我们这个里边啊画了一个图啊,当然呢,能够去体会一下啊,你看。我们从这个吞吐量的角度来讲,比如说我们这个程序呢,执行一共化了这个六秒钟,六秒钟的这个时间,就是整个这个区域是吧,那么在这个六秒钟的时间之内,这个蓝色呢叫用户线程,这个红色呢叫垃圾回收的这个线程啊,它所花的这个时间,那么这呢,实现了两这个执行过两次啊,那一次呢是200毫秒。那相较于我们这个来讲的话呢,这200毫米量才算是比较长的,对吧,那么对于我们这个程序来讲,它的这个呃吞吐量是多少呢?呃,那很简单,我们只需要呢,是不是拿这个这是六,呃六的话,我们就相当于是6000吧,哎,6000毫秒是吧,它减去这个400。
02:12
然后呢,再除以这个是不是6000就可以了。哎,这个呢,就是我们这个算出来一个叫吞吐量。啊,这是一个吞吐量,OK,那就是我们在一个时间段之内的话呢,有可能这一次呢,花的这个时间呢,会单次呢会长一点,但是没关系啊,只要呢,你在这个时间段之内呢,这个蓝色的占的比例偏高就行,我们呢就称为呢是注重这个吞吐量的一个,或者叫高吞吐量的一个行为。诶跟我们下边这个咱们做个对比啊,这个暂停时间呢,叫I part time,哎,暂停时间啊,我们也可以对应的那个词呢,叫做响应时间是吧。说暂停时间呢,是指在一个时间段之内呢,呃,应用程序这个线程的暂停,然后让我们这个JC线程呢,来进行执行的一个状态啊,就是垃圾回收线程啊,也就是我们所谓的那个stop,走word这个时间啊,比如说呢,这个JC期间呢,这个100毫秒的这个暂停时间,就意味着在100毫秒之内呢,我们没有任何的这个用户线程啊,是活跃的啊很好理解是吧,那比如呢,还是以我们刚才这个程序啊,如果说咱们注重这个暂停时间的话呢,呃,比如我们这里边,你看每次呢,花的是100毫秒,那相较于这个200毫秒,我们这个呢,是不是就注重这个暂停时间了是吧,希望这个暂停时间短一点,哎,但是呢,我们这个暂停时间短了,它回收的频率呢,你发现它明显高了。
03:26
啊,这呢一共回收过五次啊,上面呢就回收过两次啊,那么整个来看的话呢,大家会发现我们上面这个程序啊,如果咱们从这个吞吐量上来衡量这呢,我调一个这个计算器啊。从这个吞吐量上简单来衡量的话呢,我们上边这个刚才说了,呃,实际上呢,是呃6000减去400是不是五千五千六百,呃让他呢,去除以咱们这个6000。你看得到这个数是它是吧,哎,这个我们截个图这样吧。哎,这么着是吧,这呢是咱们上边这个的吞吐量啊,上面的吞吐量,你看我们下边的吞吐量的话呢,这一共是有五个,哎五个这个100那就500,那咱们上面呢,就是五千五了是吧?哎,他呢去除以咱们这个6000。
04:12
哎,等于是这个数。行是这个数行,那么通过这两个数来看的话呢,明显咱们上边这个数,它的一个呃,吞吐量是不是要更好一些啊呃,因为这个垃圾回收就花了400毫秒是吧?诶更多的时间呢,用来执行用户线程,它的通用量更好,呃下边这个通量就差一些,哎,差一些,但是我们下边这个程序的话,你会发现呢,它的这个呃是不是暂停时间呢,效果要更好一些啊啊因为我们这个呢,你看呃每次呢,都比它这个时间要短啊,所以它呢,下边这个时叫低延迟的。啊是D延迟的,那可能有同学会想说,那你下边这个没有可能说它就执行过两次或者是三次吗?诶你想想啊,我们这个暂停时间短的话呢,它就意味着我们这个内存空间你肯定要小一些了。因为你这个面对的场景肯定要小一点,那你要内存空间小,我们这个这些的频率是不是自然而然的就会高一些啊。
05:06
是吧,很正常的啊,那从另外一个角度来说的话呢,你想你每次花的这个时间短了,我们是不是频率上是不是要高一些,就跟大家说洗衣服一样。啊,你呢是每天都洗,那你每天花的时间短一点嘛,那你频率就高一些是吧?啊上面这个就这样,而且呢,就是由于你这块呢,用户线程跟我们这个垃圾回收线程是不是还得呃通过这个CPU呢,有可能是吧,咱们还会进行不断的切换,切换呢也需要花时间,所以你下边这个吞吐量呢,那你老切换嘛,肯定不如我们上边这个切换的次数比较少的,这个吞吐量呢要高一些。啊,也很好理解是吧,OK。哎,通过刚才我这样的例子来说明啊,大家能够知道这里边这个吞吐量呢,和我们这个暂停时间啊,他俩是矛盾的对吧?哎,他俩是有点矛盾的,OK,那高存储量较好,哎是因为呢,这会让这个应用程序的最终用户感觉呢,就是只有应用程序呢,线程在在执行啊,因为呢,我们单位时间段之内呢,是不是做的事更多呀。
06:02
对吧,哎,蓝的做的蓝的执行的多,就是相当于我们做的事更多嘛,就感觉上呢,只有用户现场在执行似的啊,就成这样了啊,那吞吐量高的话呢,我们这个程序的运行呢,就越快啊,就是因为你做的事更多对吧,那么低暂停时间我们也称为呢叫低延迟,这个低延迟较好呢,是从最终用户的体验的角度来看啊,不管是这些还是其他这个原因导致的一个应用程序被挂起始终是不好的啊,那比如说我们是做这种跟用户交互比较多的这个程序的时候呢,咱们是不是尽量的关注的叫诶低延迟呢。因为有的时候呢,用户呢,相里200毫秒一个暂停,用户感觉的说感觉有点卡似的是吧?诶它会影响用户的一个体验,所以呢,对于这种交互式的应用程序呢,咱们更多关注的叫做诶第一暂停事件,诶这个注意啊,诶他俩呢是互相矛盾的是吧?那如果说你要是选择这个吞吐量优先的话呢,我们必然需要降低内存回收的一个执行频率了。啊,你这个频率要低一点,哎,就是我们这里边这个图频率低了,哎,那自然而然的话呢,我们这个吞吐量呢,它就会往上涨啊,那你要说希望这个,哎关注这个低延迟的话呢,那自然而然的这个频率呢,肯定就上去了,那每次呢,这个回收的这个时间呢,相应的用的就短一些,但是导致的问题就是吞吐量呢会下来。
07:17
哎,他俩呢,是一对矛盾体啊,注意一下。好啊,那知道这样一个情况之后呢,我们接着来看啊说呢,在设计或者使用这个这些算法的时候呢,我们必须呢明确咱们的目标,就是既然呢他俩矛盾,那我们诶要怎么去这个设计这个JC啊,哎说呢,一个垃圾回收器的这个算法呢,只能够哎针对两个目标之一。啊,只能针对于吞吐量,或者针对这个暂停时间,哎,咱们之前呢,是不是也说到了,像这个parallel呢,哎,它呢主要针对是这个吞吐量啊对这个CMS啊,它呢主要针对的这叫低延迟。啊,它的低延迟,那G是什么特点呢?哎,咱们接着往下说啊。这个呃,关注于吞吐量,或者关注于暂停时间,或者找到二者的一个折中方案啊,那么G1是什么特点呢?你看这里边儿我提到现在这个标准啊,在最大吞吐量优先的情况下呢,叫降低停顿时间。
08:12
再说一遍哈,就是相当于是我们在找这个折中的一个方案啊,在最大吞吐量优先的情况下。哎,降低这个停顿时间,那么对于我们说这个G1,或者咱们叫这个g first垃圾回收器来说呢,它呢,诶实际上呢,也是会关注这个吞吐量的。啊,也是会关注这吞吐量的啊,就是在这个吞吐量尽量大的情况下呢,我们把这个呃暂停时间呢,控制在一个可确定的一个范围内,比如说要求每次垃圾回收这个时间呢,诶你都要控制在这个十毫秒以内。诶,就是说在可控的暂停时间之内,我们尽量大的提高吞吐量。也就是说从用户的角度,比如说我们这个交互的场景比较多的时候啊,诶跟用户交流的场景多的时候呢,我们比如说十毫秒是可以接受的,OK,那我们呢,就设置一个暂停时间,最大呢是十毫秒,希望呢所有的这个垃圾回收都在这个十毫秒以内,在这个情况下呢,我们把这个吞吐量呢给它往上提。
09:08
就是按住一个指标,然后呢,我们另外的这个尽量的高,诶这呢,就是我们这个G1呢,想要追求的一个目标,包括呢,咱们后边要讲的这个叫ZJC啊,甚圳都JC等等,他们呢,诶都是以追求这个,呃,在可控的暂停时间的范围之内呢,尽量的增加吞吐量。OK,诶这个呢,相当于也指明了咱们这个垃圾回收它的一个未来的发展方向,对吧?诶这个呢,我们就说清楚了。好,这呢,就是我们把这个吞吐量跟暂停时间给大家呢,做了一个对比,做了一个明确。
我来说两句