Collections.synchronizedlist () remove item, iterate from end

I use Collections.Synchronizedlist() to make the arraylist stream safe. What I want to ask is the following code, safe for the stream, that is, deleting when the list is executed again from the end: -

 pendingExecutionList = Collections.synchronizedList(new ArrayList<>(initialCapacity)); 

I am creating a list in the main thread. and adding to this list from different threads. But iteration and deletion are only performed from one scheduled thread, as shown below: -

 for (int i = pendingExecutionList.size() - 1; i >= 0; i--) { if (someCondition(pendingExecutionList.get(i))) { process(pendingExecutionList.remove(i)); } } 

The above code is executed by only one thread, and several threads are added to this list.

I want to avoid using an iterator over synchronized(list) as this is not fault tolerant.

+5
source share
2 answers

If I understand your workflow correctly, I would suggest trying some BlockingQueue option instead of synchronizedList() .

ArrayBlockingQueue will allow you to have fair execution planning and should keep the caches of several vendors pretty hot (unless your vendors start to overtake the cache prefix, in which case you will encounter false sharing).

If you are determined to experiment, you can take a look at the MPSC queues (multiple producers, single-user) available outside the JDK, such as Nitsan Wakart MpscArrayQueue or Disruptor .

+1
source

Instead of locking, you actually get a lock once per element. This can be slower than just holding the lock while you check.

I suggest you use PriorityQueue with the appropriate order. This will order a queue, so those that you are going to process further will be at the beginning, and the cost of removal will be relatively cheap, regardless of the number of tasks waiting.

+2
source

Source: https://habr.com/ru/post/1247344/


All Articles