Zastanów się, czy powszechne będzie posiadanie kolekcji obiektów o różnych kombinacjach umiejętności i czy kod może chcieć wykonać akcję na tych elementach w obrębie kolekcji, które je obsługują . Jeśli tak, i jeśli byłoby rozsądne „domyślne zachowanie” dla obiektów, które nie mają użytecznego wsparcia dla niektórych działań, pomocne może być wdrożenie interfejsów przez szeroką gamę klas, a nie tylko tych, które mogą zachowywać się pożytecznie.
Załóżmy na przykład, że tylko kilka rodzajów stworów może mieć Woozle i ktoś chce, aby takie stworzenia miały NumerOfWoozles
własność. Gdyby taka właściwość znajdowała się w interfejsie, który został zaimplementowany tylko przez stworzenia, które mogą mieć Woozle, wówczas kod, który chciał znaleźć całkowitą liczbę Woozles przechowywanych przez zbiór stworzeń mieszanych typów, musiałby powiedzieć coś w stylu:
int total = 0;
foreach (object it in creatures)
{
IWoozleCountable w = trycast(it, IWoozleCountable);
if (w != null) total += w.WoozleCount;
}
Gdyby jednak WoozleCount było członkiem Creature / ICreature, chociaż kilka podtypów zastąpiłoby domyślną implementację WoozleCount Creature, która zawsze zwraca zero, kod można uprościć w celu:
int total = 0;
foreach (ICreature it in creatures)
total += it.WoozleCount;
Chociaż niektórzy ludzie mogą się obawiać, że każde stworzenie stworzy właściwość WoozleCount, która jest naprawdę użyteczna tylko dla kilku podtypów, właściwość ta byłaby znacząca dla wszystkich typów, niezależnie od tego, czy przydałaby się w przypadku elementów tego typu, i uważałbym, że interfejs „zlewu kuchennego” jest mniej zapachowy niż operator Trycast.
IEnumerable
,IEquatable
itp