Given:
class Sum extends RecursiveAction { //line n1
static final int THRESHOLD_SIZE = 3;
int stIndex, lstIndex;
int[] data;
public Sum(int[] data, int start, int end) {
this.data = data;
this.stIndex = start;
this.lstIndex = end;
}
protected void compute() {
int sum = 0;
if (lstIndex - stIndex <= THRESHOLD_SIZE) {
for (int i = stIndex; i < lstIndex; i++) {
sum += data[i];
}
System.out.println(sum);
} else {
new Sum(data, stIndex + THRESHOLD_SIZE, lstIndex).fork();
new Sum(data, stIndex,
Math.min(lstIndex, stIndex + THRESHOLD_SIZE)
).compute();
}
}
}
and the code fragment:
ForkJoinPool fjPool = new ForkJoinPool();
int data[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
fjPool.invoke(new Sum(data, 0, data.length));
and given that the sum of all integers from 1 to 10 is 55.
Which statement is true?
A. The program prints several values that total 55.
B. The program prints 55.
C. A compilation error occurs at line n1.
D. The program prints several values whose sum exceeds 55.
題解
ForkJoinPool可以將一個大問題拆成很多小問題來進行運算。而RecursiveAction是一種ForkJoinTask,沒有回傳值。
在這個題目中,要利用ForkJoinPool和RecursiveAction來進行整數陣列的元素加總計算。
呼叫ForkJoinPool物件的invoke方法後,會執行RecursiveAction的compute方法,此時stIndex=0、lstIndex=10。程式第15行的判斷式不成立,會再fork出新的Sum物件,用新的執行緒來計算「stIndex=3、lstIndex=10」的部份,而目前的執行緒則重新計算「stIndex=0、lstIndex=3」的部份。
「stIndex=0、lstIndex=3」,會計算sum=1+2+3=6,輸出「6」。
「stIndex=3、lstIndex=10」,會再fork出「stIndex=6、lstIndex=10」,計算「stIndex=3、lstIndex=6」的sum為4+5+6=15,輸出「15」。
「stIndex=6、lstIndex=10」,會再fork出「stIndex=9、lstIndex=10」,計算「stIndex=6、lstIndex=9」的sum為7+8+9=24,輸出「24」。
「stIndex=9、lstIndex=10」,會計算sum=10,輸出「10」。
以上輸出由於是在不同執行緒處理的關係,所以順序不是固定的,但這些輸出的值加總後,即為1加到10的總和「55」。所以答案是選項A。