• Post Reply Bookmark Topic Watch Topic
  • New Topic

Synchronised ArrayList ?  RSS feed

 
sudip ghosh
Greenhorn
Posts: 3
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Hi,

What is the advantage and disadvantage of synchronizing ArrayList?

If, I want to synchronize an ArrayList then should I synchronize the entire ArrayList or only the add() method?

Does these reflect on memory management?

Please help me to find all these. Thanks in advance to all of you.
 
Henry Wong
author
Sheriff
Posts: 23280
125
C++ Chrome Eclipse IDE Firefox Browser Java jQuery Linux VI Editor Windows
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
What is the advantage and disadvantage of synchronizing ArrayList?


If you are using the array list between multiple threads, synchronization helps you use it in a thread safe manner. The advantage is, I guess, your program won't fail.

If, I want to synchronize an ArrayList then should I synchronize the entire ArrayList or only the add() method?


The Sun tutorial on threading, is a decent place to start to learn about threads...

http://java.sun.com/docs/books/tutorial/essential/concurrency/

Henry
 
Rob Spoor
Sheriff
Posts: 21050
85
Chrome Eclipse IDE Java Windows
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Originally posted by sudip ghosh:
If, I want to synchronize an ArrayList then should I synchronize the entire ArrayList or only the add() method?

First of all, you'll need to synchronize anything that can modify your ArrayList. So not only add, but also remove.

If you limit yourself to those, then your "viewing" methods can return values that are no longer true. For instance, get(2) can actually return element 3 if somewhere during the call of get(2) an element is added. So get needs to be synchronized as well. In the end you'll end up synchronizing (nearly) all methods.
 
Nitesh Kant
Bartender
Posts: 1638
IntelliJ IDE Java MySQL Database
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
BTW, you do not need to do anything on your own.
Collections.synchronizedList(java.util.List) will do it for you.
If you see the source code of the same, you will know what it does internally!
Moving to Threads & Synchronization forum.
 
Mike Simmons
Ranch Hand
Posts: 3090
14
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
[Nitesh]: BTW, you do not need to do anything on your own.
Collections.synchronizedList(java.util.List) will do it for you.


Hm, I doubt it. Usually you need to add explicit, external synchronization somewhere, in order to get useful, reliable results. Well, maybe if you put in some other restrictions, things "no more than one thread may ever remove elements from the list", or "elements may only be added to the end of this list, never earlier." Or if you lighten up some consistency requirements - e.g. "we don't care if sometimes, when you try to iterate all elements of the list, you maybe skip some elements, or process other elements twice or more." But in general, the so-called "thread safety" of APIs like Collections.sychronizedXXX() is somewhere between mildly unreliable and utterly false. It's hard to do anything useful with this class in a multithreaded environment, unless you're willing to do some additional synchronization of your own.
 
Nitesh Kant
Bartender
Posts: 1638
IntelliJ IDE Java MySQL Database
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
I agree that the iterator case is the one that does not guarantee thread safety and it is clearly mentioned in the API but I am not sure why the following restrictions

  • no more than one thread may ever remove elements from the list
  • elements may only be added to the end of this list, never earlier.


  • are required to get a useful result. After all what the synchronizedXXX() methods does is synchronize each and every method of the collection.

    I also agree that in order for multiple operations on the list to be atomic, external synchronization is required but I assume this was not something the OP was asking and will not be possible only at the list level.
     
    Mike Simmons
    Ranch Hand
    Posts: 3090
    14
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    I mentioned Iterator because even though the need for synchronization there is clearly documented, people often don't read that documentation - and "you do not need to do anything on your own.
    Collections.synchronizedList(java.util.List) will do it for you" does not seem to encourage the reader to look carefully at the docs, IMO. So I thought it was worth mentioning.

    If you're not using an Iterator, then how are you accessing elements of the list? If you use get(int) or remove(int), and there's a possibility that another thread may be removing elements from the list, then you can't reliably call get(i) or remove(i) without checking the size of the list first. And then you need to add external synchronization to prevent the other threads from removing elements in between your calls to size() and get(i) or remove(i). This is a problem for any List method that takes an index - except add() or addAll(), if the index is 0. There are other workarounds possible, depending on what you need to accomplish with the list. But in general I think it's very rare to have a situation where you do not require any external synchronization.

    The List API is not well-designed for use without external synchronization. The same is true for most of the other collections classes in java.util, even when using Collections.synchronizedXXX(). In comparison, the classes in java.util.concurrent have more useful methods that can accomplish many things without external sync - things like peek(), poll(), putIfAbsent(), etc, which handle tasks that would require multiple method calls to accomplish with java.util classes.

    In comparison
     
    Billy Tsai
    Ranch Hand
    Posts: 1307
    • Mark post as helpful
    • send pies
    • Quote
    • Report post to moderator
    If you need synchronization, a Vector will be slightly faster than an ArrayList synchronized with Collections.synchronizedList. But Vector has loads of legacy operations, so be careful to always manipulate the Vector with the List interface or else you won't be able to replace the implementation at a later time.
    In the face of concurrent access, it is imperative that the programmer manually synchronize on the returned collection when iterating over it. The reason is that iteration is accomplished via multiple calls into the collection, which must be composed into a single atomic operation. The following is the idiom to iterate over a wrapper-synchronized collection.
    List l = Collections.synchronizedList(new ArrayList());
    synchronized(l) {
    for (Object o : l)
    l.addAll(something);
    }
     
    • Post Reply Bookmark Topic Watch Topic
    • New Topic
    Boost this thread!