java - 静态和非静态同步,为什么输出结果不同?

标签 java multithreading static synchronization non-static

为什么输出有差异?我有2个案例:

  1. 在第一种情况下,我使用静态函数 f1f2:
    public static synchronized void f1() {
        for (int i = 0; i < 100; i++)
            System.out.print("A");
    }
    
    public static synchronized void f2() {
        for (int i = 0; i < 100; i++)
            System.out.print("B");
    }
    
    这是我的主要方法体:
    Thread t1 = new Thread(
            new Runnable(){public void run(){f1();}}
    );
    
    Thread t2 = new Thread(
            new Runnable(){public void run(){f2();}}
    );
    t1.start();
    t2.start();
    
    输出是:
    AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB
    
  2. 在第二种情况下,f1f2 不是静态的:
    public synchronized void f1() {
        for (int i = 0; i < 100; i++)
            System.out.print("A");
    }
    
    public synchronized void f2() {
        for (int i = 0; i < 100; i++)
            System.out.print("B");
    }
    
    输出是如此困惑:
    AAABABABBBBAAAAAAAAAABBAAAAAAAAAAAAABBBBBBBBBBBBBBBBBBBBBBBBBBAA
    

最佳答案

静态同步函数在类上同步,而非静态同步函数在实例上同步。

这意味着当函数是静态的时,它们会互相阻塞,而当它们不是静态的(并使用不同的实例)时,它们不会互相阻塞。

如果您的类名为 MyClass 则:

public static synchronized foo() {...}

类似于:

public static foo() {
    synchronized (MyClass.class) {
        // ...
    }
}

同时:

public synchronized foo() {...}

类似于:

public foo() {
    synchronized (this) {
        // ...
    }
}

通常,您希望指定要同步的内容(您想独占什么资源?)并避免在类/实例上使用隐式同步,正是因为这个原因。

关于java - 静态和非静态同步,为什么输出结果不同?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35528026/

相关文章:

c++ - 以静态方式使用 Random 类

java - 如何防止 Ball 移出屏幕边缘?简单的 KeyListenerDemo 示例

java - 部署自定义中介器时出现 WSO2 ESB 错误

python - 多线程 Python 的 C 扩展可以提高性能吗?

c# - 暂停一个线程直到一个方法和里面的所有线程完成他们的工作?

Java基础: a static function without a name,或返回类型

c++ - C++ 中的静态属性

java - 如何计算并仅返回 ArrayList 中为真的对象?

java - 从数组中复制并粘贴像素

java - 让多个 Java pop3 客户端与 GMail 一起使用