Daha modern çözüm
Dahili koleksiyonun değiştirilebilir olması gerekmedikçe, System.Collections.Immutable
paketi kullanabilir, alan türünüzü değişmez bir koleksiyon olacak şekilde değiştirebilir ve sonra bunu doğrudan ifşa edebilirsiniz - Foo
tabii ki kendi kendine değişmez olduğunu varsayarak .
Soruyu daha doğrudan ele almak için yanıt güncellendi
Çağıran kod yalnızca koleksiyon üzerinde yineleniyorsa, dahili bir koleksiyonu bir IEnumerable yerine bir ReadOnlyCollection olarak göstermek için herhangi bir neden var mı?
Arama koduna ne kadar güvendiğinize bağlıdır. Bu üyeyi arayacak her şey üzerinde tam kontrole sahipseniz ve hiçbir kodun kullanılmayacağını garanti ediyorsanız :
ICollection<Foo> evil = (ICollection<Foo>) bar.Foos;
evil.Add(...);
o zaman elbette, koleksiyonu doğrudan iade etmenizin bir zararı olmayacaktır. Genelde bundan biraz daha paranoyak olmaya çalışırım.
Aynı şekilde, dediğiniz gibi: eğer sadece ihtiyacınız varsa IEnumerable<T>
, o zaman neden kendinizi daha güçlü bir şeye bağlayasınız?
Orijinal cevap
.NET 3.5 kullanıyorsanız, basit bir Atla çağrısı yaparak kopya oluşturmaktan ve basit atamadan kaçınabilirsiniz:
public IEnumerable<Foo> Foos {
get { return foos.Skip(0); }
}
(Önemsiz bir şekilde kaydırmak için pek çok başka seçenek var - Skip
fazla Seç / Nerede ile ilgili güzel olan şey , her yineleme için anlamsızca yürütecek bir temsilcinin olmamasıdır.)
.NET 3.5 kullanmıyorsanız, aynı şeyi yapmak için çok basit bir sarmalayıcı yazabilirsiniz:
public static IEnumerable<T> Wrapper<T>(IEnumerable<T> source)
{
foreach (T element in source)
{
yield return element;
}
}
ReadOnlyCollection
paranoyak iseniz , geri dönen koleksiyonu bir paketlemek isteyeceksiniz , ancak şimdi belirli bir uygulamaya bağlı değilsiniz.