Bu durumda IQueryable<T>
ve arasında ayrım yapmak önemlidir IEnumerable<T>
. Kısacası IQueryable<T>
, optimize edilmiş bir sorgu sunmak için bir LINQ sağlayıcısı tarafından işlenir. Bu dönüştürme sırasında tüm C # ifadeleri desteklenmez, çünkü bunları arka uç özel bir sorguya (örn. SQL) çevirmek mümkün değildir veya uygulayıcı ifadeye olan ihtiyacı öngörmediğinden.
Buna karşılık IEnumerable<T>
, somut nesnelere karşı yürütülür ve bu nedenle dönüştürülmez. Yani, kullanım alanlarıdır yapılar, oldukça yaygındır IEnumerable<T>
, birlikte kullanılamaz IQueryable<T>
ve ayrıca bu IQueryables<T>
işlevlerin aynı kümesini desteklemeyen farklı LINQ sağlayıcıları tarafından desteklenmektedir.
Ancak, sorguyu değiştiren bazı geçici çözümler ( Phil'in yanıtı gibi ) vardır. Ayrıca, daha genel bir yaklaşım IEnumerable<T>
olarak, sorgunun spesifikasyonuna devam etmeden önce bir önceye geri dönmek mümkündür . Bununla birlikte, bu, özellikle kısıtlamalarda (örn. Maddeler nerede) kullanıldığında bir performans isabetine sahip olabilir. Buna karşılık, dönüşümlerle uğraşırken, isabet performansı çok daha küçük, hatta bazen yok - sorgunuza bağlı olarak.
Yukarıdaki kod da şu şekilde yeniden yazılabilir:
return this.ObjectContext.BranchCostDetails
.AsEnumerable()
.Where(
b => b.TarrifId == tariffId && b.Diameter == diameter
|| (b.TarrifId==tariffId && !string.IsNullOrWhiteSpace(b.Diameter))
||(!b.TarrifId.HasValue) && b.Diameter==diameter
);
NOT: Bu kodun Phil'in cevabından daha yüksek bir performans etkisi olacaktır . Ancak prensibi gösterir.
List<string> my = new List<string>(); var i = from m in my where !string.IsNullOrWhiteSpace(m) select m;