Java中向量的同步

Posted

技术标签:

【中文标题】Java中向量的同步【英文标题】:Synchronization in Vectors in Java 【发布时间】:2011-01-09 19:59:08 【问题描述】:

在Java中vector是什么意思是线程安全和同步的,它是如何做到线程安全的。我正在查看实施的内部细节

【问题讨论】:

【参考方案1】:

由于其所有方法都被同步(通过 synchronized 关键字),它是“线程安全的”,请参阅OpenJDK source code。

synchronized 关键字的作用是防止多个线程同时执行任何同步方法。它在内部使用了一个锁,线程在进入这些方法时必须获得该锁,并且线程在离开该方法时释放。

请注意,这并没有太大帮助,因为虽然它可以防止向量的内部状态不一致,但这并不能保证更高级别的一致性级别(对应用程序有用的级别)。

考虑这个示例,它表明您仍然需要在应用程序代码中使用同步(这样您就可以使用未同步的 ArrayList):

 // BROKEN CODE, needs external synchronization
 // only add an element if the vector is empty
 if(vector.isEmpty())
     vector.add(anElement);

【讨论】:

+1 但您应该更正“同步关键字的作用是防止多个线程同时执行该方法”。被阻止的不仅仅是对特定方法的访问。 @Fredrik:谢谢。我试图在不变得太复杂的情况下修正这个句子。我想一个更长的解释的链接是有序的。 我说对了吗,在您提供的代码中,vector 可能在 vector.add(anElement); 之前被更改(变为非空)? @soshial:没错。有人可能在检查了isEmpty 之后立即添加了一个元素(这样您就可以添加另一个元素,因为您已经在那个if 块中)。 那么,我想,使用 Collections 的线程安全类似物是没有意义的。我们只是在同步块中使用了线程不安全,对吧?是不是有点奇怪?【参考方案2】:

Vector 被认为是“线程安全的”,因为对 Vector 内部的访问是同步的。 add()get()size() 等方法都是同步的,因此对 Vector 的内部结构的修改和对该内部结构的访问不能由单独的线程同时处理。

【讨论】:

【参考方案3】:

请从 java api 中找到以下摘录

首先,同一对象上的同步方法的两次调用不可能交错。当一个线程正在为一个对象执行同步方法时,所有其他为同一对象调用同步方法的线程都会阻塞(暂停执行),直到第一个线程处理完该对象。

其次,当一个同步方法退出时,它会自动与任何后续对同一对象的同步方法调用建立起之前的关系。这保证了对象状态的更改对所有线程都是可见的。

【讨论】:

【参考方案4】:

方法标记为synchronized。查看Synchronized Method tutorial。

【讨论】:

以上是关于Java中向量的同步的主要内容,如果未能解决你的问题,请参考以下文章

Java和同步两个线程

OpenMP 中的同步

Dynamo涉及的算法和协议——p2p架构,一致性hash容错+gossip协议获取集群状态+向量时钟同步数据

java多线程-同步块

2017级面向对象程序设计作业三

控制对 Java 集合的并发访问的最佳方法