线程同步,对象级别锁,类级别锁

                                                                                      线程同步,对象级别锁,类级别锁

同步一般是指在多线程中,在某一时刻,一个同步块代码只能在一个线程中执行。

的Java的支持多线程执行,所以可能出现两个或者更多的线程访问同一个字段或者对象。同步是一个过程,保持所有并发线程同步执行。同步避免了因共享内存不一致的问题而引起的内存一致性错误。当一个方法声明为同步,并有一个线程持有这个方法对象的监视器,你的线程就会被阻塞,直到这个线程释放这个监视器。

同步在的Java中使用同步这个关键字来实现,你可以使用这个关键字在你定义类的方法或者代码块中,但是这个关键字不能使用在类定义的变量或者属性中。

对象级别锁

对象级别锁是一个机制,当你想同步一个非静态方法或者非静态代码块,让在给定的类实例中只有一个线程来执行这个代码块,这就可以使得实例级别的数据是线程安全的。具体做法如下:

public class DemoClass
{
    public synchronized void demoMethod(){}
}

or

public class DemoClass
{
    public void demoMethod(){
        synchronized (this)
        {
            //other thread safe code
        }
    }
}

or

public class DemoClass
{
    private final Object lock = new Object();
    public void demoMethod(){
        synchronized (lock)
        {
            //other thread safe code
        }
    }
}

类级别锁

在所有可变的实例或者运行环境中,类级别锁阻止多线程进入同步块,也就是说,如果运行环境中有DemoClass的100个实例,在任何时刻,只能有DemoClass的一个实例来执行它的demoMethod()方法,所有其他的DemoClass实例在其他线程中只能处于阻塞状态,这使得静态数据是线程安全的。

public class DemoClass
{
    public synchronized static void demoMethod(){}
}

or

public class DemoClass
{
    public void demoMethod(){
        synchronized (DemoClass.class)
        {
            //other thread safe code
        }
    }
}

or

public class DemoClass
{
    private final static Object lock = new Object();
    public void demoMethod(){
        synchronized (lock)
        {
            //other thread safe code
        }
    }
}

一些重要点

1,在Java的的中,同步保证两个线程不能同时执行同一个同步方法需要有相同的同步或者并发锁。

2,同步关键字只能用在方法或者代码块中,这些方法或者代码块可以使静态的也可以使非静态的。

3,当一个线程进入到的java的同步方法或者块中的时候,它会获取一个锁,并且无论什么时候它离开这个javasynchronized方法或者块的时候,它会释放这个锁。当执行完成离开同步块或者出现任何错误以及异常的时候都会释放锁。

4,JAVA的同步是关键字本质上是可重入的,这意味着如果java的同步方法调用到了另一个同步方法,并且这个方法需要同样的锁,那么持有锁的这个方法是可以进入另一个需要同一个锁的方法的。

例如:

class MyClass {
    public synchronized void method1() {
        method2();
    }

    public synchronized void method2() {

    }
}

上述代码中的两个方法方法1方法2和都用同步修饰了,假如某一时刻,线程甲执行到了方法1,此时线程甲获取了这个对象的锁,而由于方法2也是同步的方法,假如同步不具备可重入性,此时线程甲需要重新申请锁。但是这就会造成一个问题,因为线程甲已经持有了该对象的锁,而又在申请获取该对象的锁,这样就会线程甲一直等待永远不会获取到的锁。

  而由于同步和锁都具备可重入性,所以不会发生上述现象。

5,如果用在同步块中的对象是空,那么的java的同步将会抛出的空指针异常。

例如:下面就会抛出空指针异常

public class DemoClass
{
    private final static Object lock = null;
    public void demoMethod(){
        synchronized (lock)
        {
        }
    }
}

6,在Java的的中,方法的同步会影响应用的性能,所以在完全需要的时候才使用这个同步,另外,可以考虑使用同步代码块来同步你需要同步的关键代码。

7,静态同步方法和非静态同步方法是可能同时运行的,因为它们使用的是不同的对象锁。

8,根据的的Java的语言规范,不能在构造函数中使用的Java的的同步关键字,它是非法的并会导致编译错误。

9,在java的的中,不能在同步块中同步非最终字段,因为,非最后字段的引用可能在任何时候发生改变,这样如果不同的线程同步不用的对象就相当于没有同步。最好使用字符串类,它已经声明为终态并且是不可变的。

原文:线程同步,对象级锁定和类级别锁定


  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Java中的synchronized关键字是一种用于实现同步的机制。它可以应用于方法和代码块,以确保在同一时刻只有一个线程可以访问共享资源。 以下是一些使用synchronized关键字的案例: 1. 多线程访问共享资源:考虑一个银行账户的例子,多个线程同时尝试改变账户余额。为了避免竞态条件和数据不一致的问题,可以使用synchronized关键字来同步访问共享资源,例如在deposit()和withdraw()方法上使用synchronized。 2. 线程安全的容器:在多线程环境下,使用synchronized可以确保线程安全的访问容器。例如,可以在对ArrayList的增删操作上使用synchronized,以避免多个线程同时修改容器而导致的错误。 3. 生产者-消费者模型:生产者线程负责生成数据,消费者线程负责消费数据。为了保证顺序,可以使用synchronized来同步这两个线程。例如,在生产者方法的代码块和消费者方法的代码块上使用synchronized。 4. 对象:synchronized可以用来实现对象级别级别对象级别是在每个对象实例上加,而级别是在级别上加。例如,在静态方法上使用synchronized即可获得级别。 总结来说,synchronized关键字在Java中的使用案例非常广泛,可以用于多线程环境下保证共享资源的安全访问,避免并发操作导致的数据不一致问题。通过使用synchronized,可以有效地控制多个线程对共享资源的访问,确保线程安全性。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值