Reputation: 447
I have a array of objects from which I am constructing an xml document using java like below -
Object[] arr = fetchData();
Document newDoc =DocumentBuilderFactory.newInstance().newDocumentBuilder().newDocument();
Element rootElement = newDoc.createElement("company");
for(int i=0;i<arr.length();i++)
{
Element staff = new Element("staff");
staff.setAttribute(new Attribute("id", i));
staff.addContent(new Element("firstname").setText(arr[i].getFirstName()));
staff.addContent(new Element("lastname").setText(arr[i].getLastName()));
staff.addContent(new Element("nickname").setText(arr[i].getNickName()));
staff.addContent(new Element("salary").setText(arr[i].getSalary()));
............
............
............
............
............
rootElement.appendChild(staff);
}
newDoc.appendChild(rootElement);
The xml generated will be of following form -
<company>
<staff id="1">
<firstname>Foo</firstname>
<lastname>Bar</lastname>
<nickname>FB</nickname>
<salary>999999</salary>
............
............
............
............
</staff>
......
......
</company>
Above solution is working fine for small size of arrays but when array size increases it takes long time to process because of sequential processing of above code. Is there any way to process construction of staff element parallel either by using java 8 Stream parallel processing or threads in java?
Updated solution using CompletableFuture :
Object[] arr = fetchData();
Document newDoc =DocumentBuilderFactory.newInstance().newDocumentBuilder().newDocument();
Element rootElement = newDoc.createElement("company");
List<CompletableFuture<Element>> futureElements = new ArrayList<>();
for (int x = 0; x < arr.length(); x++) {
Object e = arr[x];
CompletableFuture<Element> f = CompletableFuture.supplyAsync(() -> getElement(newDoc, e));
futureElements.add(f);
}
for (CompletableFuture<Element> e : futureElements)
rootElement.appendChild(e.get());
newDoc.appendChild(rootElement);
Upvotes: 1
Views: 508
Reputation: 2602
What you could use is CompletableFutures
This way you could generate all the "staff" elements in a new thread then wait for them all to complete and add them
List<CompletableFuture<Element>> futureElements = new ArrayList<>()
for(int x = 0; x < arr.length; x++){
//getElement(arr[x]) is the get staff element logic
CompletableFuture<Element> f = CompletableFuture.supplyAsync(() -> getElement(arr[x]))
futureElements.add(f);
}
CompletableFuture<Void> allOf = CompletableFuture.allOf(futureElements.toArray(new CompletableFuture[0]))
Now you can either modify the allOf CompletableFuture or you can use things like thenAccept() to create a new thread that will start as soon as all others complete, or do a .get() to join back to the main thread.
if you do a .get() then you can do something like
futureElements.forEach(f -> rootElement.append(f.get()));
Upvotes: 3