Bir geliştirici için en büyük kabuslardan biri, uygulamanın bellek (RAM) kullanımının kontrolsüzce şişmesidir. Eğer büyük veri setleriyle çalışıyorsanız, verinin tamamının gelmesini beklemek yerine, gelen her parçayı anında işlemeye başlamalısınız.
1. IAsyncEnumerable
C# 8.0 ile hayatımıza giren IAsyncEnumerable<T>, asenkron bir foreach yapısı kurmamızı sağlar. Bu, veritabanından milyonlarca satır çekerken veya devasa bir dosyayı satır satır okurken RAM'i korumanın en zarif yoludur.
2. Üretici-Tüketici (Producer-Consumer) Deseni
Bazen veriyi okuma hızı (I/O) ile işleme hızı (CPU) birbirini tutmaz. Biri hızlıyken diğeri yavaş kalabilir. System.Threading.Channels kütüphanesi, bu iki dünya arasında yüksek performanslı, thread-safe bir tampon bölge (buffer) oluşturur.
Aşağıdaki kod bloğu hem Parallel hem de Async davranışı birleştirmemizi sağlar.
using System.Threading.Channels;
public async Task ProcessDataWithChannels()
{
// 1000 öğelik bir kanal (buffer) oluşturuyoruz.
var channel = Channel.CreateBounded<string>(1000);
// PRODUCER: Veriyi asenkron okuyan ve kanala yazan görev.
var producer = Task.Run(async () =>
{
await foreach (var line in ReadLargeFileAsync("bigdata.log"))
{
await channel.Writer.WriteAsync(line);
}
channel.Writer.Complete();
});
// CONSUMER: Kanaldan gelen veriyi PARALEL işleyen görev.
// MaxDegreeOfParallelism ile CPU çekirdeklerini kullanıyoruz.
var consumer = Task.Run(async () =>
{
var options = new ParallelOptions { MaxDegreeOfParallelism = Environment.ProcessorCount };
await Parallel.ForEachAsync(channel.Reader.ReadAllAsync(), options, async (line, ct) =>
{
// CPU-Bound işleme
AnalyzeLine(line);
await Task.Yield(); // Thread Pool dengesi için küçük bir mola
});
});
await Task.WhenAll(producer, consumer);
}Neden Bu Yapıyı Kullanmalıyız?
Bellek Yönetimi:
BoundedChannelsayesinde, tüketici yetişemezse üreticiyi yavaşlatırız (Backpressure). Böylece RAM patlamaz.Maksimum Verim: Dosya hala diskten okunurken (I/O), ilk okunan satırlar çoktan paralel olarak işlenmeye (CPU) başlar. İki aşama birbirini beklemez.
Thread Güvenliği:
lockveya karmaşıkConcurrentQueueyönetimleriyle uğraşmazsınız;Channelsaltyapısı bunu sizin yerinize en optimize şekilde yapar.
