线程八锁问题

文章详细探讨了Java中的synchronized关键字在实例方法和静态方法中的应用,以及它如何影响线程同步。通过多个示例代码,展示了不同情况下synchronized锁的对象(实例或类对象),并分析了可能的执行顺序,包括线程间的等待和唤醒。这有助于理解Java并发编程中的锁机制。
摘要由CSDN通过智能技术生成

考察内容:synchronized 锁住的是哪个对象

本质上考察 synchronized 与 static synchronized 的区别:

  • synchronized 是实例锁,对类的当前实例进行加锁
  • static synchronized 是类锁,对类对象进行加锁

情况1

public class Test1 {
    public static void main(String[] args) {
        Number n1 = new Number();
        new Thread(() -> n1.a()).start();
        new Thread(() -> n1.b()).start();
    }
}

class Number {
    public synchronized void a() {
        log.debug("1");
    }

    public synchronized void b() {
        log.debug("2");
    }
}

两种可能

  • 12 
  • 21 

情况2

public class Test2 {
    public static void main(String[] args) {
        Number n1 = new Number();
        new Thread(() -> n1.a()).start();
        new Thread(() -> n1.b()).start();
    }
}

class Number{
    public synchronized void a(){
        try {
            TimeUnit.SECONDS.sleep(1);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        log.debug("1");
    }
    public synchronized void b() {
        log.debug("2");
    }
}

两种可能

  • 1s 后打印 12
  •  先打印2, 1s 后打印 1

情况3

public class Test3 {
    public static void main(String[] args) {
        Number n1 = new Number();
        new Thread(() -> n1.a()).start();
        new Thread(() -> n1.b()).start();
        new Thread(() -> n1.c()).start();
    }
}

class Number{
    public synchronized void a() {
        try {
            TimeUnit.SECONDS.sleep(1);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        log.debug("1");
    }
    public synchronized void b() {
        log.debug("2");
    }
    public void c() {
        log.debug("3");
    }
}

三种可能

  • 先打印 3,1s 后打印 12
  • 先打印 23,1s 后打印 1
  • 先打印 32,1s 后打印 1

情况4

public class Test4 {
    public static void main(String[] args) {
        Number n1 = new Number();
        Number n2 = new Number();
        new Thread(() -> n1.a()).start();
        new Thread(() -> n2.b()).start();
    }
}

class Number{
    public synchronized void a() {
        try {
            TimeUnit.SECONDS.sleep(1);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        log.debug("1");
    }
    public synchronized void b() {
        log.debug("2");
    }
}

一种可能,先打印 2,1s 后打印 1

情况5

public class Test5 {
    public static void main(String[] args) {
        Number n1 = new Number();
        new Thread(() -> n1.a()).start();
        new Thread(() -> n1.b()).start();
    }
}

class Number {
    public static synchronized void a() {
        try {
            TimeUnit.SECONDS.sleep(1);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        log.debug("1");
    }

    public synchronized void b() {
        log.debug("2");
    }
}

一种可能,先打印 2,1s 后打印 1

情况6

public class Test6 {
    public static void main(String[] args) {
        Number n1 = new Number();
        new Thread(() -> n1.a()).start();
        new Thread(() -> n1.b()).start();
    }
}

class Number{
    public static synchronized void a() {
        try {
            TimeUnit.SECONDS.sleep(1);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        log.debug("1");
    }
    public static synchronized void b() {
        log.debug("2");
    }
}

两种可能

  • 1s 后打印 12
  • 先打印 2,1s 后打印 1

情况7

public class Test7 {
    public static void main(String[] args) {
        Number n1 = new Number();
        Number n2 = new Number();
        new Thread(() -> n1.a()).start();
        new Thread(() -> n2.b()).start();
    }
}

class Number{
    public static synchronized void a() {
        try {
            TimeUnit.SECONDS.sleep(1);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        log.debug("1");
    }
    public synchronized void b() {
        log.debug("2");
    }
}

一种可能,先打印 2,1s 后打印 1

情况8

public class Test8 {
    public static void main(String[] args) {
        Number n1 = new Number();
        Number n2 = new Number();
        new Thread(() -> n1.a()).start();
        new Thread(() -> n2.b()).start();
    }
}

class Number{
    public static synchronized void a() {
        try {
            TimeUnit.SECONDS.sleep(1);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        log.debug("1");
    }
    public static synchronized void b() {
        log.debug("2");
    }
}

 两种可能

  • 1s 后打印 12
  • 先打印 2,1s 后打印 1
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

小鲁蛋儿

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值