性能优化方法论

性能优化方法论

在历经千辛万苦,经过各类性能分析方法,终于找到引起性能问题的瓶颈后,是否是马上就要开始优化了呢?别急,动手以前,你能够先看看下面这三个问题。缓存

  • 首先,既然要作性能优化,那要怎么判断它是否是有效呢?特别是优化后,到底能提高多少性能呢?性能优化

  • 第二,性能问题一般不是独立的,若是有多个性能问题同时发生,你应该先优化哪个呢?网络

  • 第三,提高性能的方法并非惟一的,当有多种方法能够选择时,你会选用哪种呢?是否是总选那个最大程度提高性能的方法就好了呢?并发

若是你能够轻松回答这三个问题,那么二话不说就能够开始优化。ide

好比,在前面的不可中断进程案例中,经过性能分析,咱们发现是由于一个进程的直接 I/O ,致使了 iowait 高达 90%。那是否是用“直接 I/O 换成缓存 I/O”的方法,就能够当即优化了呢?工具

按照上面讲的,你能够先本身思考下那三点。若是不能肯定,咱们一块儿来看看。性能

  • 第一个问题,直接 I/O 换成缓存 I/O,能够把 iowait 从 90% 降到接近 0,性能提高很明显。测试

  • 第二个问题,咱们没有发现其余性能问题,直接 I/O 是惟一的性能瓶颈,因此不用挑选优化对象。优化

  • 第三个问题,缓存 I/O 是咱们目前用到的最简单的优化方法,并且这样优化并不会影响应用的功能。spa

好的,这三个问题很容易就能回答,因此当即优化没有任何问题。

可是,不少现实状况,并不像我举的例子那么简单。性能评估可能有多重指标,性能问题可能会多个同时发生,并且,优化某一个指标的性能,可能又致使其余指标性能的降低。

那么,面对这种复杂的状况,咱们该怎么办呢?

接下来,咱们就来深刻分析这三个问题。

怎么评估性能优化的效果?

首先,来看第一个问题,怎么评估性能优化的效果。

咱们解决性能问题的目的,天然是想获得一个性能提高的效果。为了评估这个效果,咱们须要对系统的性能指标进行量化,而且要分别测试出优化前、后的性能指标,用先后指标的变化来对比呈现效果。我把这个方法叫作性能评估“三步走”。

  1. 肯定性能的量化指标。

  2. 测试优化前的性能指标。

  3. 测试优化后的性能指标。

先看第一步,性能的量化指标有不少,好比 CPU 使用率、应用程序的吞吐量、客户端请求的延迟等,均可以评估性能。那咱们应该选择什么指标来评估呢?

个人建议是不要局限在单一维度的指标上,你至少要从应用程序和系统资源这两个维度,分别选择不一样的指标。好比,以 Web 应用为例:

  • 应用程序的维度,咱们能够用吞吐量和请求延迟来评估应用程序的性能。

  • 系统资源的维度,咱们能够用 CPU 使用率来评估系统的 CPU 使用状况。

之因此从这两个不一样维度选择指标,主要是由于应用程序和系统资源这二者间相辅相成的关系。

  • 好的应用程序是性能优化的最终目的和结果,系统优化老是为应用程序服务的。因此,必需要使用应用程序的指标,来评估性能优化的总体效果。

  • 系统资源的使用状况是影响应用程序性能的根源。因此,须要用系统资源的指标,来观察和分析瓶颈的来源。

至于接下来的两个步骤,主要是为了对比优化先后的性能,更直观地呈现效果。若是你的第一步,是从两个不一样维度选择了多个指标,那么在性能测试时,你就须要得到这些指标的具体数值。

仍是以刚刚的 Web 应用为例,对应上面提到的几个指标,咱们能够选择 ab 等工具,测试 Web 应用的并发请求数和响应延迟。而测试的同时,还能够用 vmstat、pidstat 等性能工具,观察系统和进程的 CPU 使用率。这样,咱们就同时得到了应用程序和系统资源这两个维度的指标数值。

