Ich bin an einem Punkt in meinem Entwicklungslernen angelangt, an dem ich das Gefühl habe, mehr über Schnittstellen lernen zu müssen.
Ich lese häufig über sie, aber es scheint nur, dass ich sie nicht erfassen kann.
Ich habe Beispiele gelesen wie: Tierbasisklasse mit einer minimalen Schnittstelle für Dinge wie 'Walk', 'Run', 'GetLegs' usw. - aber ich habe noch nie an etwas gearbeitet und dachte: "Hey, ich sollte eine Schnittstelle verwenden Hier!"
Was vermisse ich? Warum ist es für mich so schwer zu verstehen! Ich bin nur eingeschüchtert von der Tatsache, dass ich möglicherweise nie einen konkreten Bedarf für einen erkennen werde - hauptsächlich aufgrund eines fehlenden Aspekts, um sie zu verstehen! Ich habe das Gefühl, dass mir als Entwickler etwas ganz oben fehlt! Wenn jemand eine solche Erfahrung gemacht und einen Durchbruch erzielt hat, würde ich mich über einige Tipps zum Verständnis dieses Konzepts freuen. Danke dir.
quelle
Antworten:
es löst dieses konkrete Problem:
Sie haben a, b, c, d von 4 verschiedenen Typen. Überall in Ihrem Code haben Sie so etwas wie:
Warum lassen Sie sie IProcessable nicht implementieren und tun dies dann?
Dies lässt sich viel besser skalieren, wenn Sie beispielsweise 50 Arten von Klassen hinzufügen, die alle dasselbe tun.
Ein weiteres konkretes Problem:
Haben Sie sich jemals System.Linq.Enumerable angesehen? Es definiert eine Menge Erweiterungsmethoden, die mit jedem Typ arbeiten, der IEnumerable implementiert. Da alles, was IEnumerable implementiert, im Grunde sagt "Ich unterstütze die Iteration in einem ungeordneten Muster für jeden Typ", können Sie komplexe Verhaltensweisen (Anzahl, Max, Wo, Auswahl usw.) für jeden aufzählbaren Typ definieren.
quelle
foreach(IMyCompanyWidgetFrobber a in list) a.Frob(widget, context);
Ich mag Jimmys Antwort sehr, aber ich habe das Gefühl, dass ich etwas hinzufügen muss. Der Schlüssel zum Ganzen ist das "fähige" in IProcess fähig. Es gibt eine Fähigkeit (oder Eigenschaft, die jedoch "intrinsische Qualität" bedeutet, nicht im Sinne von C # -Eigenschaften) des Objekts an, das die Schnittstelle implementiert. IAnimal ist wahrscheinlich kein gutes Beispiel für eine Schnittstelle, aber IWalkable ist möglicherweise eine gute Schnittstelle, wenn Ihr System viele Dinge hat, die laufen können. Möglicherweise haben Sie von Tieren abgeleitete Klassen wie Hund, Kuh, Fisch, Schlange. Die ersten beiden würden wahrscheinlich IWalkable implementieren, die beiden letzteren gehen nicht, also würden sie nicht. Jetzt fragen Sie: "Warum nicht einfach eine andere Superklasse haben, WalkingAnimal, von der Hund und Kuh abstammen?". Die Antwort ist, wenn Sie etwas vollständig außerhalb des Vererbungsbaums haben, das auch laufen kann, wie z. B. einen Roboter. Robot würde IWalkable implementieren, aber wahrscheinlich nicht von Animal ableiten. Wenn Sie eine Liste von Dingen wollen, die laufen können,
Ersetzen Sie jetzt IWalkable durch etwas Software-ähnlicheres wie IPersistable, und die Analogie kommt dem, was Sie in einem echten Programm sehen würden, viel näher.
quelle
Verwenden Sie Schnittstellen, wenn sich Implementierungen derselben Funktionalität unterscheiden.
Verwenden Sie eine Zusammenfassung / Basisklasse, wenn Sie eine gemeinsame konkrete Implementierung gemeinsam nutzen möchten.
quelle
is
Schlüsselwort)Stellen Sie sich eine Schnittstelle wie einen Vertrag vor. Es ist eine Möglichkeit zu sagen: "Diese Klassen sollten diesen Regeln folgen."
Im IAnimal-Beispiel kann man also sagen: "Ich muss Run, Walk usw. für Klassen aufrufen können, die IAnimal implementieren."
Warum ist das nützlich? Möglicherweise möchten Sie eine Funktion erstellen, die auf der Tatsache beruht, dass Sie beispielsweise Run and Walk für das Objekt aufrufen können müssen. Sie könnten Folgendes haben:
... und wiederholen Sie dies für alle Objekte, von denen Sie wissen, dass sie laufen und gehen können. Mit Ihrer IAnimal-Schnittstelle können Sie die Funktion jedoch einmal wie folgt definieren:
Wenn Sie gegen die Schnittstelle programmieren, vertrauen Sie im Wesentlichen darauf, dass die Klassen die Absicht der Schnittstelle implementieren. In unserem Beispiel lautet der Gedanke also: "Es ist mir egal, wie sie laufen und gehen, solange sie laufen und gehen. Mein RunThenWalk ist gültig, solange sie diese Vereinbarung erfüllen. Es funktioniert einwandfrei, ohne etwas anderes zu wissen." die Klasse."
Es gibt auch eine gute Diskussion in dieser verwandten Frage .
quelle
Mach dir nicht so viele Sorgen. Viele Entwickler müssen selten eine Schnittstelle schreiben. Sie werden häufig Schnittstellen verwenden, die im .NET Framework verfügbar sind. Wenn Sie jedoch nicht das Bedürfnis haben, bald eine zu schreiben, ist dies nicht überraschend.
Das Beispiel, das ich immer jemandem gebe, ist, wenn Sie eine Segelboot- und eine Viper-Klasse haben. Sie erben die Bootsklasse bzw. die Autoklasse. Angenommen, Sie müssen alle diese Objekte durchlaufen und ihre
Drive()
Methode aufrufen . Sie könnten zwar Code wie den folgenden schreiben:Es wäre viel einfacher zu schreiben:
quelle
Jimmy hat es richtig gemacht, wenn Sie eine einzelne Variable für mehrere Typen verwenden möchten, aber alle diese Typen dieselbe Methode über eine Schnittstellendeklaration implementieren. Dann können Sie sie als Hauptmethode für die vom Typ Schnittstelle eingegebene Variable aufrufen.
Es gibt jedoch einen zweiten Grund, Schnittstellen zu verwenden. Wenn der Projektarchitekt eine andere Person als der Implementierungscodierer ist oder mehrere Implementierungscodierer und ein Projektmanager vorhanden sind. Die verantwortliche Person kann eine ganze Reihe von Schnittstellen schreiben und sicherstellen, dass das System zusammenarbeitet, und es dann den Entwicklern überlassen, die Schnittstellen mit Implementierungsklassen auszufüllen. Dies ist der beste Weg, um sicherzustellen, dass mehrere Personen kompatible Klassen schreiben und dies parallel tun können.
quelle
Ich mag Armee-Analogie.
Sergeant ist es egal, ob Sie Softwareentwickler , Musiker oder Anwalt sind .
Sie werden als Soldat behandelt .
Es ist für Sergeant einfacher, sich nicht um bestimmte Details von Personen zu kümmern, mit denen er arbeitet,
alle als Soldatenabstraktionen zu behandeln (... und sie zu bestrafen, wenn sie sich nicht wie solche verhalten).
Die Fähigkeit von Personen, sich wie Soldaten zu verhalten, wird als Polymorphismus bezeichnet.
Schnittstellen sind Softwarekonstruktionen, mit denen Polymorphismus erreicht werden kann.
Die Notwendigkeit , Details zu abstrahieren, um Einfachheit zu erreichen, ist die Antwort auf Ihre Frage.
quelle
Nach meiner Erfahrung trat die treibende Kraft beim Erstellen von Schnittstellen erst auf, als ich mit Unit-Tests mit einem spöttischen Framework begann. Es wurde sehr deutlich, dass die Verwendung von Schnittstellen das Verspotten erheblich erleichtern würde (da das Framework von den virtuellen Methoden abhing). Als ich anfing, sah ich den Wert, die Schnittstelle zu meiner Klasse von der Implementierung zu abstrahieren. Auch wenn ich keine tatsächliche Schnittstelle erstelle, versuche ich jetzt, meine Methoden virtuell zu machen (Bereitstellung einer impliziten Schnittstelle, die überschrieben werden kann).
Es gibt viele andere Gründe, die ich gefunden habe, um die bewährte Methode des Refactorings von Schnittstellen zu verstärken, aber das Testen / Verspotten von Einheiten war der Grund für den ersten "Aha-Moment" praktischer Erfahrung.
EDIT : Zur Verdeutlichung habe ich beim Testen und Verspotten von Einheiten immer zwei Implementierungen - die reale, konkrete Implementierung und eine alternative Scheinimplementierung, die beim Testen verwendet wird. Sobald Sie zwei Implementierungen haben, wird der Wert der Schnittstelle offensichtlich - behandeln Sie sie in Bezug auf die Schnittstelle, damit Sie die Implementierung jederzeit ersetzen können. In diesem Fall ersetze ich es durch eine Scheinschnittstelle. Ich weiß, dass ich dies ohne eine tatsächliche Schnittstelle tun kann, wenn meine Klasse richtig aufgebaut ist, aber die Verwendung einer tatsächlichen Schnittstelle verstärkt dies und macht sie sauberer (für den Leser klarer). Ohne diesen Impuls hätte ich den Wert von Schnittstellen nicht geschätzt, da die meisten meiner Klassen nur eine einzige konkrete Implementierung haben.
quelle
Einige Beispiele ohne Programmierung, anhand derer Sie möglicherweise die geeignete Verwendung von Schnittstellen bei der Programmierung erkennen können.
Es gibt eine Schnittstelle zwischen elektrischen Geräten und dem Stromnetz - es sind die Konventionen über die Form der Stecker und Buchsen und die Spannungen / Ströme über ihnen. Wenn Sie ein neues elektrisches Gerät implementieren möchten, kann Ihr Stecker Dienste aus dem Netzwerk abrufen, solange er den Regeln entspricht. Dies macht die Erweiterbarkeit sehr einfach und reduziert oder senkt die Koordinierungskosten : Sie müssen den Stromversorger nicht über die Funktionsweise Ihres neuen Geräts informieren und eine separate Vereinbarung über den Anschluss Ihres neuen Geräts an das Netzwerk treffen.
Länder haben Standard-Schienenlehren. Dies ermöglicht eine Arbeitsteilung zwischen Ingenieurbüros, die Schienen abstellen, und Ingenieurbüros, die Züge bauen, um auf diesen Schienen zu fahren, und ermöglicht es Eisenbahnunternehmen , Züge zu ersetzen und zu verbessern , ohne das gesamte System neu zu gestalten.
Der Service, den ein Unternehmen einem Kunden bietet, kann als Schnittstelle bezeichnet werden: Eine gut definierte Schnittstelle betont den Service und verbirgt die Mittel . Wenn Sie einen Brief in eine Mailbox legen, erwarten Sie, dass das Postsystem den Brief innerhalb einer bestimmten Zeit zustellt, aber Sie haben keine Erwartungen an die Zustellung des Briefes: Sie müssen es nicht wissen , und der Postdienst hat die Flexibilität dazu Wählen Sie das Versandmittel, das den Anforderungen und den aktuellen Umständen am besten entspricht. Eine Ausnahme bildet die Möglichkeit der Kunden, Luftpost zu wählen - dies ist nicht die Art von Schnittstelle, die ein moderner Computerprogrammierer entworfen hätte, da sie zu viel von der Implementierung enthüllt.
Beispiele aus der Natur: Ich bin nicht besonders scharf auf die Beispiele eat (), makeSound (), move () usw. Sie beschreiben zwar das richtige Verhalten, aber sie beschreiben keine Interaktionen und wie sie aktiviert sind . Die offensichtlichen Beispiele für Schnittstellen, die Interaktionen in der Natur ermöglichen, betreffen die Fortpflanzung. Beispielsweise bietet eine Blume einer Biene eine bestimmte Schnittstelle, damit eine Bestäubung stattfinden kann.
quelle
Es ist durchaus möglich, Ihr ganzes Leben als .net-Entwickler zu verbringen und niemals Ihre eigenen Schnittstellen zu schreiben. Immerhin haben wir jahrzehntelang ohne sie gut überlebt und unsere Sprachen waren immer noch Turing-vollständig.
Ich kann Ihnen nicht sagen, warum Sie Schnittstellen benötigen, aber ich kann Ihnen eine Liste geben, wo wir sie in unserem aktuellen Projekt verwenden:
In unserem Plug-In-Modell laden wir Plug-Ins nach Schnittstelle und stellen diese Schnittstelle Plug-In-Writern zur Verfügung.
In unserem maschinellen Nachrichtensystem implementieren alle Nachrichtenklassen eine bestimmte Schnittstelle und werden über die Schnittstelle "entpackt".
Unser Konfigurationsmanagementsystem definiert eine Schnittstelle zum Festlegen und Abrufen von Konfigurationseinstellungen.
Wir haben eine Schnittstelle, die wir verwenden, um ein unangenehmes Zirkelverweisproblem zu vermeiden. (Tun Sie dies nicht, wenn Sie nicht müssen.)
Ich denke, wenn es eine Regel gibt, ist es, Schnittstellen zu verwenden, wenn Sie mehrere Klassen innerhalb einer is-a-Beziehung gruppieren möchten, aber keine Implementierung in der Basisklasse bereitstellen möchten.
quelle
Ein Codebeispiel (Kombination von Andrews mit einem Extra von mir an dem Zweck der Schnittstellen ), in dem auch erläutert wird, warum die Schnittstelle anstelle einer abstrakten Klasse für Sprachen ohne Unterstützung für Mehrfachvererbung (c # und Java):
Beachten Sie, dass FileLogger und DataBaseLogger die Schnittstelle nicht benötigen (möglicherweise eine abstrakte Logger-Basisklasse). Bedenken Sie jedoch, dass Sie einen Drittanbieter-Logger verwenden müssen, der Sie zur Verwendung einer Basisklasse zwingt (beispielsweise werden geschützte Methoden verfügbar gemacht, die Sie verwenden müssen). Da die Sprache keine Mehrfachvererbung unterstützt, können Sie den abstrakten Basisklassenansatz nicht verwenden.
Fazit: Verwenden Sie nach Möglichkeit eine Schnittstelle, um zusätzliche Flexibilität für Ihren Code zu erhalten. Ihre Implementierung ist weniger gebunden, sodass sie sich besser für Änderungen eignet.
quelle
Ich habe ab und zu Schnittstellen verwendet und hier ist meine neueste Verwendung (Namen wurden verallgemeinert):
Ich habe eine Reihe von benutzerdefinierten Steuerelementen in einer WinForm, die Daten in meinem Geschäftsobjekt speichern müssen. Ein Ansatz besteht darin, jedes Steuerelement separat aufzurufen:
Das Problem bei dieser Implementierung ist, dass ich jedes Mal, wenn ich ein Steuerelement hinzufüge, in meine Methode "Daten speichern" gehen und das neue Steuerelement hinzufügen muss.
Ich habe meine Steuerelemente geändert, um eine ISaveable-Schnittstelle mit der Methode SaveToBusinessObject (...) zu implementieren. Daher durchläuft meine Methode "Daten speichern" jetzt nur noch die Steuerelemente. Wenn sie eine ISaveable-Methode findet, ruft sie SaveToBusinessObject auf. Wenn nun ein neues Steuerelement benötigt wird, muss nur noch ISaveable in diesem Objekt implementiert werden (und niemals eine andere Klasse berühren).
Der häufig nicht realisierte Vorteil von Schnittstellen besteht darin, dass Sie Änderungen lokalisieren. Einmal definiert, ändern Sie selten den Gesamtfluss einer Anwendung, nehmen jedoch häufig Änderungen auf Detailebene vor. Wenn Sie die Details in bestimmten Objekten behalten, wirkt sich eine Änderung in ProcessA nicht auf eine Änderung in ProcessB aus. (Basisklassen bieten Ihnen auch diesen Vorteil.)
EDIT: Ein weiterer Vorteil ist die Spezifität der Aktionen. Wie in meinem Beispiel möchte ich nur die Daten speichern. Es ist mir egal, um welche Art von Steuerelement es sich handelt oder ob es etwas anderes kann - ich möchte nur wissen, ob ich die Daten im Steuerelement speichern kann. Es macht meinen Speichercode ziemlich klar - es gibt keine Überprüfungen, ob es sich um Text, Zahlen, Boolesche Werte oder was auch immer handelt, da das benutzerdefinierte Steuerelement all dies übernimmt.
quelle
Sie sollten eine Schnittstelle definieren, sobald Sie ein Verhalten für Ihre Klasse erzwingen müssen.
Das Verhalten eines Tieres kann Gehen, Essen, Laufen usw. umfassen. Daher definieren Sie sie als Schnittstellen.
Ein weiteres praktisches Beispiel ist die ActionListener-Schnittstelle (oder Runnable-Schnittstelle). Sie würden sie implementieren, wenn Sie ein bestimmtes Ereignis verfolgen müssen. Daher müssen Sie die Implementierung für die
actionPerformed(Event e)
Methode in Ihrer Klasse (oder Unterklasse) bereitstellen . In ähnlicher Weise stellen Sie für die Runnable-Schnittstelle die Implementierung für diepublic void run()
Methode bereit .Sie können diese Schnittstellen auch von einer beliebigen Anzahl von Klassen implementieren lassen.
Eine andere Instanz, in der Schnittstellen verwendet werden (in Java), ist die Implementierung der in C ++ angebotenen Mehrfachvererbung.
quelle
Angenommen, Sie möchten Belästigungen modellieren, die auftreten können, wenn Sie versuchen, einzuschlafen.
Modell vor Schnittstellen
Wie Sie deutlich sehen, können viele „Dinge“ ärgerlich sein, wenn Sie versuchen zu schlafen.
Verwendung von Klassen ohne Schnittstellen
Aber wenn es darum geht, diese Klassen zu verwenden, haben wir ein Problem. Sie haben nichts gemeinsam. Sie müssen jede Methode separat aufrufen.
Modell mit Schnittstellen
Um dieses Problem zu lösen, können wir ein Iterface einführen
Und implementieren Sie es in Klassen
Verwendung mit Schnittstellen
Dies erleichtert die Verwendung dieser Klassen erheblich
quelle
Neighbour
und mussLampJustOutsideYourWindow
auch implementierenAnnoying
?Das einfachste Beispiel ist so etwas wie Zahlungsabwickler (Paypal, PDS usw.).
Angenommen, Sie erstellen eine Schnittstelle IPaymentProcessor mit den Methoden ProcessACH und ProcessCreditCard.
Sie können jetzt eine konkrete Paypal-Implementierung implementieren. Wenn Sie diese Methoden verwenden, rufen Sie PayPal-spezifische Funktionen auf.
Wenn Sie später entscheiden, dass Sie zu einem anderen Anbieter wechseln müssen, können Sie dies tun. Erstellen Sie einfach eine weitere konkrete Implementierung für den neuen Anbieter. Da Sie nur an Ihre Schnittstelle (Vertrag) gebunden sind, können Sie die von Ihrer Anwendung verwendete Schnittstelle austauschen, ohne den Code zu ändern, der sie verwendet.
quelle
Außerdem können Sie Mock-Unit-Tests (.Net) durchführen. Wenn Ihre Klasse eine Schnittstelle verwendet, können Sie das Objekt in Ihrem Komponententest verspotten und die Logik einfach testen (ohne die Datenbank, den Webdienst usw. zu treffen).
http://www.nmock.org/
quelle
Wenn Sie die .NET Framework-Assemblys durchsuchen und einen Drilldown in die Basisklassen für eines der Standardobjekte durchführen, werden Sie viele Schnittstellen (Mitglieder mit dem Namen ISomeName) bemerken.
Schnittstellen dienen im Wesentlichen zur Implementierung großer oder kleiner Frameworks. Bei Schnittstellen ging es mir genauso, bis ich ein eigenes Framework schreiben wollte. Ich fand auch heraus, dass das Verständnis von Schnittstellen mir half, Frameworks viel schneller zu lernen. In dem Moment, in dem Sie für fast alles eine elegantere Lösung schreiben möchten, werden Sie feststellen, dass eine Benutzeroberfläche sehr sinnvoll ist. Es ist wie eine Methode, eine Klasse die passende Kleidung für den Job anziehen zu lassen. Noch wichtiger ist, dass Schnittstellen es Systemen ermöglichen, sich viel selbst zu dokumentieren, da komplexe Objekte weniger komplex werden, wenn die Klasse Schnittstellen implementiert, was zur Kategorisierung ihrer Funktionalität beiträgt.
Klassen implementieren Schnittstellen, wenn sie explizit oder implizit an einem Framework teilnehmen möchten. IDisposable ist beispielsweise eine allgemeine Schnittstelle, die eine Methodensignatur für die beliebte und nützliche Dispose () -Methode bereitstellt. In einem Framework müssen Sie oder ein anderer Entwickler nur wissen, dass ((IDisposable) myObject) .Dispose () verfügbar ist, um zu Bereinigungszwecken aufgerufen zu werden, wenn es IDisposable implementiert.
KLASSISCHES BEISPIEL: Ohne Implementierung der IDisposable-Schnittstelle können Sie das Schlüsselwortkonstrukt "using ()" in C # nicht verwenden, da jedes als Parameter angegebene Objekt implizit in IDisposable umgewandelt werden kann.
KOMPLEXES BEISPIEL: Ein komplexeres Beispiel wäre die System.ComponentModel.Component-Klasse. Diese Klasse implementiert sowohl IDisposable als auch IComponent. Die meisten, wenn nicht alle .NET-Objekte, denen ein visueller Designer zugeordnet ist, implementieren IComponent, sodass die IDE mit der Komponente interagieren kann.
SCHLUSSFOLGERUNG: Wenn Sie mit .NET Framework vertraut werden, müssen Sie als Erstes auf eine neue Klasse im Objektbrowser oder im (.NET) Reflector-Tool ( http://www.red-gate.com ) stoßen / products / Reflector / ) überprüft, von welcher Klasse es erbt und welche Schnittstellen es implementiert. .NET Reflector ist sogar noch besser als der Objektbrowser, da Sie damit auch die abgeleiteten Klassen anzeigen können. Auf diese Weise können Sie alle Objekte kennenlernen, die von einer bestimmten Klasse stammen, und so möglicherweise Informationen zu Framework-Funktionen erhalten, von denen Sie nicht wussten, dass sie existieren. Dies ist besonders wichtig, wenn dem .NET Framework aktualisierte oder neue Namespaces hinzugefügt werden.
quelle
Stellen Sie sich vor, Sie machen ein Ego-Shooter-Spiel. Der Spieler hat mehrere Waffen zur Auswahl.
Wir können eine Schnittstelle haben,
Gun
die eine Funktion definiertshoot()
.Wir brauchen nämlich verschiedene
Gun
KlassenunterklassenShotGun
Sniper
und so weiter.Schützenklasse
Der Schütze hat alle Waffen in seiner Rüstung. Erstellen wir ein
List
, um es darzustellen.Der Schütze fährt bei Bedarf mit der Funktion durch seine Waffen
switchGun()
Wir können die aktuelle Waffe mit der obigen Funktion einstellen und einfach die
shoot()
Funktion aufrufen , wenn siefire()
aufgerufen wird.Das Verhalten der Aufnahmefunktion hängt von den verschiedenen Implementierungen der
Gun
Schnittstelle ab.Fazit
Erstellen Sie eine Schnittstelle, wenn eine Klassenfunktion von einer Funktion einer anderen Klasse abhängig ist, deren Verhalten basierend auf der Instanz (dem Objekt) der implementierten Klasse geändert wird.
Zum Beispiel erwartet die
fire()
Funktion aus derShooter
Klasse, dass gun (Sniper
,ShotGun
) dieshoot()
Funktion implementiert . Also, wenn wir die Waffe wechseln und schießen.Wir haben das Verhalten der
fire()
Funktion geändert .quelle
Um das zu erweitern, was Larsenal gesagt hat. Eine Schnittstelle ist ein Vertrag, dem alle implementierenden Klassen folgen müssen. Aus diesem Grund können Sie eine Technik verwenden, die als Programmierung für den Vertrag bezeichnet wird. Dadurch kann Ihre Software unabhängig von der Implementierung werden.
quelle
Schnittstellen werden im Allgemeinen verwendet, wenn Sie ein Verhalten definieren möchten, das Objekte aufweisen können.
Ein gutes Beispiel hierfür in der .NET-Welt ist die IDisposable- Schnittstelle, die in allen Microsoft-Klassen verwendet wird, die Systemressourcen verwenden, die manuell freigegeben werden müssen. Es erfordert, dass die Klasse, die es implementiert, über eine Dispose () -Methode verfügt.
(Die Dispose () -Methode wird auch vom using-Sprachkonstrukt für VB.NET und C # aufgerufen , das nur mit
IDisposable
s funktioniert. )Beachten Sie, dass Sie mithilfe von Konstrukten wie
TypeOf ... Is
(VB.NET),is
(C #),instanceof
(Java) usw. überprüfen können, ob ein Objekt eine bestimmte Schnittstelle implementiert.quelle
Wie wahrscheinlich bereits mehrere Personen geantwortet haben, können Schnittstellen verwendet werden, um bestimmte Verhaltensweisen zwischen Klassen zu erzwingen, die diese Verhaltensweisen nicht auf die gleiche Weise implementieren. Wenn Sie also eine Schnittstelle implementieren, sagen Sie, dass Ihre Klasse das Verhalten der Schnittstelle hat. Die IAnimal-Schnittstelle wäre keine typische Schnittstelle, da Klassen für Hunde, Katzen, Vögel usw. Tierarten sind und sie wahrscheinlich erweitern sollten, was ein Fall von Vererbung ist. Stattdessen ähnelt eine Schnittstelle in diesem Fall eher dem Verhalten von Tieren, z. B. IRunnable, IFlyable, ITrainable usw.
Schnittstellen sind für viele Dinge gut, eines der wichtigsten Dinge ist die Steckbarkeit. Wenn Sie beispielsweise eine Methode mit einem List-Parameter deklarieren, kann alles, was die List-Schnittstelle implementiert, übergeben werden, sodass der Entwickler zu einem späteren Zeitpunkt eine andere Liste entfernen und einfügen kann, ohne eine Menge Code neu schreiben zu müssen.
Es ist möglich, dass Sie niemals Schnittstellen verwenden, aber wenn Sie ein Projekt von Grund auf neu entwerfen, insbesondere ein Framework, möchten Sie sich wahrscheinlich mit diesen vertraut machen.
Ich würde empfehlen, das Kapitel über Schnittstellen in Java Design von Coad, Mayfield und Kern zu lesen . Sie erklären es etwas besser als der durchschnittliche Einführungstext. Wenn Sie kein Java verwenden, können Sie einfach den Anfang des Kapitels lesen, bei dem es sich hauptsächlich um Konzepte handelt.
quelle
Wie alle Programmiertechniken, die Ihrem System Flexibilität verleihen, erhöhen auch die Schnittstellen die Komplexität. Sie sind oft großartig und können überall verwendet werden (Sie können eine Schnittstelle für alle Ihre Klassen erstellen). Auf diese Weise würden Sie jedoch ein komplexeres System erstellen, das schwieriger zu warten wäre.
Hier gibt es wie üblich einen Kompromiss: Flexibilität über Wartbarkeit. Welches ist wichtiger? Es gibt keine Antworten - es kommt auf das Projekt an. Aber denken Sie daran, dass jede Software gewartet werden muss ...
Also mein Rat: Verwenden Sie keine Schnittstellen, bis Sie sie wirklich brauchen. (Mit Visual Studio können Sie in 2 Sekunden eine Schnittstelle aus einer vorhandenen Klasse extrahieren - beeilen Sie sich also nicht.)
Wann müssen Sie jedoch eine Schnittstelle erstellen?
Ich mache es, wenn ich eine Methode umgestalte, die plötzlich zwei oder mehr ähnliche Klassen verarbeiten muss. Ich erstelle dann eine Schnittstelle, ordne diese Schnittstelle den zwei (oder mehr) ähnlichen Klassen zu und ändere den Methodenparametertyp (ersetze den Klassentyp durch den Schnittstellentyp).
Und es funktioniert: o)
Eine Ausnahme: Wenn ich Objekte verspotten soll, ist die Benutzeroberfläche viel einfacher zu bedienen. Deshalb erstelle ich oft nur dafür eine Schnittstelle.
PS: Wenn ich "Schnittstelle" schreibe, meine ich: "Schnittstelle einer beliebigen Basisklasse", einschließlich reiner Schnittstellenklassen. Beachten Sie, dass abstrakte Klassen oft eine bessere Wahl sind als reine Schnittstellen, da Sie ihnen Logik hinzufügen können.
Grüße, Sylvain.
quelle
Schnittstellen werden deutlich, wenn Sie Bibliotheksentwickler werden (jemand, der für andere Codierer codiert). Die meisten von uns beginnen als Anwendungsentwickler , wo wir vorhandene APIs und Programmierbibliotheken verwenden.
In dem Sinne, dass Schnittstellen ein Vertrag sind , hat noch niemand erwähnt, dass Schnittstellen eine großartige Möglichkeit sind, einige Teile Ihres Codes stabil zu machen . Das ist besonders nützlich , wenn es ein Team - Projekt (oder , wenn Sie Code entwickeln von anderen Entwicklern verwendet wird ). Hier ist ein konkretes Szenario für Sie:
Siehe auch diese verwandte Frage zum Codieren in eine Schnittstelle .
quelle
Es gibt so viele Zwecke für die Verwendung einer Schnittstelle.
Verwendung im polymorphen Verhalten. Wo Sie bestimmte Methoden einer untergeordneten Klasse mit einer Schnittstelle aufrufen möchten, die auf die untergeordnete Klasse verweist.
Einen Vertrag mit Klassen haben, um alle Methoden zu implementieren, wo dies erforderlich ist, wie es am häufigsten bei COM-Objekten der Fall ist, bei denen eine Wrapper-Klasse in einer DLL generiert wird, die die Schnittstelle erbt. Diese Methoden werden hinter den Kulissen aufgerufen, und Sie müssen sie nur implementieren, jedoch mit derselben Struktur wie in der COM-DLL definiert, die Sie nur über die Schnittstelle kennen, die sie verfügbar machen.
Reduzieren der Speichernutzung durch Laden bestimmter Methoden in eine Klasse. Wenn Sie beispielsweise drei Geschäftsobjekte haben und diese in einer einzelnen Klasse implementiert sind, können Sie drei Schnittstellen verwenden.
ZB IUser, IOrder, IOrderItem
Wenn Sie nur einen Benutzer hinzufügen möchten, gehen Sie folgendermaßen vor:
quelle