Hi!
Nach meinem autodidaktischen Verständnis sehe ich das so:
Folgendes ist das Szenario:
(1) Definition eines generischen Provider Interfaces
interface IDataProvider<D, I>
(2) Definition einer Exception, die als Parameter einen IDataProvider bekommt (throw new MyException(this)).
Hier fordert der Compiler jetzt eine Typisierung ein.
Der Compiler fordert eigentlich immer eine Typisierung ein. Nur, wie soll er sie erkennen, wenn erst zur Laufzeit die Typen aufgrund des übergebenen Objekts bekannt werden? Ohne dass du der Exception-Klasse die Typen verrätst, kann sie nichts typspezifisches mit dem Argument anfangen, jedenfalls nicht ohne Typecast.
2.1 Aus der Javawelt kommend würde ich einen Wildcard verwenden
MyException(IDataProvider<? extends Object, ? extends Object>)
Wo ist dann der Vorteil der starken Typisierung, wenn du nur Object vorgibst? Dann kannst du gleich auf die Generic verzichten und object/Object verwenden.
2.3 also definiere ich die Exception selbst als generisch
MyException<D, I>
MyException(IDataProvider<D, I>)
Das funktioniert, zwingt mich jetzt aber beim Werfen der Exception dazu, die Exception entsprechend zu typisieren. Erscheint mir etwas viel für ein
throw new MyException(this).
Nun weiß aber MyException aufgrund der beim Instantiieren angegebenen konkreten Typen, was Phase ist.
Danke, ich geh jetzt arbeiten, zurück in meine Java-Welt.
Nicht alles was erlaubt ist, ist auch gut. Dein verlinkter Artikel verlinkte auf einen über Generic type parameter variance in the CLR, in dem unter anderem zu lesen ist, dass selbst in Java die covarianten Arrays gar nicht hätten enthalten sein sollen.
Lo!