不过,在进行性能测试时,有两个特别重要的地方你须要注意下。

第一,要避免性能测试工具干扰应用程序的性能。一般,对 Web 应用来讲,性能测试工具跟目标应用程序要在不一样的机器上运行。

好比,在以前的 Nginx 案例中,我每次都会强调要用两台虚拟机,其中一台运行 Nginx 服务,而另外一台运行模拟客户端的工具,就是为了不这个影响。

第二,避免外部环境的变化影响性能指标的评估。这要求优化前、后的应用程序,都运行在相同配置的机器上,而且它们的外部依赖也要彻底一致。

好比仍是拿 Nginx 来讲,就能够运行在同一台机器上,并用相同参数的客户端工具来进行性能测试。

多个性能问题同时存在,要怎么选择?

再来看第二个问题,开篇词里咱们就说过,系统性能老是牵一发而动全身,因此性能问题一般也不是独立存在的。那当多个性能问题同时发生的时候,应该先去优化哪个呢?

在性能测试的领域,流传很广的一个说法是“二八原则”,也就是说 80% 的问题都是由 20% 的代码致使的。只要找出这 20% 的位置,你就能够优化 80% 的性能。因此,我想表达的是,并非全部的性能问题都值得优化

个人建议是,动手优化以前先动脑,先把全部这些性能问题给分析一遍,找出最重要的、能够最大程度提高性能的问题,从它开始优化。这样的好处是,不只性能提高的收益最大,并且极可能其余问题都不用优化,就已经知足了性能要求。

那关键就在于,怎么判断出哪一个性能问题最重要。这其实仍是咱们性能分析要解决的核心问题,只不过这里要分析的对象,从原来的一个问题,变成了多个问题,思路其实仍是同样的。

因此,你依然能够用我前面讲过的方法挨个分析,分别找出它们的瓶颈。分析完全部问题后,再按照因果等关系,排除掉有因果关联的性能问题。最后,再对剩下的性能问题进行优化。

若是剩下的问题仍是好几个,你就得分别进行性能测试了。比较不一样的优化效果后,选择能明显提高性能的那个问题进行修复。这个过程一般会花费较多的时间,这里,我推荐两个能够简化这个过程的方法。

第一,若是发现是系统资源达到了瓶颈,好比 CPU 使用率达到了 100%,那么首先优化的必定是系统资源使用问题。完成系统资源瓶颈的优化后,咱们才要考虑其余问题。

第二,针对不一样类型的指标,首先去优化那些由瓶颈致使的,性能指标变化幅度最大的问题。好比产生瓶颈后,用户 CPU 使用率升高了 10%,而系统 CPU 使用率却升高了 50%,这个时候就应该首先优化系统 CPU 的使用。

有多种优化方法时,要如何选择?

接着来看第三个问题,当多种方法均可用时,应该选择哪种呢?是否是最大提高性能的方法,必定最好呢?

通常状况下,咱们固然想选能最大提高性能的方法,这其实也是性能优化的目标。

但要注意,现实状况要考虑的因素却没那么简单。最直观来讲,性能优化并不是没有成本。性能优化一般会带来复杂度的提高,下降程序的可维护性,还可能在优化一个指标时,引起其余指标的异常。也就是说,极可能你优化了一个指标,另外一个指标的性能却变差了。

一个很典型的例子是我将在网络部分讲到的 DPDK(Data Plane Development Kit)。DPDK 是一种优化网络处理速度的方法,它经过绕开内核网络协议栈的方法,提高网络的处理能力。

不过它有一个很典型的要求,就是要独占一个 CPU 以及必定数量的内存大页,而且老是以 100% 的 CPU 使用率运行。因此,若是你的 CPU 核数不多,就有点得不偿失了。

因此,在考虑选哪一个性能优化方法时,你要综合多方面的因素。切记,不要想着“一步登天”,试图一次性解决全部问题;也不要只会“拿来主义”,把其余应用的优化方法原封不动拿来用,却不通过任何思考和分析。

相关文章
相关标签/搜索