Core concurrency: What CAS that? How Java8 is to optimize the CAS? I do not understand you play

You may have heard say in Java and contracting, if you want to read in Java and contracting, its core is to first understand the mechanism CAS, CAS can be said that because of the underlying implementation and contract principles.

Today will take you understand how CAS is to ensure that atomic operations, as well as what the CAS Java8 optimization.

synchronized: overkill

Let's look at a few lines of code:

public class CASTest {
    static int i = 0;

    public static void increment() {
        i++;
    }
}

If there are 100 threads simultaneously call increment () method to perform i increment operation, the result would be 100 i do?

Learn multithreaded students should know that this method is not thread-safe, since i ++ is not an atomic operation , it is difficult to get 100.

Explain why there will not be a bit 100 (known may skip), i ++ this operation, the computer is divided into three steps need to be performed.
1, reads the value of i.
2, i is increased by 1 to
3, the final result is written into the memory i. Therefore, if the thread A reads the value i i = 0, this time also thread B reads the value of i i = 0. Then A i is incremented to 1, and then written to memory, when i = 1. Then, i is incremented by 1 to be B, then thread B is i = 1, then the thread B i written to memory, the memory at this time i = 1. In other words, the thread A, B i have been on the increase since, but the end result is 1, not 2.

Then how to do it? Solving strategies are generally add a lock to this method, as follows

public class CASTest {
    static int i = 0;

    public synchronized static void increment() {
        i++;
    }
}

After the addition of synchronized, you can only have one thread can enter the increment () method has. In this way, it will not appear thread-unsafe. I do not understand synchronized can see this article: thoroughly get to know synchronized (from biased lock to lock heavyweight)

However, a simple increment operator, on the addition of synchronized synchronization, feeling like a little overkill, after the addition of synchronized keyword, when there are many threads to compete increment this method when the lock is to get will be blocked out the method, finally, to wake them up, and blocking / wake these operations are very time-consuming.

Here Some may say, synchronized to the JDK1.6 after not doing a lot of optimization yet? Yes, it has really done a lot of optimization, increased biased locking, lightweight lock, etc. However, even if these increases, when many threads to competition, the cost is still a lot, do not believe you introduced me to another article: they get completely synchronized (lock biased from heavyweight to lock)

CAS: such a trivial matter to me

That there is no other method instead of locking synchronized methods, and to ensure the increment () method is thread safe?

We look, if I use the following in this way, can guarantee increment is thread safe? Proceed as follows:

1, thread reads from memory the value of i, if the value of i is 0 at this time, we called k value it, i.e. case k = 0.

2, so that j = k + 1.

3, compared with the value k i in memory, and if they are equal, this means that no other thread modified value of i, we put j (in this case 1) the value written to memory; if not equal ( i mean values ​​are modified by other threads), we would not have the value of j written to memory, but again jumps back to step 1 to continue these three operations.

Translated into code words is this:

public static void increment() {
    do{
        int k = i;
        int j = k + 1;
    }while (compareAndSet(i, k, j))
}

If you go to the simulation, you will find, write thread-safe.

Some may say here, the third step of compareAndSet this operation not only to read the memory, but also relatively dry, write to memory and other operations ,,, This step in itself is not thread-safe ah?

If you can think of this show that you really have to think to simulate this process, but I want to tell you is that this compareAndSet operation, he in fact only the corresponding operating system of a hardware operating instructions , although there appears to many operations on the inside, but the operating system can guarantee that he is atomic execution.

For a very long instruction word in English, we like to use it to call him for short, so we put compareAndSet called CAS it.

So it occurs, the use of this mechanism CAS wording is thread-safe, in this way, can be said that there is competition not lock, there was no obstruction of things, can make a better program execution.

In Java, this class also provides the CAS atoms, for example:

  1. AtomicBoolean
  2. AtomicInteger
  3. AtomicLong
  4. AtomicReference

How you use it? I will take the example above were revised it, the code is as follows:

public class CASTest {
    static AtomicInteger i = new AtomicInteger(0);

    public static void increment() {
        // 自增 1并返回之后的结果
        i.incrementAndGet();
    }
}

CAS: Who secretly changed my values

Although the mechanism of this CAS can guarantee increment () method, but there are still some problems, for example, when thread A third step is about to be executed, the thread B i value plus 1, followed immediately reduce the value of i 1, then thread a executes the third step, this time no one thought thread a is the modified value of i, since i have not changed. And that is what we usually say the ABA problem .

For the value of the basic types, this the digital change in the value back to the original is not much impact, but if it is for a reference type, it would have a huge impact on.

To a version control it

ABA To solve this problem, we can introduce version control, for example, each time a thread modifies the value of the referenced version will be updated, although two threads hold the same references, but they have different versions, so, we can prevent ABA problem. Java provides AtomicStampedReference this class, you can perform version control.

Java8 optimization of the CAS.

As a result of this CAS is no mechanism for locking methods, so all the threads can enter the increment () This method, if too many threads into this method, there will be a problem: Every time there is a thread to be executed when the third step, the value of i always have been modified, so the thread and continue to return to the first step to start over.

This will cause a problem: Because the thread too dense, too many people want to change the value of i, and then most people will modify unsuccessful, in vain the cycle where resource consumption.

To solve this problem, Java8 introduced a cell [] array, its working mechanism is this: if there are five threads To i perform increment operator, less likely because the five threads, then, not a lot of conflict of , then let them follow the normal as ever, by the use of CAS from it.

However, if there are 100 threads to be on the i increment operator, then, this time, the conflict will be greatly increased, the system will assign to these different threads of cell array elements go, if cell [10] There are 10 elements in it and initializing the elements is 0, then the system will put 100 threads into 10 groups, each element of a cell array which do increment operation, so the final value of the cell array 10 elements are 10 , the value of this system is summarized in the element 10 and finally to obtain 100, which two, is equivalent to 100 threads 100 to i were self-energizing operation.

Of course, I'm just here to give an example to illustrate the general principle of Java8 CAS optimized specifically we are interested can go to the source, or to search the corresponding article oh.

to sum up

CAS understanding of the principles is very important, it is the cornerstone of AQS, and AQS is the cornerstone of concurrency framework, the next time, I will write an article AQS.

Brother dei, if I feel well written, might favor

1, pay attention to my original micro-channel public number " handsome to play programmed " on time push dry technical articles every day, focusing on write algorithm + basic computer knowledge (computer network + operating system + database + Linux), I heard that attention is not good Oh will become outstanding.

2, to a point I praise chant , so that more people can see this article, by the way inspired me, hee hee.

Published 79 original articles · won praise 20000 + · views 1.63 million +

Guess you like

Origin blog.csdn.net/m0_37907797/article/details/104710698