2010-12-30 3 views
1

Ziel C hat Protokoll, das die Äquivalenz der Schnittstelle in C# ist. Trotzdem setzt C# die Implementierung aller Methoden wie in Objective C 1.0 durch.Wie erhält man OPTIONALE Schnittstellenmethodenimplementierung in C# wie in Objective C 2.0?

Aber in Objective C 2.0 ist es jetzt möglich, eine Methode im Protokoll als optional zu markieren. Ermöglicht C# dies oder wird dies in Zukunft möglich sein? In der Theorie ist das Erzwingen der Zweck der Schnittstelle, aber in der Praxis habe ich die Last dieser harten Regel in einem komplexen Projekt erfahren: Sie müssen viele Interfaces erstellen, die schwer zu managen sind, Design oder Refactor zu verwalten. Für mich macht diese Entwicklung von Objective C 1.0 zu Objective C 2.0 wirklich Sinn.

Da Microsoft im Allgemeinen pragmatisch ist, wäre es großartig, wenn sie dies auch tun könnten.

+2

Nitpick: C# -Schnittstellen entsprechen chronologisch den Objective-C-Protokollen, nicht umgekehrt. Objective-C war der Haupteinfluss auf das Design von Java (in der Tat, als NeXTStep pleite ging, migrierten mehrere Mitglieder des Objective-C-Designteams zu Sun), und Protokolle (in Java als Interfaces bezeichnet) waren eine von vielen Dinge genommen. C# hat sie natürlich von Java bekommen. Objective-C hat sie von Smalltalk erhalten, aber in Smalltalk sind sie nur eine Dokumentationskonvention, während sie in Objective-C, Java und C# ein echtes Sprachmerkmal sind. Und damit endet die heutige Geschichtsstunde. –

+0

Dann wäre es nicht mehr "Interface". – Xaqron

+0

Java kann von Objective C inspiriert sein, aber nicht von dem wesentlichen Teil, der Smalltalk Messaging ist. C# ist Java sehr ähnlich, da Microsoft aus rechtlichen Gründen Java für Windows Platform nicht ändern konnte. – user310291

Antwort

6

Der nächste, den Sie kommen können, ist eine explizite Implementierung (also ist die Methode nicht Teil der öffentlich sichtbaren API) und gehen Sie einen Schritt weiter und lassen Sie es werfen, falls jemand es gefunden und versucht, es zu verwenden.

void ICanDoSomething.DoSomething() 
{ 
    throw new NotSupportedException(); // optional 
} 

Wenn jemand ein Objekt instanziiert, die die Schnittstelle implementiert, würden sie die explizite Implementierung nicht sehen, es sei denn, sie auf das Objekt beziehen, werden als die Schnittstelle.

Ein Beispiel aus dem BCL ist ein Array, das implementiert. hat eine Add Methode, die nicht für ein Array fester Länge nützlich ist. Es ist eine explizite Implementierung im Falle eines Arrays, und wenn Sie versuchen, es zu verwenden, wird es werfen.

int[] array = { 1, 2, 3 }; 
ICollection<int> collection = (ICollection<int>)array; 
collection.Add(4); // throws NotSupportedException 

Natürlich, wenn Sie einige "optionale" Verhalten vermeiden können, ist es am besten, dies zu tun. Teilen Sie es beispielsweise in mehrere Schnittstellen auf, sodass eine Klasse nur die Schnittstelle für das tatsächlich gewünschte Verhalten implementiert.

+0

Wahrscheinlich die beste Antwort, muss neu lesen und darüber nachdenken, dann werde ich es als gut markieren :) – user310291

1

Nein, das ist nicht möglich, weil dies gegen die Art einer Schnittstelle wäre. Wenn Sie die Implementierung einer Methode optional machen könnten, was würde passieren, wenn ein Codecode erwartet, dass diese Methode funktioniert, aber nicht, weil sie nicht implementiert ist? Eine Schnittstelle soll einen Vertrag von Methoden anbieten, die implementiert werden und genutzt werden können, optionale Methoden dagegen wären. Wenn Sie dies tun müssen, verletzen Sie wahrscheinlich ohnehin die Regel für die einfache Antwort.

+0

Ich stimme zu. Das "optionale" Ding für Interfaces in Objective C ist eine schlechte Idee und verschraubt sich komplett mit dem ganzen Zweck für sie. Wenn die Signatur nur von einigen Klassen verwendet werden soll, dann brechen Sie sie in ihre eigene Schnittstelle aus. – NotMe

+0

Es ist eine schlechte Idee nur in der Theorie. In der Praxis ist das, wie gesagt, keine schlechte Idee. Wie SOAP im Vergleich zu REST eine gute Idee war, scheint Google REST gewählt zu haben. – user310291