简体   繁体   English

在不同步的情况下在多个线程之间共享和更新变量

[英]sharing and updating a variable among multiple threads without synchronisation in java

I am trying to simulate a 100 m running race program in java using multithreading. 我正在尝试使用多线程在Java中模拟一个100 m运行的竞赛程序。 In this attempt I made a Atomic integer variable which should be common to all threads. 在此尝试中,我制作了一个原子整数变量,该变量应为所有线程所共有。 This variable should increase by 1 after each thread crosses 100. unfortunately the result is not as expected.This is my attempt at the program. 每个线程超过100后,此变量应增加1。不幸的是结果与预期不符。这是我在程序中的尝试。

    package running;
    import java.util.concurrent.atomic.*;
    public class Employee implements Runnable{
    AtomicInteger j = new AtomicInteger();

public void run() {

for(int i=1;i<=100;i++){
        System.out.println(Thread.currentThread().getName()+" " + i);
        try {
             Thread.sleep(100);
        } 
        catch (InterruptedException e) {
             e.printStackTrace();
        }
        if(i==100)
        {
             System.out.println(Thread.currentThread().getName()+" is in "+j.incrementAndGet()+" place");

        }
}
} 

public static void main(String []args) throws Exception{
Employee e= new Employee();
Thread a= new Thread(e,"First");
Thread b= new Thread(e,"Second");
Thread c= new Thread(e,"Third");
Thread d= new Thread(e,"Fourth");
Thread f= new Thread(e,"Fifth");
a.start();
b.start();
c.start();
d.start();
f.start();

}
}

To demonstrate my problem in an understandable way I have added a print statement to check the running of the threads in the code . 为了以一种可以理解的方式演示我的问题,我添加了一条print语句来检查代码中线程的运行情况。 Here is the last 10 lines of the output. 这是输出的最后10行。

Second 100
Fourth 100
Third 100
Fifth 100
First 100
Fourth is in 3 place
Third is in 1 place
Second is in 2 place
Fifth is in 4 place
First is in 5 place

I don't see unexpected results. 我没有看到意外的结果。 when I run your code I get: 当我运行您的代码时,我得到:

First is in 1 place
Third is in 3 place
Second is in 4 place
Fifth is in 2 place
Fourth is in 5 place

if I run the code again, I get this: 如果我再次运行代码,则会得到以下信息:

First is in 1 place
Second is in 2 place
Fifth is in 4 place
Fourth is in 3 place
Third is in 5 place

as expected, the results are not always the same. 不出所料,结果并不总是相同。 and the AtomicInteger is not losing any update. 并且AtomicInteger不会丢失任何更新。

if you want the results to be displayed in order, you need to synchronize the part of the code that registers the results. 如果要按顺序显示结果,则需要同步注册结果的代码部分。 (to make sure that the first thread that reaches 100 will write that information before the next thread reaches 100) for example, see below: (以确保到达第一个线程的第一个线程将在下一个线程到达100之前写入该信息),例如,请参见以下内容:

import java.util.ArrayDeque;
import java.util.Queue;
import java.util.concurrent.atomic.AtomicInteger;

public class Employee implements Runnable {
    private static AtomicInteger j = new AtomicInteger();
    private static Queue<String> queue = new ArrayDeque<>();

    public static void main(String[] args) throws Exception {
        Employee e = new Employee();
        Thread a = new Thread(e, "First");
        Thread b = new Thread(e, "Second");
        Thread c = new Thread(e, "Third");
        Thread d = new Thread(e, "Fourth");
        Thread f = new Thread(e, "Fifth");
        a.start();
        b.start();
        c.start();
        d.start();
        f.start();

        a.join();
        b.join();
        c.join();
        d.join();
        f.join();

        while (queue.size() > 0) {
            System.out.println(queue.remove());
        }

    }

    public void run() {

        for (int i = 1; i <= 100; i++) {
            System.out.println(Thread.currentThread().getName() + " " + i);
            try {
                Thread.sleep(100);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            synchronized (queue) {
                if (i == 100) {
                    queue.add(Thread.currentThread().getName() + " is in " + j.incrementAndGet() + " place");
                }
            }
        }
    }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM