Quick clarification please
I know BlockingQueues are threadsafe.
Does that mean that I can pass a single reference to a blocking queue to all producers who can drop Events in willy-nilly to be consumed by a single consumer, and nothing gets disrupted?
Otherwise having to produce up to 20 BlockingQueues that may or may not have regular updates and reading them with any efficiency seems an insurmountable task.
Does that mean that I can pass a single reference to a blocking queue to all producers who can drop Events in willy-nilly to be consumed by a single consumer, and nothing gets disrupted?
In a word, yes. This is safe. To quote the documentation:
BlockingQueue implementations are thread-safe. All queuing methods achieve their effects atomically using internal locks or other forms of concurrency control.
If it's threadsafe that means that you only need one instance of that queue which can be accessed by all threads. The concurrent data structure manages those accesses. This also means that no synchronization from your side is needed.
Related
I read about concurrent queue in java, and i received confusion about LinkedTransferQueue. What is type of LinkedTransferQueue (is it blocking or not-blocking queue)? I have read that LinkedTransferQueue uses a CAS (compare and swap) approach and park method from Unsafe, and consists from nodes and pointers like ConcurrentLinkedQueue, it pushed on idea that it's a non-blocking queue. But interface TransferQueue extends BlockingQueue. It looks ambiguous. In the end, is LinkedTransferQueue blocking or not-blocking queue?
The LinkedTransferQueue is an unbounded queue so though it is BlockingQueue it will never actually reach the common producer/consumer patterns normal BlockingQueue implementations may achieve.
So, is it or isn't it blocking? It actually depends on the operation. For example, a few are listed below.
Non-blocking operations:
offer
put
add
poll
tryTransfer
Blocking operations:
take
transfer
Point is, if an operation can achieve without blocking it will. Since the LinkedTransferQueue is forced to be unbounded, it can get away with both blocking and non-blocking operations.
If interested, I found this out by going through the Java 8 implementation.
From the Javadoc:
An optionally-bounded blocking queue based on linked nodes.
I have a class that's a listener to a log server. The listener gets notified whenever a log/text is spewed out. I store this text in an arraylist.
I need to process this text (remove duplicate words, store it in a trie, compare it against some patterns etc).
My question is should i be doing this as an when the listener is notified? Or should i be creating a separate thread that handles the processing.
What is the best way to handle this situation?
Sounds like you're trying to solve the Producer Consumer Problem, in which case - Yes, you should be looking at threads.
If, however, you only need to do very basic operations that take less than milliseconds per entry - don't overly complicate things. If you use a TreeSet in conjunction with an ArrayList - it will automatically take care of keeping duplicates out. Simple atomic operations such as validating the log entry aren't such a big deal that they need a seperate thread, unless new text is coming in at such a rapid rate that you need to need a thread to busy itself full time with processing new notifications.
The process that are not related to UI i always run that type of process in separate thread so it will not hang your app screen. So as my point of view you need to go with separate thread.
Such a situation can be solved using Queues. The simplest solution would be to have an unbounded blocking queue (a LinkedTransferQueue is tailored for such a case) and a limited size pool of worker threads.
You would add()/offer() the log entry from the listener's thread and take() for processing with worker threads. take() will block a thread if no log entries are available for processing.
P. S. A LinkedTransferQueue is designed for concurrent usage, no external synchronization is necessary: it's based on weak iterators, just like the Concurrent DS family.
I am also thinking of integrating the disruptor pattern in our application. I am a bit unsure about a few things before I start using the disruptor
I have 3 producers, mainly a FIX thread which de-serialises the requests. Another thread which continously modifies order price as the market moves. Also we have one more thread which is responsible for de-serialising the requests sent from a GUI application. All three threads currently write to a Blocking Queue (hence we see a lot of contention on the queue)
The disruptor talks about a Single writer principle and from what I have read that approach scales the best. Is there any way we could make the above three threads obey the single writer principle?
Also in a typical request/response application, specially in our case we have contention on an in memory cache, as we need to lock the cache when we update the cache with the response, whilst a request might be happening for the same order. How do we handle this through the disruptor, i.e. how do I tie up a response to a particular request? Can I eliminate the lock on the cache if yes how?
Any suggestions/pointers would be highly appreciated. We are currently using Java 1.6
I'm new to distruptor and am trying to understand as much usecases as possible. I have tried to answer your questions.
Yes, Disruptor can be used to sequence calls from multiple
producers. I understand that all 3 threads try to update the state
of a shared object. And a single consumer which takes necessary action on the shared object. Internally you can have the single consumer delegate calls to the appropriate single threaded handler based on responsibility. The
The Disruptor exactly does this. It sequences the calls such that
the state is accessed only by a thread at a time. If there's a specific order in which the event handlers are to be invoked, set up the memory barrier. The latest version of Disruptor has a DSL that lets you setup the order easily.
The Cache can be abstracted and accessed through the Disruptor. At a time, only a
Reader or a Writer would get access to the cache, since all calls to
the cache are sequential.
I am completely new to java, but I have urgent requirement to create a queue and thread. I am confused which queue class must be used.
Here's the scenario:
I need to a thread to handle user events from the application layer as well as callback events from the lower middleware layer.
For this purpose, it was decided that a queue will be maintained.
Events will be posted to this queue whenever a user event or callback event occurs.
The thread polls for events in the queue and takes appropriate action.
The same queue can be written into by different classes(i.e application layer & lower layer). Hence, which queue wuld be safer, to ensure the same location is not being written into simultaneously by different classes?
Also, what is the basic one-sentence difference between a Queue, BlockingQueue and ArrayBlockingQueue and in what scenarios must each be selected?
Regards,
kiki
Of the three you listed, the only which is actually a class is ArrayBlockingQueue. A blocking queue is different from a normal queue in that, if an object attempts to remove the front item, it will pause execution until there is an available item to remove.
"BlockingQueue" and "Queue" are just a interfaces; you can't instantiate them. Types of BlockingQueue that you can instantiate are ArrayBlockingQueue, LinkedBlockingQueue, etc.
Personally, I would use a LinkedBlockingQueue for this application - the advantage of using a linked list is that there's no set max capacity, and the memory usage decreases as the queue shrinks.
In connection to "few words difference": Queue and BlockingQueue are interfaces, whereas ArrayBlockingQueue is a class which imiplements BlockingQueue interface.
You should choice mainly between ConcurrentLinkedQueue and ArrayBlockingQueue/LinkedBlockingQueue.
Former gives you unbounded queue ( not limite sin size), latter provide fixed-size queues which wait for space to become available in the queue when storing an element.
As an alternative to queues + threads you can consider Executor and Future interfaces from concurrent package, they may be easier in usage to implement client-server model.
For your scenario, what you need is a thread safe queue such as ConcurrentLinkedQueue. Regarding your other question on Queue and BlockingQueue. There are basically the following types of queue implementations:
Blocking: Blocks until the operation (put(),take() etc.) is possible with an optional timeout.
Non-Blocking: The operation completes instantly
Bound: Has a upper limit on the number of items in the queue
Non-bound: No limit on the number of items in the queue.
As for ArrayBlockingQueue, it is backed up by an Array while a LinkedBlockingQueue is backed up by a LinkedList.
Use the higher-level Executors.newSingleThreadExecutor()
I think I shall reframe my question from
Where should you use BlockingQueue Implementations instead of Simple Queue Implementations ?
to
What are the advantages/disadvantages of BlockingQueue over Queue implementations taking into consideration aspects like speed,concurrency or other properties which vary e.g. time to access last element.
I have used both kind of Queues. I know that Blocking Queue is normally used in concurrent application. I was writing simple ByteBuffer pool where I needed some placeholder for ByteBuffer objects. I needed fastest , thread safe queue implementation. Even there are List implementations like ArrayList which has constant access time for elements.
Can anyone discuss about pros and cons of BlockingQueue vs Queue vs List implementations?
Currently I have used ArrayList to hold these ByteBuffer objects.
Which data structure shall I use to hold these objects?
A limited capacity BlockingQueue is also helpful if you want to throttle some sort of request. With an unbounded queue, a producers can get far ahead of the consumers. The tasks will eventually be performed (unless there are so many that they cause an OutOfMemoryError), but the producer may long since have given up, so the effort is wasted.
In situations like these, it may be better to signal a would-be producer that the queue is full, and to give up quickly with a failure. For example, the producer might be a web request, with a user that doesn't want to wait too long, and even though it won't consume many CPU cycles while waiting, it is using up limited resources like a socket and some memory. Giving up will give the tasks that have been queued already a better chance to finish in a timely manner.
Regarding the amended question, which I'm interpreting as, "What is a good collection for holding objects in a pool?"
An unbounded LinkedBlockingQueue is a good choice for many pools. However, depending on your pool management strategy, a ConcurrentLinkedQueue may work too.
In a pooling application, a blocking "put" is not appropriate. Controlling the maximum size of the queue is the job of the pool manager—it decides when to create or destroy resources for the pool. Clients of the pool borrow and return resources from the pool. Adding a new object, or returning a previously borrowed object to the pool should be fast, non-blocking operations. So, a bounded capacity queue is not a good choice for pools.
On the other hand, when retrieving an object from the pool, most applications want to wait until a resource is available. A "take" operation that blocks, at least temporarily, is much more efficient than a "busy wait"—repeatedly polling until a resource is available. The LinkedBlockingQueue is a good choice in this case. A borrower can block indefinitely with take, or limit the time it is willing to block with poll.
A less common case in when a client is not willing to block at all, but has the ability to create a resource for itself if the pool is empty. In that case, a ConcurrentLinkedQueue is a good choice. This is sort of a gray area where it would be nice to share a resource (e.g., memory) as much as possible, but speed is even more important. In the worse case, this degenerates to every thread having its own instance of the resource; then it would have been more efficient not to bother trying to share among threads.
Both of these collections give good performance and ease of use in a concurrent application. For non-concurrent applications, an ArrayList is hard to beat. Even for collections that grow dynamically, the per-element overhead of a LinkedList allows an ArrayList with some empty slots to stay competitive memory-wise.
You would see BlockingQueue in multi-threaded situations. For example you need pass in a BlockingQueue as a parameter to create ThreadPoolExecutor if you want to create one using constructor. Depending on the type of queue you pass in the executor could act differently.
It is a Queue implementation that additionally supports operations that
wait for the queue to become non-empty when retrieving an element,
and
wait for space to become available in the queue when storing an
element.
If you required above functionality will be followed by your Queue implementation then use Blocking Queue