繁体   English   中英

基本的多线程问题

[英]Basic multi-threading issue

package demo5;

class Process extends Thread {

static int counter = 0;

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

public void run() {
    for (int i = 0; i < 1000000; i++)
    {
        increment();
    }
    System.out.println("Done.");
  }
}

public class App {

public static void main(String[] args) throws InterruptedException {
    Process p1 = new Process();
    Process p2 = new Process();
    p1.start();
    p2.start();

    p1.join();
    p2.join();

    System.out.println("Value of count is :" + p1.counter);

}

}

如果我将增量​​函数声明为NON-STATIC函数,那么最后的计数器值将不会是200万。

另一方面,当增量方法定义为静态时,它可以正常工作。

据我所知,所有Process对象都只有一个增量函数。为什么我必须将其声明为静态方法呢?

谢谢

声明为静态将导致synchronized锁定在Process.class实例上。 因此,所有运行中的线程都将在increment方法内阻塞对象。 删除静态变量将导致每个线程仅在Thread实例(在您的情况下为两个)上阻塞。

结果,您的counter变量被并行递增,并且多次出现,int递增不是线程安全的。

As far as I know there will be only ONE increment function for all the Process objects

Process类有一个增量函数,但是同步是在Object而不是在方法上完成的,例如:

class Process{
     public synchronized void increment() { counter++; }
}

等价于:

class Process{
     public void increment() { 
           synchronized(this){
                  counter++; 
            }
}

编辑:回答鲁基的问题。

class Process{
     public static synchronized void increment() { counter++; }
}

等价于

class Process{
     public void increment() { 
           synchronized(Process.class){
                  counter++; 
            }
}

您可能需要用AtomicInteger计数器替换int计数器-这样,您可以从方法中删除synced关键字,并且该方法是静态方法还是实例方法都没有关系。

暂无
暂无

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

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