当我们说 ArrayList 不同步时,这意味着什么?

发布于 2024-11-27 14:24:09 字数 93 浏览 2 评论 0原文

当我们说 ArrayList 不同步时,这意味着什么?

这是否意味着如果我们在对象范围内声明一个ArrayList,访问该对象的多个线程就有机会修改该列表?

What does it mean when we say an ArrayList is not synchronized?

Does it mean that if we declare an ArrayList in object scope, multiple threads accessing the objects have the opportunity to modify the list?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(7

捶死心动 2024-12-04 14:24:09

我们说 ArrayList 不同步是什么意思?

这意味着从多个线程访问 ArrayList 实例可能不安全(请阅读、“可能会导致意外行为”或“可能不会像宣传的那样工作”)。

进一步阅读:

这是否意味着如果我们在对象作用域中声明一个ArrayList,访问该对象的多个线程就有机会修改该列表?

即使它是线程安全的,多个线程也 可以修改该列表。线程将能够修改列表。

不同之处在于,如果它不是线程安全的并且多个线程访问该列表,那么所有的赌注都会被取消。说该类不是线程安全的,相当于在每个方法描述前面添加“如果一次从一个线程访问,此方法的工作原理如下......”。

What does it mean when we say an ArrayList is not synchronized?

It means that accessing an ArrayList instance from multiple threads may not be safe (read, "may result in unexpected behavior" or "may not work as advertised").

Further reading:

Does it mean that if we declare an ArrayList in object scope, multiple threads accessing the objects have the opportunity to modify the list?

Even if it would have been thread safe, multiple threads would be able to modify the list.

The difference is that if it's not thread safe and multiple threads access the list, all bets are off. Saying that the class is not thread safe, is the same as adding "If accessed from one thread at a time, this method works as follows....." in front of every method description.

我偏爱纯白色 2024-12-04 14:24:09

无论同步与否,ArrayList 始终可以由多个线程修改。同步是为了防止并发访问。

对于 ArrayList(或一般的集合),存在两个并发问题。

首先,有方法同步。这意味着,对 ArrayList 实例的所有方法的调用都是同步的。所以一次总是只执行一个方法。当第一个方法仍在计算时发生的所有其他方法调用都会排队,直到正在运行的方法完成。

可以通过像这样包装 ArrayList 来确保方法同步:

List list = Collections.synchronizedList(new ArrayList());

示例:假设两个线程尝试同时执行以下操作:

list.add(0, "test");

如果您有一个同步列表,则可以保证列表后缀以两个“测试”条目开头。如果列表未同步,您可能会得到一个仅包含一个“测试”条目的列表...或其他意外结果。

第二,有实例同步。在这里,我们不仅防止并发方法调用,而且确保在一段时间内只有一个线程可以访问列表对象。如果您的逻辑片段要求列表在逻辑完成之前保持不变状态,那么这一点很重要。例如迭代列表。您不希望其他线程在您迭代列表时添加元素。

这种同步是通过用同步块包装您的逻辑来完成的:

synchronized(list) {
      for (Object o:list) {
         ...
      }
}

Synchronized or not, an ArrayList can always be modified by multiple threads. Synchronization is about preventing concurrent access.

With ArrayList (or Collections in general) there are two concurrency problems.

First, there is method synchronization. This means, all calls to methods of an ArrayList instance are synchronized. So there is always only one method executed at a time. All other method calls that happen while the first method still computes are queued until the running method is completed.

Method synchronization can be ensured by wrapping an ArrayList like this:

List list = Collections.synchronizedList(new ArrayList());

Example: assume two threads try to do the following at the same time:

list.add(0, "test");

If you have a synchronized list, you are guaranteed that the list afterwords starts with two "test" entries. If the list is not synchronized, you might get a list with only one "test" entry... or other unexpected results.

Second, there is instance synchronization. Here we not only prevent concurrent method calls, but we make sure that only one thread has access to the list object for a time. This is important if you have pieces of logic that require that the list remains in an unchanged state until the logic is done. For example iterating over lists. You don't want other threads to add elements while you iterate over a list.

This kind of synchronization is done by wrapping your piece of logic with a synchronized block:

synchronized(list) {
      for (Object o:list) {
         ...
      }
}
吹泡泡o 2024-12-04 14:24:09

这意味着 ArrayList 的实例不能保证是线程安全的。这通常包括读和写访问。如果您在没有外部同步的情况下执行此操作,则可能会使对象处于异常状态并导致一些难以调试的行为。

It means that instances of ArrayList are not guaranteed to be threadsafe. This usually includes both read and write access. If you do it without external synchronization you can leave the object in stange states and get some hard to debug behavior.

这是否意味着如果我们在对象作用域中声明一个ArrayList,访问该对象的多个线程就有机会修改该列表?

是的。如果多个线程同时对其进行操作,可能会导致意外的行为

Does it mean that if we declare an ArrayList in object scope, multiple threads accessing the objects have the opportunity to modify the list ?

Yes. If multiple threads operate on it at the same time, it may result in unexpected behaviour

无尽的现实 2024-12-04 14:24:09

同步意味着每个操作都是线程安全的 - 如果您同时从两个线程使用相同的数组列表,它们就不会破坏状态。然而,这会使其变慢。

默认情况下ArrayList是不同步的,可以通过synchronized关键字来实现

ArrayList al=new ArrayList();

Collections.synchronized(al);

Being synchronized means that every operation is thread safe - if you use the same Array List from two threads at the same time, they can't corrupt the state. However, this makes it slower.

By default ArrayList is not synchronized, you can achieved that by synchronized keyword

ArrayList al=new ArrayList();

Collections.synchronized(al);
对你而言 2024-12-04 14:24:09

同步意味着每个操作都是线程安全的 - 如果您同时使用两个线程的相同向量,它们就不会破坏状态。然而,这会使其变慢。

如果您在单线程环境中工作(或者列表仅限于线程且从不共享),请使用 ArrayList。如果您正在使用共享同一集合的多个线程,请使用 Vector,或使用 ArrayList 但以其他方式同步(例如,手动或通过包装器)。

Being synchronized means that every operation is thread safe - if you use the same vector from two threads at the same time, they can't corrupt the state. However, this makes it slower.

If you are working in a single threaded environment (or the list is limited to a thread and never shared), use ArrayList. If you are working with multiple threads that share the same collection, either use Vector, or use ArrayList but synchronize in some other way (e.g., manually or via a wrapper).

暖阳 2024-12-04 14:24:09

从多个线程访问 arraylist 的实例是相当不安全的。有一些替代方法可以到达 **Arraylist ** 与 linkdlist 不同。它们可能听起来相似,但内部构造并不相同。

Arraylist<datamodel> are;

Accessing arraylist's instances from multiple threads is not safe considerable. There are some alternate way to go there **Arraylist ** is not like linkdlist. They may sound similar but not made internally same.

Arraylist<datamodel> are;
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文