Java中的同步:StringBuffer与StringBuilder和Vector与ArrayList

时间:2012-12-29 17:19:56

标签: java synchronization

这是一个多次被问到的问题,但并非总是如此,Java初学者(像我一样)可以深入理解给出的答案。

我一直在阅读一些Java书籍,其中一本书我读到了Vector和ArrayList之间的区别在于前者是同步的而后者是不同的(与StringBuffer和StringBuilder相同)。

本书解释说,“如果我们需要它,我们可以”添加“同步到未同步的代码»。

this帖子中,Brian Roach解释说« StringBuffer和Vector有线程同步会增加开销(除非你需要它,但即便如此,还是有办法将它添加到更新的类中)»。

所以,我有三个问题:

1)如果同步增加了开销但我们可以在需要时添加更新的类,为什么不使用StringBuffer和Vector而不是向StringBuilder和ArrayList添加同步?

2)我们如何向班级添加同步?

3)同步的目的是什么?

对不起我的新手问题(我知道我必须阅读更多书籍),但这些概念不是很容易理解。

4 个答案:

答案 0 :(得分:4)

同步具有与之相关的开销,并且可能不必要地降低性能。请考虑以下代码段:

synchronized(this) {
   doSomething();
}

每当一个线程进入同步块时,它就必须获得一个锁。当它离开块时,它会放弃锁定。这是防止多个线程同时进入代码块的原因。

如果代码不需要同步(因为它一次只能被一个线程访问),那么你可以把代码写成

doSomething();

总结一下 - 除非您需要,否则通常不应使用同步版本,因为它会增加开销。但您始终可以使用synchronized块(和/或锁定)添加同步。

答案 1 :(得分:0)

1)因为在Vector之前将ArrayList引入了java API。几乎没有理由再使用Vector了。 StringBufferStringBuilder

的情况也是如此

2)如果需要同步,可以同步访问/修改实例的方法(或块)

答案 2 :(得分:0)

<强>兼容性即可。他们不想更改现有的类。因此,他们添加了一个不会自动同步的变体。您可以通过ArrayListList<String> list = Collections.synchronizedList(new ArrayList<String>());包装到同步列表中来使 // Class definition ArrayList<String> foo; void doSomething() { synchronized(foo) { foo.add("Foobar"); } } 同步。

维基百科中解释了

Synchronization。从那里开始阅读。

简单同步ArrayList示例:

doSomething

方法{{1}}是线程安全的。

答案 3 :(得分:0)

  

1)如果同步增加了开销但我们可以在需要时添加更新的类,为什么不使用StringBuffer和Vector而不是将同步添加到StringBuilder和ArrayList?

恕我直言,没有充分的理由拥有同步的StringBuffer。我认为这只是为了与其他馆藏保持一致。现在使用它的唯一原因是你有一个坚持它的API。

Vector更有用,虽然您可以使用Collection.synchronizedList(),但某些API需要它。从Java 5.0开始,一些并发集合是更好的选择。

  

2)我们如何向类添加同步?

synchronized关键字添加到所有方法中(还有更多内容,但在最简单的情况下,这就是所需的全部内容)您还可以创建一个像synchronizedList一样的同步包。

  

3)同步的目的是什么?

线程安全。