Często tego rodzaju zmienne są używane do konserwacji iteratorów. C# ma te wbudowane bezpośrednio w język za pomocą słowa kluczowego yield
. Oto przykład:
IEnumerable<int> TimesTable(int table)
{
for (int i=0 ; i<12 ; i++)
{
yield return i * table;
}
}
W tym przykładzie tworzymy wartości w tablicy n-razy, gdzie n jest określone przez wywołującego. Możemy to wykorzystać w dowolnym iterator jest używana, tak jak w foreach
pętli:
foreach (var value in TimesTable(3))
{
Console.Write(""+ value + " ");
}
... która produkuje:
3 6 9 12 15 18 21 24 27 30 33 36
W C++, to mógłby stosować zmienne statyczne jak te można opisane z VB (nie jestem VB facet więc nie wiem składni VB):
int TimesTable(int table) {
static i = 1;
if (i == 12) {
i = 1;
}
return i++ * table;
}
C# wersja jest lepsza niż w C++ (lub VB) równoważne becuase iterator może być odwołany ucho ly i może być wiele iteratorów aktywnych w danym momencie. Te rzeczy nie są prawdziwe dla wersji C++ bez większej pracy dewelopera. Z drugiej strony oznacza to, że jedyny przypadek, gdy coś podobnego do zmiennej statycznej jest poprawne w C# podczas implementacji iteratora, a wartość nie utrzymuje się poza tym zakresem.
Mam nadzieję, że przydaje się wam to.
Korzystanie z konstruktora statycznego w celu zainicjowania pola uczestnika przy zamknięciu jest prawdopodobnie nieco bliższe pod względem dostępu do zmiennej (w przeciwieństwie do pola statycznego, nie będzie widoczne przez odbicie na klasie lub widoczne dla innych metod klasy) –
@Ben - ciekawe podejście, ale dużo dodatkowej złożoności - przekonanie ludzi do zrozumienia przechwyconych zmiennych jest trudne w najlepszym momencie ;-p –
OK, rozumiem, ale * dlaczego *? Czy w jakiś sposób złamie OOP? – blez