This is the 23rd day of my participation in the Gwen Challenge.More article challenges

Preface:

With the business iteration and the increase of requests, we will find that the throughput of the system gradually enters the bottleneck. During the peak period, there will be a series of problems in our system due to some reasons, such as slow response, request failure, and even the service will be directly suspended. When your system reaches this point, When tuning memory and GC for Java applications, we should base our decisions on key performance metrics. Which ones should we focus on? Today we mainly talk about some of the time when we optimize the project through those indicators to observe your project, in order to lock your optimization point, this is also xiaobian has been doing things recently, here to write some heart experience;

GC performance indicators:

  1. Throughput: The percentage of time an application spends on non-GC
  2. GC load: As opposed to throughput, refers to the percentage of time an application spends on GC
  3. If you are responsible for a service that requires no more than 5 seconds for any request, then your maximum GC pause duration should not exceed 5 seconds. Because during a GC pause, the entire JVM pauses and no business code can be executed, the maximum GC pause time is important;
  4. An interactive application requires as little pause time as possible, whereas a non-interactive application, of course, wants as little GC load as possible.

Select the memory capacity configuration

Young generation:

  • Response time first application: Set as large as possible, directly close to the system’s minimum response time limit (selected according to the actual situation), in this case, the frequency of GC occurring in the younger generation is also minimal, and at the same time, reduce the objects arriving in the old age.
  • Throughput first applications: Settings as far as possible big, may reach the level of Gbit, because no response time requirements, garbage collection can be done in parallel, the application of generally more than 8 CPU to avoid setting up is too small, when the new generation set through the hours will cause YGC times more frequently, may cause YGC object directly into old age, if at that time, the old s full, will trigger the FGC;

The old s

  • Response time first applications: In the old days, concurrent collectors were used, so the size needs to be carefully set. Generally, some parameters such as concurrent session rate and session duration should be taken into account. If the heap is set too small, it may cause memory fragmentation, high recycle frequency, and the use of traditional token clearing methods for application pauses. If the heap is large and takes a long time to collect, the optimal solution is usually to look at some other data: concurrent garbage collection information, the number of concurrent collections in persistent generation, traditional GC information, and the proportion of time spent collecting in young generation versus old generation.

  • Throughput first applications: Generally, throughput first applications have a large young generation and a small old generation. The reasons are as follows: Most short-term objects can be reclaimed as much as possible, while mid-term objects are reduced and the old generation stores long-term objects.

GC overhead can also cause throughput to plummet, making applications indescribably slow. In addition, tuning GC early can help you avoid heap size allocation problems. To start, you can choose any heap size from 1GB to 8GB. When you choose the right heap size, the concept of old and new generation objects is not needed. In summary, the heap size should depend on the ratio of old to new generation objects, previous GC optimizations, and the set of objects (that is, how much memory all objects occupy).

According to memory tuning guidelines, you can only choose two of the three at best: throughput, latency, and CPU

  • If you want better throughput and latency, you have to sacrifice CPU consumption
  • If you want better throughput and CPU consumption, you have to sacrifice latency
  • If you want better latency and CPU consumption, you have to sacrifice throughput

Key application optimization

In addition to optimize the ratio of the memory is actually a lot of our time is to optimize the key code, such as small make up of the system is every 10 minutes will appear YGC particularly high frequency, and there will be some type of recycling precipice, the reason is that our code in every 10 minutes will have multiple timing task to do something to create a large number of objects of task; Therefore, YGC frequently occurs every time the task is executed, which causes the system to slow down at that time. This is my GRAPH of YGC and GC pause times

This time you need to optimize your code, according to their own business conditions to adjust;

Ok! This is the end of today’s article, I hope it can be helpful to you, there are wrong places I hope you can put forward, grow together;

Neat makes for great code, and there’s only so much detail