Multithreading best practices in java - java

I'm new to Java programming. I have a use case where I have to execute 2 db queries parallely. The structure of my class is something like this:
class A {
public Object func_1() {
//executes db query1
}
public Object func_2() {
//executes db query1
}
}
Now I have a add another function func_3 in the same class which calls these 2 functions but also makes sure that they execute parallely. For this, I'm making use callables and futures. Is it the right way to use it this way? I'm storing the this variable in a temporary variable and then using this to call func_1 and func_2 from func_3(which I'm not sure is correct approach). Or is there any other way to handle cases like these?
class A {
public Object func_1() {
//executes db query1
}
public Object func_2() {
//executes db query1
}
public void func_3() {
final A that = this;
Callable call1 = new Callable() {
#Override
public Object call() {
return that.func_1();
}
}
Callable call2 = new Callable() {
#Override
public Object call() {
return that.func_2();
}
}
ArrayList<Callable<Object>> list = new ArrayList<Callable<Object>>();
list.add(call1);
list.add(call2);
ExecutorService executor = Executors.newFixedThreadPool(2);
ArrayList<Future<Object>> futureList = new ArrayList<Future<Object>>();
futureList = (ArrayList<Future<Object>>) executor.invokeAll(list);
//process result accordingly
}
}

First of all, you do NOT need to store this in another local variable: outer functions will be available just as func_1() or func_2() and when you want to get this of outer class you just use A.this.
Secondly, yes, it is common way to do it. Also, if you are going to call func_3 often - avoid creating of fixed thread pool, you should just pass it as params, since thread creation is rather 'costly'.

The whole idea of Executor(Service) is to use small number of threads for many small tasks. Here you use 2-threaded executor for 2 tasks. I would either create globally defined executor, or just spawn 2 threads for 2 tasks.

Related

How to wait for completion of multiple tasks in Java?

What is the proper way to implement concurrency in Java applications? I know about Threads and stuff, of course, I have been programming for Java for 10 years now, but haven't had too much experience with concurrency.
For example, I have to asynchronously load a few resources, and only after all have been loaded, can I proceed and do more work. Needless to say, there is no order how they will finish. How do I do this?
In JavaScript, I like using the jQuery.deferred infrastructure, to say
$.when(deferred1,deferred2,deferred3...)
.done(
function(){//here everything is done
...
});
But what do I do in Java?
You can achieve it in multiple ways.
1.ExecutorService invokeAll() API
Executes the given tasks, returning a list of Futures holding their status and results when all complete.
2.CountDownLatch
A synchronization aid that allows one or more threads to wait until a set of operations being performed in other threads completes.
A CountDownLatch is initialized with a given count. The await methods block until the current count reaches zero due to invocations of the countDown() method, after which all waiting threads are released and any subsequent invocations of await return immediately. This is a one-shot phenomenon -- the count cannot be reset. If you need a version that resets the count, consider using a CyclicBarrier.
3.ForkJoinPool or newWorkStealingPool() in Executors is other way
Have a look at related SE questions:
How to wait for a thread that spawns it's own thread?
Executors: How to synchronously wait until all tasks have finished if tasks are created recursively?
I would use parallel stream.
Stream.of(runnable1, runnable2, runnable3).parallel().forEach(r -> r.run());
// do something after all these are done.
If you need this to be asynchronous, then you might use a pool or Thread.
I have to asynchronously load a few resources,
You could collect these resources like this.
List<String> urls = ....
Map<String, String> map = urls.parallelStream()
.collect(Collectors.toMap(u -> u, u -> download(u)));
This will give you a mapping of all the resources once they have been downloaded concurrently. The concurrency will be the number of CPUs you have by default.
If I'm not using parallel Streams or Spring MVC's TaskExecutor, I usually use CountDownLatch. Instantiate with # of tasks, reduce once for each thread that completes its task. CountDownLatch.await() waits until the latch is at 0. Really useful.
Read more here: JavaDocs
Personally, I would do something like this if I am using Java 8 or later.
// Retrieving instagram followers
CompletableFuture<Integer> instagramFollowers = CompletableFuture.supplyAsync(() -> {
// getInstaFollowers(userId);
return 0; // default value
});
// Retrieving twitter followers
CompletableFuture<Integer> twitterFollowers = CompletableFuture.supplyAsync(() -> {
// getTwFollowers(userId);
return 0; // default value
});
System.out.println("Calculating Total Followers...");
CompletableFuture<Integer> totalFollowers = instagramFollowers
.thenCombine(twitterFollowers, (instaFollowers, twFollowers) -> {
return instaFollowers + twFollowers; // can be replaced with method reference
});
System.out.println("Total followers: " + totalFollowers.get()); // blocks until both the above tasks are complete
I used supplyAsync() as I am returning some value (no. of followers in this case) from the tasks otherwise I could have used runAsync(). Both of these run the task in a separate thread.
Finally, I used thenCombine() to join both the CompletableFuture. You could also use thenCompose() to join two CompletableFuture if one depends on the other. But in this case, as both the tasks can be executed in parallel, I used thenCombine().
The methods getInstaFollowers(userId) and getTwFollowers(userId) are simple HTTP calls or something.
You can use a ThreadPool and Executors to do this.
https://docs.oracle.com/javase/tutorial/essential/concurrency/pools.html
This is an example I use Threads. Its a static executerService with a fixed size of 50 threads.
public class ThreadPoolExecutor {
private static final ExecutorService executorService = Executors.newFixedThreadPool(50,
new ThreadFactoryBuilder().setNameFormat("thread-%d").build());
private static ThreadPoolExecutor instance = new ThreadPoolExecutor();
public static ThreadPoolExecutor getInstance() {
return instance;
}
public <T> Future<? extends T> queueJob(Callable<? extends T> task) {
return executorService.submit(task);
}
public void shutdown() {
executorService.shutdown();
}
}
The business logic for the executer is used like this: (You can use Callable or Runnable. Callable can return something, Runnable not)
public class MultipleExecutor implements Callable<ReturnType> {//your code}
And the call of the executer:
ThreadPoolExecutor threadPoolExecutor = ThreadPoolExecutor.getInstance();
List<Future<? extends ReturnType>> results = new LinkedList<>();
for (Type Type : typeList) {
Future<? extends ReturnType> future = threadPoolExecutor.queueJob(
new MultipleExecutor(needed parameters));
results.add(future);
}
for (Future<? extends ReturnType> result : results) {
try {
if (result.get() != null) {
result.get(); // here you get the return of one thread
}
} catch (InterruptedException | ExecutionException e) {
logger.error(e, e);
}
}
The same behaviour as with $.Deferred in jQuery you can archive in Java 8 with a class called CompletableFuture. This class provides the API for working with Promises. In order to create async code you can use one of it's static creational methods like #runAsync, #supplyAsync. Then applying some computation of results with #thenApply.
I usually opt for an async notify-start, notify-progress, notify-end approach:
class Task extends Thread {
private ThreadLauncher parent;
public Task(ThreadLauncher parent) {
super();
this.parent = parent;
}
public void run() {
doStuff();
parent.notifyEnd(this);
}
public /*abstract*/ void doStuff() {
// ...
}
}
class ThreadLauncher {
public void stuff() {
for (int i=0; i<10; i++)
new Task(this).start();
}
public void notifyEnd(Task who) {
// ...
}
}

java threading method within object with return value

I am pretty new to using multithreading, but I want to invoke a method asynchronously (in a separate Thread) rather than invoking it synchronously. The basic idea is that I'm creating a socket server with an object in memory, so for each client I will have to run something like object.getStuff() asynchronously.
The two constructs I found were:
having the class implement Runnable and threading this and
declaring a runnable class within a method.
Additionally this method needs a return value- will it be necessary to use Executor and Callable to achieve this? Could someone point me in the right direction for implementing this?
I have tried implement option 2, but this doesn't appear to be processing concurrently:
public class Test {
private ExecutorService exec = Executors.newFixedThreadPool(10);
public Thing getStuff(){
class Getter implements Callable<Thing>{
public Thing call(){
//do collection stuff
return Thing;
}
}
Callable<Thing> callable = new Getter();
Future<Thing> future = exec.submit(callable);
return future.get();
}
}
I am instantiating a single test object for the server and calling getStuff() for each client connection.
Threading Tutorial
The Java tutorial on concurrency has a good section on this. It's at https://docs.oracle.com/javase/tutorial/essential/concurrency/runthread.html. Essentially, you can either implement Runnable or Callable, or inherit from Thread.
Subclassing Thread
You can write a class, including an anonymous inner class, that extends Thread. Instantiate it, then invoke the start() method.
public class MyThread extends Thread {
public void run() {
System.out.println("This is a thread");
}
public static void main(String[] args) {
MyThread m = new MyThread();
m.start();
}
}
Implementing Runnable
You can write a class that implements Runnable, then wrap an instance in a Thread and invoke start(). Very much like the previous.
public class MyRunnable implements Runnable {
public void run() {
System.out.println("This is a thread");
}
public static void main(String[] args) {
MyRunnable r = new MyRunnable();
(new Thread(r)).start();
}
}
Return Value
Runnable doesn't allow for return values. If you need that, you need to implement Callable instead. Callable looks a lot like Runnable, except you override the call() method instead of the run() method, and you need to give it to an ExecutorService.
public class MyCallable implements Callable<Integer> {
public Integer call() {
System.out.println("A thread using Callable<Integer>");
return 42;
}
public static void main(String[] args) {
MyCallable c = new MyCallable();
Future<Integer> f = Executors.newSingleThreadExecutor().submit(c));
System.out.println("The thread returned: " +
f.get());
}
}
The two constructs I found were 1) having the class implement Runnable and threading 'this' and 2) declaring a runnable class within a method.
Option (2) probably is better. Most programs would be improved if they had more classes, not fewer. Each named entity in a program—each package, class, method, whatever—should have just one responsibility. In your option (1), you are asking the class to do two things.
For your option (2), you don't actually have to declare a whole class. You can either use an anonymous inner class, or if you can go with Java8 all the way, you can use a lambda expression. Google for either one to learn more.
Additionally this method needs a return value.
The classic way, is for the Runnable object to return the value through one of its own fields before the thread terminates. Then the parent thread, can examine the object and get the return value afterward.
Will it be necessary to use Executor and Callable to achieve this?
Necessary? A lot of people think that ExecutorService is a Good Thing.
Sounds like you are creating a server that serves multiple clients. Do these clients continually connect and disconnect? The advantage of using a thread pool (i.e., ThreadPoolExecutor) is that it saves your program from continually creating and destroying threads (e.g., every time a client connects/disconnects). Creating and destroying threads is expensive. If you have a lot of clients connecting and disconnecting, then using a thread pool could make a big difference in the performance of your server.
Creating and managing threads by yourself is generally bad approach.
As you already pointed - use Executors utility class to create executor and submit Callables to it.
public class RunWResult implements Runable{
private volatile ResultType var;
//the thread method
public void run(){
...
//generate a result and save it to var
var = someResult();
//notify waiting threads that a result has been generated
synchronized(this){
notify();
}
}
public ResultType runWithResult(){
//run the thread generating a result
Thread t = new Thread(this);
t.start();
//wait for t to create a result
try{
wait();
}catch(InterruptedException e){}
//return the result
return var;
}
}

