My question is on CopyOnWriteArraylist(COWA). So in a multi-thread env ..suppose Thread1 is iterating over the COWA and the Thread2 add a new element in the COWA. As i understand Thread2
will do a write on the Copy of the COWA while Thread1 is iterating over the original one.
Now after the Thread2 update the copy of COWA ....will the other threads in the system see the updated version of the COWA or the modified COWA will be only be seen by Thread2......so incase there is Thread3 , thread4
which do update on this COWA ....will all these thread will have their own copy of COWA....
Or does these copies get merged to the original COWA..... hope my question make some sense..
Writes are mutually exclusive with each other - you can have multiple reads at once, and reads running at the same time as writes, but you can't have multiple writes at once. Each write gets an exclusive lock, makes a copy of the underlying data, changes the data, then swaps the new copy for the old and finally releases the lock. So by the time Thread 3 gets a chance to make a change, Thread 2 has completed, and there is no need to merge.
The iterator iterates over the underlying array of data, and maintains a reference to that array. So when changes are made by a write, since those writes end up in a new array, the reference the iterator uses is unaffected.
Joined: Aug 05, 2013
So after thread 2 make a change and swap
The old COWA with new..thread 3 see the
Change..but what about the thread1 or other threads
Which were reading in parallel ..they will
Be working on the old list since update still going
In thread2 ,so isn't this a problem..incase I want
All threads in Sync and see latest data only
If thread1 is iterating, then yes, it will only see a 'snapshot' of the data from a time before the changes were made. If thread1 is doing other forms of direct access (get(), size(), contains()) it will be working on the data from the change that happens just prior to the access.
If you need completely synced data with iteration viewing the data currently in the list, then you can't let writes happen concurrently to reads/iteration and you should not be using CopyOnWrite collections.
If you need iteration/reads to see the latest data that was there before the iteration/read (a snapshot) and want to allow concurrent writes, and know that reads/iterations far outnumber writes, then CopyOnWrite collections are a good choice.
If you need iteration/reads to see the latest data from the just before the iterations/read (a snapshot) and want to allow concurrent writes, and do not know about the relative number of reads versus writes or are sure there will be even or more writes than reads, a Concurrent collection is a good choice.
If you need iteration/reads to see the latest data, and never to be out of sync with the last successful write, then you must give up concurrent writes and a synchronized collection (such as Collections.synchronizedxxx()) might be a good choice, though you may have to add your own synchronization in many cases (see the API documents for Collections).
Joined: Aug 05, 2013
Thanks for a detailed explanation.
So i get it that when the requirement is for mostly reads and very few writes go for COWA... So as an example Cache implementation will be the best scenario when we can go for COWA....
it will be nice scalable solution right... can you give me some real life example please for COWA..
A cache may or may not be well served using a CopyOnWrite collection: it depends on its usage. Some real world examples would be just repeating what has been said...
Say I have a web application serving 1000s of users a day. The application serves a list of active game hosts. The list of game hosts are updated once a day. That is a good application for a CopyOnWrite collection. I have a store that sells ice cream. The vast majority of my time is spent searching for particular flavors, and I have a background task that keeps an accounting of the current stock as well. A few times per day I get deliveries, and so I need to update the collection with new flavors, this is also done in a different thread. Another use of CopyOnWrite, I would think.
These are all long-term applications but the short term can benefit from CopyOnWrite as well, as long as a single Copy operation doesn't take longer than the time 'saved' by blocking during an individual write. This cost of Copy gets longer as the size of the collection grows, so it depends on how it is used and how big it is.
I actually rarely use them. I think to make best use of them you would need to prove the need - use a collection which doesn't so depend on the lopsided action and profile it to show you spend a lot of time in bottlenecks associated with reading/writing from the collection. Then use the CopyOnWrite collection and profile again to see you have reduced the bottleneck and that no new and worse bottleneck comes in as a result.
Joined: Aug 05, 2013
Thanks for the quick response. I liked the Ice -cream example...now whenever i will have an ice-cream i will remember COWA ....with these example i feel more confident on understanding of COWA...Thanks