Kontekst: .NET 3.5, VS2008. Nie jestem pewien co do tytułu tego pytania, więc nie krępuj się komentować tytuł :-)Jak napisać ogólną klasę kontenera, która implementuje dany interfejs w języku C#?
Oto scenariusz: Mam kilka klas, na przykład Foo i Bar, wszystkie implementują następujący interfejs :
public interface IStartable
{
void Start();
void Stop();
}
a teraz chciałbym mieć klasę pojemnik, który dostaje IEnumerable <IStartable> jako argument konstruktora. Klasa ta, z kolei, należy również wdrożyć IStartable interfejs:
public class StartableGroup : IStartable // this is the container class
{
private readonly IEnumerable<IStartable> startables;
public StartableGroup(IEnumerable<IStartable> startables)
{
this.startables = startables;
}
public void Start()
{
foreach (var startable in startables)
{
startable.Start();
}
}
public void Stop()
{
foreach (var startable in startables)
{
startable.Stop();
}
}
}
Więc moje pytanie brzmi: w jaki sposób mogę to zrobić bez ręcznego pisania kodu i bez generowania kodu? Innymi słowy, chciałbym mieć coś takiego jak poniżej.
var arr = new IStartable[] { new Foo(), new Bar("wow") };
var mygroup = GroupGenerator<IStartable>.Create(arr);
mygroup.Start(); // --> calls Foo's Start and Bar's Start
Ograniczenia:
- Nie generowania kodu (czyli nie prawdziwy kod tekstowy w czasie kompilacji)
- interfejs ma tylko void metod, z lub bez argumentów
Motywacja:
- Mam dość dużą aplikację, z wieloma wtyczkami różnych interfejsów. Ręczne pisanie klasy "kontener grupowy" dla każdego interfejsu "przeciąża" projekt z klasami
- Ręczne pisanie kodu jest podatne na błędy
- Wszelkie dodatki lub aktualizacje sygnatur do interfejsu IStartable spowodują (ręczne) zmiany w " pojemnik grupa”klasa
- Nauka
rozumiem, że muszę użyć refleksji tutaj, ale wolałbym używać solidnych ram (jak Castle'a DynamicProxy lub RunSharp) zrobić okablowanie dla mnie.
Jakieś myśli?
Czyli * nie chcesz mieć klasy StartableGroup? Co jest z tym nie tak? – Noldorin
Czy mogę zapytać: dlaczego? Jaki problem musi rozwiązać ten problem? (może to wpłynąć na odpowiedź ...). –
@Noldorin, @Marc Gravell, dodano motywację do pierwotnego pytania. –