2011-04-18 20 views
17

Böyle bir IEnumerable döndüren bir yöntem var ..IEnumerable <T> döndüren bir yönteme adım atamıyor?

public virtual IEnumerable<Page> ToPages(){ 
    // foreach logic 
    yield return pages; 

    // more foreach logic 
    yield return otherPages; 

    // etc 
} 

yöntem bir bakıma ... çalışıyor gibi görünüyor. Ama gerçekten şaşırtıcı olan şey, içine adım atamıyorum! Ben her yerde hata ayıklayıcı noktaları yerleştiririm ve hata ayıklayıcı sadece onların üzerinden geçer!

Bunun neden olabileceğini bilen var mı?

+0

... Sen değil mi' türetilmiş bir sınıfta geçersiz kıldınız mı? –

cevap

27

Bu yöntem, numaralandırma işlemi yapana kadar çalışmaz.

foo.ToPages().ToList() // will enumerate and your breakpoint will be hit. 
+0

Bu katı bir cevaptır. IEnumerable <> her zaman tembel infaz anlamına gelir. Bir IEnumerable ve bir liste vs arasındaki çalışma arasındaki temel farklardan biridir. IEnumerable lezzet sadece zaman geldiğinde yineleme için talimatlar verecektir. Liste aslında koleksiyonda yürüyecek ve sonuçları hemen üretecek. –

+0

Bu işe yaradı ...ama bu garipliğin ötesinde. Neden böyle davranıyor? – Ciel

+1

StackOverflow bana 9 dakika içinde izin verdiğinde cevabınızı kabul edeceğim. Teşekkürler. Bu gerçekten beni şaşırtıyordu. – Ciel

0

Verim ara vermeye çalışın. Bu düzeltmeli.

+0

Ne demek istiyorsun? Tüm yöntemde her satırda kesme noktaları koymuştum ve hala hiçbir zaman bir adım atamıyorum. – Ciel

+0

"verim", fonksiyonun döndüğü noktadır, bunun üzerinde kırılmalıdır. –

+0

Olmalı, evet. Ama öyle değil. – Ciel

3

Sayısız yönteminiz, yalnızca üyelere erişmeyi denediğinizde yürütülür. Bu

" Ertelenmiş Yürütme" iade, ya da sadece çağrı edilir IEnumerable erişen aslında deneyin

(http://blogs.msdn.com/b/charlie/archive/2007/12/09/deferred-execution.aspx bakınız) denir; Diğerleri de belirtildiği gibi yineleyici aslında taşınana kadar

var p = obj.ToPages().ToList(); 
5

, bir yineleyici bloğunun vücut yürütülmez. Sadece yineleyici oluşturmak onu oluşturmaktan başka bir şey yapmaz. İnsanlar genellikle bu kafa karıştırıcıyı bulurlar.

yineleyici blokları çıkarlar tasarım ve uygulama buradasın, konuyla ilgili bazı iyi haberler ise:

Raymond Chen: (temel noktalara kısa tanıtımı)

http://blogs.msdn.com/b/oldnewthing/archive/2008/08/12/8849519.aspx

http://blogs.msdn.com/b/oldnewthing/archive/2008/08/13/8854601.aspx

http://blogs.msdn.com/b/oldnewthing/archive/2008/08/14/8862242.aspx

Jon Skeet: (l ong,) derinlemesine

http://csharpindepth.com/Articles/Chapter6/IteratorBlockImplementation.aspx

Eric Lippert'ın (me): (gelişmiş senaryolar ve köşe durumlarda)

bu bir aptal soru gibi görünüyor özür dilerim

http://blogs.msdn.com/b/ericlippert/archive/tags/iterators/