348 Intermediate C Programming
checkRange , ( void *) & thd [ ind ]) ;69
i f ( rtv != 0)70
{71
printf (" ERROR : pthr ead_cr a te () fail n ");72
}73
}74
75
// wait for the threads to complete76
for ( ind = 0; ind < NUMB E R_THRE AD ; ind ++)77
{78
int rtv ;79
rtv = p thread_ join ( tid [ ind ] , NULL ) ;80
i f ( rtv != 0)81
{82
printf (" ERROR ; pthr ead_join () returns %d n" , rtv ) ;83
return EXIT _FAILUR E ;84
}85
total += thd [ ind ]. numSol ;86
}87
return total ;88
}89
There are a few details worth noting. First, the ranges checked by the threads must be
mutually exclusive. If one subset is checked by two or more threads and this subset’s sum
happens to equal to k, then this subset is counted multiple times and the total is wrong.
Second, the threads combined should check all subsets (excluding the empty set). Also,
checkRange needs to be consistent with the ranges assigned in subsetSum. In particular, if
checkRange uses <= maxval, then the maximum value checked by the last thread must be
maxCode - 1, not maxCode. You may notice that the individual threads share some data.
In each object, the attribute setA is a pointer to an array. This means that every thread
uses the same piece of memory. This is acceptable because the threads do not modify the
array. The other attributes are unique to each thread, because the object stores unshared
attributes (the int and unsigned int data).
21.5 Interleaving the Execution of Threads
The threads in the subset sum program shared a common array setA. Being able to share
memory between different threads is a characteristic of threaded programming; however, it
can sometimes be problematic. In the subset sum case, the threads never modify the shared
memory (i.e., setA), but only read the elements from the array. The only memory that the
threads modify is the attribute numSol, and each thread has a unique copy of this variable.
The main thread waits until all the threads are complete by calling pthread join on each
thread. Then the main thread adds the numSol values. The threads never intend to modify
any piece of shared memory. What happens if threads share memory that may be read and
written? The following listing is a simple and instructive example:
// outsync .c1
#in clude < pthread .h >2
#in clude < stdio .h >3