Samuel Lenoy
Samuel Lenoy

Reputation: 3

Parallel Stream Hash Sets

I have the following issue programming in Java 8. The HashSet "mySet" ususally contains thousands of integers and is the bottleneck of my programm. Its executed pretty often. Speeding it up would result in much faster execution times.

void doStuff(int val){
    for (int i : mySet) {
        if (val > limits)
            alpha = arrayA[i] + arrayB[val];
        else
            alpha = arrayK[i][val] + arrayA[i] + arrayB[val];

        if (cmpArray[i] > alpha) {
            cmpArray[i] = alpha;
            arrayC[i] = val;
        }
        if (alpha == 0) {
            zeroSet.add(i);
        }
    }
}

I tried to use parallel streams to have this work done faster:

void doStuff(int val){
    if (val > limits)
            mySet
           .parallelStream()
           .filter(p -> this.cmpArray[p] > -(arrayA[p] + arrayB[val]))
           .forEach(p -> op(p, val, -(arrayA[p] + arrayB[val])));
        else
            mySet
           .parallelStream()
           .filter(p -> this.alpha[p] > arrayK[p][val] - arrayA[p] - arrayB[val])
           .forEach(p -> op(p, val, arrayK[p][val] - arrayA[p] - arrayB[val]));

    for (int i : mySet()) { 
        if (arrayA[i] == 0) {
            zeroSet.add(i); 
        }
    }

void op(int p, int val, int alpha){
    cmpArray[p] = alpha;
    arrayC[p] = val;
}

I was not able to parallelize the HashSet-Function add(). It resulted in some strange outcomes. Can anyone give me a keyword, what to look for in order to understand whats going on? Is there even a chance to parallelize this code?

I don't want you to solve the problem for me but just to check if I am on the right track :-D

Thanks for your replies.

Best, Sam

Upvotes: 0

Views: 1737

Answers (1)

Zaiyang Li
Zaiyang Li

Reputation: 102

Note that the HashSet implementation is not thread-safe. Multiple threads adding element will corrupt the data set.

See documentation

In order to parallelise the loop, one must create a new Set.

Replace

for (int i : mySet()) { 
    if (arrayA[i] == 0) {
        zeroSet.add(i); 
    }
}

with

zeroSet = mySet
      .parallelStream()
      .filter(i -> arrs[i] == 0)
      .collect(Collectors.toSet());

Hope this helps :)

Upvotes: 1

Related Questions