了解具有线程和同步的共享对象

Posted

技术标签:

【中文标题】了解具有线程和同步的共享对象【英文标题】:Understanding shared Objects with Threads and synchronization 【发布时间】:2014-01-06 18:04:08 【问题描述】:

我是 Java 新手,正在阅读有关同步的内容我有一个问题

我不太确定这仍然有效,所以我想问一下:

例如我有一个名为“数学”的类,它具有同步的添加和删除方法 然后创建它的一个对象

Math m = new Math();

然后我启动 3 个线程并将这个对象 (m) 传递给所有线程。 我知道它们会在同一个对象中工作,并且每个线程都会按预期排队

但是如果每个线程都创建自己的对象呢?

Math m = new Math();

它们不会使用相同的同步方法,对吧?

【问题讨论】:

正确,如果方法不是静态的,是的,你是对的。每个线程将锁定不同的 Math 实例。如果你有 sycn 块而不是 sycn 方法,你可以在你的情况下使用相同的对象(如果你没有在方法中处理实例变量) 【参考方案1】:

不,他们没有使用相同的方法。但它可以依赖于 Math 对象。

【讨论】:

【参考方案2】:

如果每个线程都创建自己的 Math 对象,它们将相互独立;它们不会被共享 - 因此不能使用相同的同步方法(除非它们是 Mani 指出的静态方法)。但是,如果 Math 对象有一个在同步方法中使用的静态成员,请注意 - 如果任何方法更改了它的状态,您仍然需要围绕它提供一个锁定构造。

【讨论】:

【参考方案3】:

这里你唯一需要了解的是Class级别锁和Instance级别锁。

1。实例级别锁定

与第一种情况一样,所有线程共享同一个对象,因此每个线程都需要获得唯一一个锁才能调用这些方法。

例如

Class Math 
    synchronized public void add()
    synchronized public void decrease()

adddecrease 都是实例方法。所以如果两个线程在不同的实例中运行,它们不会相互影响。

2。类级别锁定

Class Math 
    synchronized public static void add()
    synchronized public static void decrease()

在这种情况下,adddecrease 可以在不创建数学对象的情况下被调用,它们是类级别的锁,所有线程使用Math.addMath.decrease 应该获得相同的锁。

【讨论】:

以上是关于了解具有线程和同步的共享对象的主要内容,如果未能解决你的问题,请参考以下文章

多线程(02)

线程共享数据的安全问题

线程同步

面向对象课程第二次随笔

从多个线程同步对共享对象的方法调用

线程同步与死锁