简体   繁体   English

Java线程(种族条件)

[英]Java Threads (Race Condition)

I have doubt in the following piece of code. 我对以下代码有疑问。 In this i expect race condition to occur for both the static variables 'a' and 'b' and the expect the output for both the variables to be less than 1000. However, the expected behaviour is not observed when i execute the below code as shown ie the output for b is always 1000. But, when i uncomment the lines marked with arrows and execute the below code, the race condition is observed for both the variables ie the output for both the variables 'a' and 'b' is less than 1000. Need help with the same. 在这种情况下,我希望静态变量“ a”和“ b”都发生竞争,并且期望两个变量的输出均小于1000。但是,当我执行以下代码时,未观察到预期的行为如图所示,即b的输出始终为1000。但是,当我取消注释带有箭头的行并执行以下代码时,两个变量都观察到竞争条件,即变量'a'和'b'的输出为少于1000。需要同样的帮助。 Pardon me if i have missed out or ignored any of the basic or elementary concepts of threading considering the fact that i am still a newbie to java threads !!! 考虑到我仍然是Java线程的新手,请谅解我是否错过或忽略了线程的任何基本概念或基本概念!

public class SampleRace {

    public static void main(String[] args) {
        // TODO Auto-generated method stub
        SampleRace1 a = new SampleRace1();
        SampleRace1 b = new SampleRace1();
        Thread t1 = new Thread(a);
        Thread t2 = new Thread(b);
        t1.start();
        t2.start();
        try {
            t1.join();
            t2.join();
        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        //System.out.println(SamapleLoop.a); // <---------------------
        System.out.println(SampleRace1.b);
    }

}

class SamapleLoop {
    public static int a = 0;
    public static void loop() {
        a++;
    }
}

class SampleRace1 implements Runnable {
    public static int b = 0; 
    @Override
    public void run() {
        // TODO Auto-generated method stub
        for (int i = 1; i <= 500; i++) {
            //SamapleLoop.loop(); // <------------------------
            b++;
        }
    }

}

Try increasing 500 to a 500.000.000, or doing more complex operations inside the loop. 尝试将500增加到500.000.000,或者在循环内执行更复杂的操作。 There's a chance that thread a is running to completion before thread b is even started - so they end up running in sequence, rather than in parallel. 有一个机会,线程a运行完成之前线程b甚至开始-所以他们最终会按顺序运行,而不是并行。

You can also call Thread.yield every few cycles to give up your timeslice and let the other thread run. 您还可以每隔几个周期调用Thread.yield放弃时间片,让另一个线程运行。

If you want I can suggest a more proper race condition you can work on 如果您愿意,我可以建议更合适的比赛条件,

import java.util.concurrent.atomic.AtomicInteger;

/*
 * author: Atom Karinca
 */

/*
 * Run this program multiple times to see the output.
 * How does the result vary? Why does that happen?
 *
 */
class Racer extends Thread {    
    private static final int NUM_ITERS = 1000000;

    public void run() {
        for(int j = 0; j < NUM_ITERS; j++) {
            RaceCondition.sum();
        }
    }    
}

public class RaceCondition {
    public static long sum = 0;


    // What happens when you make this method "synchronized"?
    // Do you still see the bug?    
    //synchronized 
    public static void sum() {
        sum = sum + 1;
    }

    public static void main(String[] args) throws InterruptedException {        
        Racer leftAdder = new Racer();
        Racer rightAdder = new Racer();

        leftAdder.start();
        rightAdder.start();

        // wait for the threads to finish
        leftAdder.join();
        rightAdder.join();

        System.out.println("Sum: " + sum);
    }
}

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

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