Middle+
Fork/Join çerçevesi nedir ve Java'da nasıl kullanılır?
sobes.tech yapay zeka
AI'dan gelen yanıt
Fork/Join çerçevesi, görevleri verimli bir şekilde paralelleştirmek için tasarlanmış, rekürsif olarak daha küçük alt görevlere bölünebilen ve ardından (join) sonuçları birleştirilebilen özel bir Executor çerçevesi uygulamasıdır. "Böl ve yönet" (divide and conquer) ilkesine dayanır.
Ana bileşenler:
ForkJoinPool: Görevlerin yürütülmesini yöneten bir iş parçacığı havuzudur. "Work-stealing" mekanizması kullanır; havuzdaki boşta olan iş parçacıkları, meşgul olan diğer iş parçacıklarından görev çalabilir.ForkJoinTask: Bu çerçevede yürütülebilen bir görevi temsil eden soyut sınıftır. İki alt türü vardır:RecursiveAction: Sonuç döndürmeyen görev.RecursiveTask<V>:Vtüründe sonuç döndüren görev.
Kullanım:
RecursiveActionveyaRecursiveTask'tan türeyen bir sınıf oluşturulur.compute()yöntemi geçersiz kılınır. Bu yöntemde mantık tanımlanır:- Görev yeterince küçükse (bir eşik değerinden az), doğrudan yürütülür.
- Aksi takdirde, görev alt görevlere bölünür ve
fork()ile asenkron olarak başlatılır. - Alt görevlerin tamamlanması
join()ile beklenir ve sonuçlar birleştirilir.
- Bir
ForkJoinPoolörneği oluşturulur. - Görev,
invoke()veyasubmit()kullanılarak havuza gönderilir.
Örnek:
import java.util.concurrent.RecursiveTask;
import java.util.concurrent.ForkJoinPool;
class SumArrayTask extends RecursiveTask<Long> {
private final long[] array;
private final int start;
private final int end;
private static final int THRESHOLD = 1000; // Eşik değeri
public SumArrayTask(long[] array, int start, int end) {
this.array = array;
this.start = start;
this.end = end;
}
@Override
protected Long compute() {
if (end - start <= THRESHOLD) {
long sum = 0;
for (int i = start; i < end; i++) {
sum += array[i];
}
return sum;
} else {
int mid = start + (end - start) / 2;
SumArrayTask leftTask = new SumArrayTask(array, start, mid);
SumArrayTask rightTask = new SumArrayTask(array, mid, end);
leftTask.fork();
Long rightResult = rightTask.compute();
Long leftResult = leftTask.join();
return leftResult + rightResult;
}
}
}
// Ana kodda kullanım
// long[] data = new long[10000]; // Başlangıç verileri
// // data doldurulur
// ForkJoinPool pool = new ForkJoinPool();
// long sum = pool.invoke(new SumArrayTask(data, 0, data.length));
// pool.shutdown(); // Kullanımdan sonra havuzu kapat
Avantajlar:
- Otomatik iş parçacığı havuzu yönetimi.
- "Work-stealing" sayesinde verimli yük dağılımı.
- "Böl ve yönet" tipi görevler için geliştirilmiş performans.
Dezavantajlar:
- Tüm paralel görev türleri için uygun değildir.
- Basit görevler için diğer yaklaşımlara kıyasla daha karmaşık olabilir.