How do i get returned value from inner Thread Runnable method in Java?

How do i assign Status with CallMe() using isFinish() to have returned value true?
public static boolean isFinish ()
{
boolean Status = false;
new Thread(new Runnable()
{
public void run()
{
/* This shell return true or false
* How do you keep it in Status
*/
CallMe();
}
}).start();
/* How can i get the true or false exactly from CallMe? here */
return Status;
}
public static boolean CallMe()
{
/* some heavy loads ... */
return true;
}
There are two ways of doing this.
The first is to use a future computation result and the other is to have a shared variable.
I think that the first method is much cleaner than the second, but sometimes you need to push values to the thread too.
Using a RunnableFuture.
FutureTask implements a RunnableFuture. So you create that task which, once executed, will have a value.
RunnableFuture f = new FutureTask(new Callable<Boolean>() {
// implement call
});
// start the thread to execute it (you may also use an Executor)
new Thread(f).start();
// get the result
f.get();
Using a holder class
You create a class holding a value and share a reference to that class. You may create your own class or simply use the AtomicReference.
By holder class, I mean a class that has a public modifiable attribute.
// create the shared variable
final AtomicBoolean b = new AtomicBoolean();
// create your thread
Thread t = new Thread(new Runnable() {
public void run() {
// you can use b in here
}
});
t.start();
// wait for the thread
t.join();
b.get();
You rewrite the code to use Callable<Boolean> and obtain a Future when launching the Runnable.
Futures allow the launching thread to properly check that the value is ready and read it asynchronously. You could do the coding by hand, but since Future is now part of the standard JVM libraries, why would you (outside of a programming class)?
Working with raw threads, you could implement Runnable with a named type, and store the value in it.
class MyRunnable implements Runnable {
boolean status;
public void run() {
...
}
}
However, if you're working with another thread, you'll have to synchronize in some way.
It would be easier to use the higher-level tools provided by the java.util.concurrent hierarchy. You can submit a Callable to an Executor, and get a Future. You can ask the Future if it's done, and get the result. There's an Oracle tutorial here.

