I see in the code here a lot of
executorService.submit(() -> {
// do stuff
}).get();
...and I wonder why is the executorService used like this, submitting something you will immediately get?
Calling an immediate get()
forces the ExecutorService
to process "do stuff" in the executor service's threadpool rather than the local thread, which may for example choke processing if the maximum number of threads allocated to it is small, despite there being a great many threads running to handle requests.
Consider an obvious example of an executor service that has only 1 thread:
ExecutorService executorService = Executors.newSingleThreadExecutor();
and the example code being called from say an HttpRequestHandler
.
By using the immediate get()
processing of "do stuff" will be serialized, which may be desirable or a requirement, despite there being many simultaneous requests being processed each in their own thread.
Without the wrapper of executorService.submit(...).get()
, processing of "do stuff" would be done in parallel in the request handler's thread, which may be fine or may cause problems if "do stuff" is particularly expensive or constrained in some way if parallelism is unbounded.
Parallelism can be limited/bounded instead of eliminated as follows:
ExecutorService executorService = Executors.newFixedThreadPool(3);
would limit processing to (for example) a maximum of 3 concurrently processing "do stuff"s, despite there being a great many requests being processed simultaneously.
Other more subtle effects are possible to via the choice of Thread
in which "do stuff" runs. Consider:
ExecutorService executorService = Executors.newSingleThreadExecutor(myThreadFactory);
will make "do stuff" run in a custom type of thread, rather than in the thread type chosen for the HttpRequestHandler
.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With