I have a program that works perfectly, unfortunately I have some calculations that takes a lot of time, some minutes.
My objective is to use multithreading to accelerate the parts that take so much time.
In this example I give the prototype of the part that I should parallelize.
public static ArrayList<Object2> createListOfObject2(ArrayList<Object1> mylist) {
ArrayList<Object2> listToReturn = new ArrayList<>();
Object2 object2;
for (int i = 0; i < mylist.size(); i++) {
for (int j = 0; j < mylist.size(); j++) {
object2 = heavyCalcul(mylist, i, j);
listToReturn.add(object2);
}
}
return listToReturn;
}
private static Object2 heavyCalcul(ArrayList<Object1> mylist, int i, int j) {
int weight = MyCalculator.getInstance().calcul(mylist.get(i),mylist.get(j));
Object2 Object2 = new Object2(weight);
return Object2;
}
As you can see the method
public static ArrayList<Object2> createListOfObject2(ArrayList<Object1> mylist)
gets a list of Object1, and should create another list of object2.
I made two for loops, and each time I create an object2 forming by two object, it should take O(n²) time. For bigger list it takes a long time.
So where should I put the multithreading and which type of list should I use?
The second Problem is that the class MyCalculator is a singleton Class, and I create only one object of it, and in my opinion even using multithreading the real program will not benefit of multithreading.
What are the rules I should follow to use multithreading?
Many Thanks.
The fact that your object is a singleton is irrelevant. What matters is shared mutable state. So, if your computation don't mutate shared state, and every computation is thus independant from the others, you can just use a parallel stream:
myList.parallelStream()
.flatMap(first -> myList.stream().map(second -> MyCalculator.getInstance().calcul(first, second)))
.collect(Collectors.toList());