Propagating ThreadLocal to a new Thread fetched from a ExecutorService

I'm running a process in a separate thread with a timeout, using an ExecutorService and a Future (example code here) (the thread "spawning" takes place in a AOP Aspect).
Now, the main thread is a Resteasy request. Resteasy uses one ore more ThreadLocal variables to store some context information that I need to retrieve at some point in my Rest method call. Problem is, since the Resteasy thread is running in a new thread, the ThreadLocal variables are lost.
What would be the best way to "propagate" whatever ThreadLocal variable is used by Resteasy to the new thread? It seems that Resteasy uses more than one ThreadLocal variable to keep track of context information and I would like to "blindly" transfer all the information to the new thread.
I have looked at subclassing ThreadPoolExecutor and using the beforeExecute method to pass the current thread to the pool, but I couldn't find a way to pass the ThreadLocal variables to the pool.
Any suggestion?
Thanks
The set of ThreadLocal instances associated with a thread are held in private members of each Thread. Your only chance to enumerate these is to do some reflection on the Thread; this way, you can override the access restrictions on the thread's fields.
Once you can get the set of ThreadLocal, you could copy in the background threads using the beforeExecute() and afterExecute() hooks of ThreadPoolExecutor, or by creating a Runnable wrapper for your tasks that intercepts the run() call to set an unset the necessary ThreadLocal instances. Actually, the latter technique might work better, since it would give you a convenient place to store the ThreadLocal values at the time the task is queued.
Update: Here's a more concrete illustration of the second approach. Contrary to my original description, all that is stored in the wrapper is the calling thread, which is interrogated when the task is executed.
static Runnable wrap(Runnable task)
{
Thread caller = Thread.currentThread();
return () -> {
Iterable<ThreadLocal<?>> vars = copy(caller);
try {
task.run();
}
finally {
for (ThreadLocal<?> var : vars)
var.remove();
}
};
}
/**
* For each {#code ThreadLocal} in the specified thread, copy the thread's
* value to the current thread.
*
* #param caller the calling thread
* #return all of the {#code ThreadLocal} instances that are set on current thread
*/
private static Collection<ThreadLocal<?>> copy(Thread caller)
{
/* Use a nasty bunch of reflection to do this. */
throw new UnsupportedOperationException();
}
Based on #erickson answer I wrote this code. It is working for inheritableThreadLocals. It builds list of inheritableThreadLocals using same method as is used in Thread contructor. Of course I use reflection to do this. Also I override the executor class.
public class MyThreadPoolExecutor extends ThreadPoolExecutor
{
#Override
public void execute(Runnable command)
{
super.execute(new Wrapped(command, Thread.currentThread()));
}
}
Wrapper:
private class Wrapped implements Runnable
{
private final Runnable task;
private final Thread caller;
public Wrapped(Runnable task, Thread caller)
{
this.task = task;
this.caller = caller;
}
public void run()
{
Iterable<ThreadLocal<?>> vars = null;
try
{
vars = copy(caller);
}
catch (Exception e)
{
throw new RuntimeException("error when coping Threads", e);
}
try {
task.run();
}
finally {
for (ThreadLocal<?> var : vars)
var.remove();
}
}
}
copy method:
public static Iterable<ThreadLocal<?>> copy(Thread caller) throws Exception
{
List<ThreadLocal<?>> threadLocals = new ArrayList<>();
Field field = Thread.class.getDeclaredField("inheritableThreadLocals");
field.setAccessible(true);
Object map = field.get(caller);
Field table = Class.forName("java.lang.ThreadLocal$ThreadLocalMap").getDeclaredField("table");
table.setAccessible(true);
Method method = ThreadLocal.class
.getDeclaredMethod("createInheritedMap", Class.forName("java.lang.ThreadLocal$ThreadLocalMap"));
method.setAccessible(true);
Object o = method.invoke(null, map);
Field field2 = Thread.class.getDeclaredField("inheritableThreadLocals");
field2.setAccessible(true);
field2.set(Thread.currentThread(), o);
Object tbl = table.get(o);
int length = Array.getLength(tbl);
for (int i = 0; i < length; i++)
{
Object entry = Array.get(tbl, i);
Object value = null;
if (entry != null)
{
Method referentField = Class.forName("java.lang.ThreadLocal$ThreadLocalMap$Entry").getMethod(
"get");
referentField.setAccessible(true);
value = referentField.invoke(entry);
threadLocals.add((ThreadLocal<?>) value);
}
}
return threadLocals;
}
As I understand your problem, you can have a look at InheritableThreadLocal which is meant to pass ThreadLocal variables from Parent Thread context to Child Thread Context
I don't like Reflection approach. Alternative solution would be to implement executor wrapper and pass object directly as a ThreadLocal context to all child threads propagating a parent context.
public class PropagatedObject {
private ThreadLocal<ConcurrentHashMap<AbsorbedObjectType, Object>> data = new ThreadLocal<>();
//put, set, merge methods, etc
}
==>
public class ObjectAwareExecutor extends AbstractExecutorService {
private final ExecutorService delegate;
private final PropagatedObject objectAbsorber;
public ObjectAwareExecutor(ExecutorService delegate, PropagatedObject objectAbsorber){
this.delegate = delegate;
this.objectAbsorber = objectAbsorber;
}
#Override
public void execute(final Runnable command) {
final ConcurrentHashMap<String, Object> parentContext = objectAbsorber.get();
delegate.execute(() -> {
try{
objectAbsorber.set(parentContext);
command.run();
}finally {
parentContext.putAll(objectAbsorber.get());
objectAbsorber.clean();
}
});
objectAbsorber.merge(parentContext);
}
Here is an example to pass the current LocaleContext in parent thread to the child thread spanned by CompletableFuture[By default it used ForkJoinPool].
Just define all the things you wanted to do in a child thread inside a Runnable block. So when the CompletableFuture execute the Runnable block, its the child thread who is in control and voila you have the parent's ThreadLocal stuff set in Child's ThreadLocal.
The problem here is not the entire ThreadLocal is copied over. Only the LocaleContext is copied. Since the ThreadLocal is of private access to only the Thread it belongs too using Reflection and trying to get and set in Child is all too much of wacky stuff which might lead to memory leaks or performance hit.
So if you know the parameters you are interested from the ThreadLocal, then this solution works way cleaner.
public void parentClassMethod(Request request) {
LocaleContext currentLocale = LocaleContextHolder.getLocaleContext();
executeInChildThread(() -> {
LocaleContextHolder.setLocaleContext(currentLocale);
//Do whatever else you wanna do
}));
//Continue stuff you want to do with parent thread
}
private void executeInChildThread(Runnable runnable) {
try {
CompletableFuture.runAsync(runnable)
.get();
} catch (Exception e) {
LOGGER.error("something is wrong");
}
}
If you look at ThreadLocal code you can see:
public T get() {
Thread t = Thread.currentThread();
...
}
current thread cannot be overwritten.
Possible solutions:
Look at java 7 fork/join mechanism (but i think it's a bad way)
Look at endorsed mechanism to overwrite ThreadLocal class in your JVM.
Try to rewrite RESTEasy (you can use Refactor tools in your IDE to replace all ThreadLocal usage, it's look like easy)

Return values from Java Threads

I have a Java Thread like the following:
public class MyThread extends Thread {
MyService service;
String id;
public MyThread(String id) {
this.id = node;
}
public void run() {
User user = service.getUser(id)
}
}
I have about 300 ids, and every couple of seconds - I fire up threads to make a call for each of the id. Eg.
for(String id: ids) {
MyThread thread = new MyThread(id);
thread.start();
}
Now, I would like to collect the results from each threads, and do a batch insert to the database, instead of making 300 database inserts every 2 seconds.
Any idea how I can accomplish this?
The canonical approach is to use a Callable and an ExecutorService. submitting a Callable to an ExecutorService returns a (typesafe) Future from which you can get the result.
class TaskAsCallable implements Callable<Result> {
#Override
public Result call() {
return a new Result() // this is where the work is done.
}
}
ExecutorService executor = Executors.newFixedThreadPool(300);
Future<Result> task = executor.submit(new TaskAsCallable());
Result result = task.get(); // this blocks until result is ready
In your case, you probably want to use invokeAll which returns a List of Futures, or create that list yourself as you add tasks to the executor. To collect results, simply call get on each one.
If you want to collect all of the results before doing the database update, you can use the invokeAll method. This takes care of the bookkeeping that would be required if you submit tasks one at a time, like daveb suggests.
private static final ExecutorService workers = Executors.newCachedThreadPool();
...
Collection<Callable<User>> tasks = new ArrayList<Callable<User>>();
for (final String id : ids) {
tasks.add(new Callable<User>()
{
public User call()
throws Exception
{
return svc.getUser(id);
}
});
}
/* invokeAll blocks until all service requests complete,
* or a max of 10 seconds. */
List<Future<User>> results = workers.invokeAll(tasks, 10, TimeUnit.SECONDS);
for (Future<User> f : results) {
User user = f.get();
/* Add user to batch update. */
...
}
/* Commit batch. */
...
Store your result in your object. When it completes, have it drop itself into a synchronized collection (a synchronized queue comes to mind).
When you wish to collect your results to submit, grab everything from the queue and read your results from the objects. You might even have each object know how to "post" it's own results to the database, this way different classes can be submitted and all handled with the exact same tiny, elegant loop.
There are lots of tools in the JDK to help with this, but it is really easy once you start thinking of your thread as a true object and not just a bunch of crap around a "run" method. Once you start thinking of objects this way programming becomes much simpler and more satisfying.
In Java8 there is better way for doing this using CompletableFuture. Say we have class that get's id from the database, for simplicity we can just return a number as below,
static class GenerateNumber implements Supplier<Integer>{
private final int number;
GenerateNumber(int number){
this.number = number;
}
#Override
public Integer get() {
try {
TimeUnit.SECONDS.sleep(1);
}catch (InterruptedException e){
e.printStackTrace();
}
return this.number;
}
}
Now we can add the result to a concurrent collection once the results of every future is ready.
Collection<Integer> results = new ConcurrentLinkedQueue<>();
int tasks = 10;
CompletableFuture<?>[] allFutures = new CompletableFuture[tasks];
for (int i = 0; i < tasks; i++) {
int temp = i;
CompletableFuture<Integer> future = CompletableFuture.supplyAsync(()-> new GenerateNumber(temp).get(), executor);
allFutures[i] = future.thenAccept(results::add);
}
Now we can add a callback when all the futures are ready,
CompletableFuture.allOf(allFutures).thenAccept(c->{
System.out.println(results); // do something with result
});
You need to store the result in a something like singleton. This has to be properly synchronized.
This not the best advice as it is not good idea to handle raw Threads.
You could create a queue or list which you pass to the threads you create, the threads add their result to the list which gets emptied by a consumer which performs the batch insert.
The simplest approach is to pass an object to each thread (one object per thread) that will contain the result later. The main thread should keep a reference to each result object. When all threads are joined, you can use the results.
public class TopClass {
List<User> users = new ArrayList<User>();
void addUser(User user) {
synchronized(users) {
users.add(user);
}
}
void store() throws SQLException {
//storing code goes here
}
class MyThread extends Thread {
MyService service;
String id;
public MyThread(String id) {
this.id = node;
}
public void run() {
User user = service.getUser(id)
addUser(user);
}
}
}
You could make a class which extends Observable. Then your thread can call a method in the Observable class which would notify any classes that registered in that observer by calling Observable.notifyObservers(Object).
The observing class would implement Observer, and register itself with the Observable. You would then implement an update(Observable, Object) method that gets called when Observerable.notifyObservers(Object) is called.

Categories