Was ist frühe und späte Bindung?
On November 18, 2020 by adminIch höre immer wieder von früher und später Bindung, aber ich verstehe nicht, was sie sind. Ich habe die folgende Erklärung gefunden, die ich nicht verstehe:
Frühe Bindung bezieht sich auf die Zuweisung von Werten zu Variablen während der Entwurfszeit, während sich späte Bindung auf die Zuweisung von Werten bezieht zu Variablen zur Laufzeit.
Könnte jemand bitte die beiden Bindungsarten definieren und vergleichen?
Kommentare
- Kompilierungszeit vs. Laufzeit.
- Hier ist eine gute Lektüre zu diesem Thema: en.wikibooks.org/ wiki / Introduction_to_Programming_Languages / …
Antwort
Bei Verwirrung gibt es zwei Hauptkonzepte: Binden und Laden. Es wird durch das Konzept der Datenbindung zusammengeführt, die irgendwo in der Mitte oft beides tut. Nachdem ich darüber nachgedacht habe, werde ich ein weiteres Konzept hinzufügen, um die Trifecta, den Versand, zu vervollständigen.
Typen
Late Binding : Typ ist unbekannt , bis die Variable zur Laufzeit ausgeübt wird; normalerweise durch Zuweisung, aber es gibt andere Mittel, um einen Typ zu erzwingen; Dynamisch typisierte Sprachen nennen dies eine zugrunde liegende Funktion, aber viele statisch typisierte Sprachen verfügen über eine Methode zum Erreichen einer späten Bindung.
Wird häufig mithilfe von [speziellen] dynamischen Typen, Introspektion / Reflexion, Flags und Compileroptionen oder über virtuelle Methoden implementiert durch Ausleihen und Erweitern des dynamischen Versands
Frühe Bindung : Typ ist bekannt bevor die Variable zur Laufzeit ausgeübt wird, normalerweise durch statische, deklarative Mittel
Wird häufig unter Verwendung von primitiven Standardtypen implementiert.
Funktionen
Statischer Versand : bekannte, spezifische Funktion oder Unterprogramm zur Kompilierungszeit; Es ist eindeutig und wird von der Signatur
abgeglichen, die als statische Funktionen implementiert ist. Keine Methode kann dieselbe Signatur haben.
Dynamischer Versand : keine bestimmte Funktion oder Unterprogramm zur Kompilierungszeit; bestimmt durch den Kontext während der Ausführung. Es gibt zwei verschiedene Ansätze für den „dynamischen Versand“, die sich dadurch unterscheiden, welche Kontextinformationen zur Auswahl der geeigneten Funktionsimplementierung verwendet werden.
In single [ dynamic ] dispatch wird nur der Typ der Instanz verwendet, um die entsprechende Funktionsimplementierung zu bestimmen. In statisch typisierten Sprachen bedeutet dies in der Praxis, dass der Instanztyp unabhängig vom Referenztyp, der bei der Deklaration / Zuweisung der Variablen angegeben wird, entscheidet, welche Methodenimplementierung verwendet wird. Da nur ein einziger Typ – der Typ der Objektinstanz – verwendet wird, um auf die entsprechende Implementierung zu schließen, wird dieser Ansatz als „Einzelversand“ bezeichnet.
Es gibt auch mehrere [ dynamic ] versenden , wobei Eingabeparametertypen auch dazu beitragen, die aufzurufende Funktionsimplementierung zu bestimmen. Weil mehrere Typen – sowohl der Typ der Instanz als auch – die Typen der Parameter beeinflussen Welche Methodenimplementierung ausgewählt ist, wird als „Mehrfachversand“ bezeichnet.
Implementiert als virtuelle oder abstrakte Funktionen; Andere Hinweise sind überschriebene, versteckte oder schattierte Methoden.
NB: Ob das Überladen von Methoden einen dynamischen Versand beinhaltet oder nicht, ist sprachspezifisch. In Java werden beispielsweise überladene Methoden statisch versendet.
Werte
Lazy Loading : Objektinitialisierungsstrategie, die die Wertzuweisung verzögert, bis sie benötigt wird ; ermöglicht, dass sich ein Objekt in einem im Wesentlichen gültigen, aber wissentlich unvollständigen Zustand befindet und wartet, bis die Daten benötigt werden, bevor es geladen wird; Wird häufig als besonders nützlich zum Laden großer Datenmengen oder zum Warten auf externe Ressourcen angesehen.
Wird häufig implementiert, indem eine Sammlung oder Liste während des Konstruktor- oder Initialisierungsaufrufs absichtlich nicht in ein zusammengesetztes Objekt geladen wird, bis ein nachgeschalteter Aufrufer nach dem Inhalt von fragt diese Sammlung (z. B. get_value_at, get_all_as usw.).Zu den Variationen gehört das Laden von Metainformationen über die Sammlung (wie Größe oder Schlüssel), aber das Weglassen der tatsächlichen Daten. bietet auch einen Mechanismus für einige Laufzeiten, um Entwicklern ein ziemlich sicheres und effizientes Singleton-Implementierungsschema bereitzustellen
Eifriges Laden : Objektinitialisierungsstrategie, die sofort alle Wertzuweisungen ausführt, damit alle Daten vollständig sind, bevor sie sich als in einem gültigen Zustand befindlich betrachten.
Wird häufig von implementiert Bereitstellen eines zusammengesetzten Objekts mit all seinen bekannten Daten so schnell wie möglich, beispielsweise während eines Konstruktoraufrufs oder einer Initialisierung
Datenbindung : Oft wird eine aktive Verknüpfung oder Zuordnung zwischen zwei kompatiblen Informationsströmen erstellt, damit Änderungen an einem wieder in den anderen übernommen werden und umgekehrt. Um kompatibel zu sein, müssen sie häufig einen gemeinsamen Basistyp oder eine gemeinsame Schnittstelle haben.
Wird häufig implementiert, um eine sauberere, konsistente Synchronisation zwischen verschiedenen Anwendungsaspekten zu gewährleisten (z. B. Ansichtsmodell zu Ansicht, Modell zu Steuerung) usw.) und spricht über Konzepte wie Quelle und Ziel, Endpunkte, Binden / Aufheben der Bindung, Aktualisieren und Ereignisse wie on_bind, on_property_change, on_explicit, on_out_of_scope
BEARBEITEN von Beispielen, wie diese häufig auftreten. Bestimmte Codebeispiele hängen vollständig von der Implementierung / Laufzeit / Plattform ab.
Kommentare
- Diese Antwort scheint für objektorientierte Sprachen zu spezifisch zu sein.
- @Jack Ich ‚ fühle mich nicht so, ich denke, dies ist ein ausgezeichnetes Produkt, das viele Aspekte abdeckt.
Antwort
Alles, was der Compiler beim Kompilieren entscheidet, kann auf EARLY / COMPILE TIME Bindung und alles, was unter RUNTIME zu entscheiden ist, heißt LATE / RUNTIME Bindung.
Zum Beispiel
Methode Überladen von und Methode Überschreiben von .
1 ) In Methodenüberladung ruft Ihre Methode die Methoden ar auf Der Compiler entscheidet in dem Sinne, dass die Funktion, die aufgerufen werden soll, zur Kompilierungszeit von Ihrem Compiler festgelegt wird. Daher ist EARLY BINDING .
2) Beim Überschreiben von Methoden wird bei RUNTIME entschieden, welche Methode verwendet wird wird gerufen werden. Daher wird es als LATE BINDING bezeichnet.
Es wurde versucht, es einfach und leicht zu bekommen. Hoffe, das hilft.
Antwort
Späte Bindung ist, wenn das Verhalten zur Laufzeit ausgewertet wird. Es ist notwendig, wenn Sie tatsächlich anhand von Informationen bestimmen möchten, wie Sie handeln sollen, wenn das Programm ausgeführt wird. Meiner Meinung nach ist das klarste Beispiel der virtuelle Funktionsmechanismus, insbesondere in C ++.
class A { public: void f() {} virtual void g() {} }; class B : public A { void f() {} virtual void g() {} }; int main() { A* a = new B; a->f(); a->g(); }
In diesem Beispiel ruft a->f()
tatsächlich void A::f()
auf, da es früh (oder statisch) ist ) gebunden, und so denkt das Programm zur Laufzeit , es sei nur ein Zeiger auf eine Variable vom Typ A
, während a->g()
ruft tatsächlich void B::g()
auf, da der Compiler, der g()
sieht, virtuell Code einfügt, um die Adresse der richtigen Funktion nachzuschlagen zur Laufzeit aufrufen.
Kommentare
- “ Die Laufzeit „? Sie ‚ sprechen von C ++. C ++ wird direkt in Maschinencode kompiliert. ‚ benötigt keine Laufzeit zum Auflösen virtuelle Methoden.
- @tdammers C ++ benötigt tatsächlich eine Laufzeitbibliothek, jedoch nicht für virtuelle Aufrufe. Wenn Sie sorgfältig lesen, werden Sie ‚ feststellen, dass diese Antwort besagt, dass der Compiler “ Code einfügt, um die Adresse der richtigen Funktion nachzuschlagen [ …] zur Laufzeit „.
- Nun, aber dieser “ Code Das Nachschlagen der Adresse der richtigen Funktion “ ist im Grunde nur eine typunabhängige zweistufige Zeiger-Dereferenzierung, gefolgt von einem Funktionsaufruf. Es ist kein “ Denken “ beteiligt. Der einzige Grund, warum es zuverlässig funktioniert, ist, dass der Compiler die Typprüfung zur Kompilierungszeit durchführt. Zur Laufzeit vertraut der generierte Code darauf, dass der Compiler die Hausaufgaben zur Typprüfung ausgeführt hat. Wenn Sie unsichere Abgüsse verwenden (z.C-artige Zeigerumwandlungen), Sie können C ++ – Objekte legal als Objekt der falschen Klasse behandeln, aber ihre vtables werden völlig durcheinander gebracht und der Code bricht nur.
- @tdammers Ich habe versucht, mich von dieser Art von Antwort fernzuhalten, da es sich bei ‚ um ein Implementierungsdetail von Compilern handelt, das für einen esoterischen Compiler möglicherweise zutrifft oder nicht. Was zählt, ist das Konzept.
- @tdammers Und mit “ der Laufzeit “ meine ich “ das Programm zur Laufzeit „. Offensichtlich wird C ++ nicht ‚ verwaltet. Aber da Sie mir gezeigt haben, dass es Verwirrung stiften kann, ändere ich ‚ den vollständigen Wortlaut.
Antwort
Wenn Sie mit Funktionszeigern vertraut sind, ist dies ein Beispiel. Die definierten Funktionen können als frühe Bindung bezeichnet werden. Wenn Sie dagegen Funktionszeiger verwenden, erfolgt die späte Bindung.
int add(int x,int y) { return x+y; } int sub(int x,int y) { return x-y; } int main() { //get user choice int(*fp)(int,int); //if add fp=add; //else if sub fp=sub; cout<<fp(2,2); }
Hier sind Funktionen add und sub Funktionen (seine Adresse wird beim Kompilierungszeit-Linker gebunden)
, aber der Funktionszeiger ist zu spät Das Binden des fp kann je nach Benutzerauswahl [zur Laufzeit] entweder add oder sub aufrufen.
Antwort
Nur frühes und spätes Binden Sinn machen im Kontext von Typen und nicht so, wie Sie es beschreiben. Nahezu alle modernen Sprachen sind in dem Sinne typisiert, dass alle Werte feste Typen haben. Der Unterschied ergibt sich, wenn wir dynamisch und statisch typisierte Sprachen betrachten. In dynamisch typisierten Sprachen haben Variablen keine Typen, sodass sie auf Werte eines beliebigen Typs verweisen können. Wenn Sie also eine Methode für ein Objekt aufrufen, auf das von einer Variablen verwiesen wird, können Sie nur feststellen, ob dieser Aufruf gültig ist oder nicht Suchen Sie in der Klasse nach dem Objekt und prüfen Sie, ob diese Methode tatsächlich vorhanden ist. Dies ermöglicht einige coole Dinge wie das Hinzufügen neuer Methoden zu Klassen zur Laufzeit, da die eigentliche Methodensuche bis zum allerletzten Moment verschoben wird. Die meisten Leute nennen diesen Status von Angelegenheiten späte Bindung.
In einer statisch typisierten Sprache haben Variablen Typen und können nach ihrer Deklaration nicht auf einen Wert verweisen, der nicht vom gleichen Typ ist. Dies ist nicht unbedingt wahr, aber wir nehmen es vorerst an. Wenn Sie nun wissen, dass die Variable immer nur auf Werte eines bestimmten Typs verweist, gibt es keinen Grund herauszufinden, ob ein Methodenaufruf zur Laufzeit gültig ist oder nicht, da Sie die Gültigkeit bestimmen können, bevor der Code jemals ausgeführt wird. Dies wird als frühe Bindung bezeichnet.
Ein Beispiel zum Nachweis der späten Bindung in Ruby:
a = 1 # a is an integer at this point a.succ # asking for its successor is valid class A def method_a # some code end end a = A.new a.method_a # this is also valid a.succ # this is not valid class A # we can re-open the class and add a method def succ # some more code end end a.succ # now this is valid
Die obige Abfolge von Aktionen ist dies nicht möglich in einer Sprache wie Java, in der alle Typen zur Laufzeit festgelegt sind.
Antwort
Anstatt Ihnen eine akademische Definition zu geben I. Ich werde versuchen, Ihnen einige der Unterschiede anhand eines Beispiels aus der Praxis mit VBA zu zeigen:
Frühe Bindung:
Dim x As FileSystemObject Set x = New FileSystemObject Debug.Print x.GetSpecialFolder(0)
Hierfür muss zur Entwurfszeit ein Verweis auf die Komponente „Microsoft Scripting Runtime“ festgelegt werden. Es hat den Vorteil, dass Sie bereits zur Kompilierungszeit eine Fehlermeldung erhalten, wenn Sie einen Tippfehler in FileSystemObject
oder Methodennamen wie GetSpecialFolder
haben.
Späte Bindung
Dim x As Object Set x = CreateObject("Scripting.FileSystemObject") Debug.Print x.GetSpecialFolder(0)
Hierfür muss keine Referenz festgelegt werden, die Instanz erstellt und der Typ Die Bestimmung erfolgt nur zur Laufzeit. Der Compiler wird sich zur Kompilierungszeit nicht beschweren, wenn Sie versuchen, eine nicht vorhandene Methode von x
aufzurufen. Dies führt nur dann zu einem Laufzeitfehler, wenn die bestimmte Zeile ausgeführt wird
Der Nachteil der späten Bindung besteht also darin, dass Sie hier keine starke Typprüfung haben. Dies ist aber auch der Vorteil: Nehmen wir an, Sie haben eine Komponente, in der mehrere Versionen vorhanden sind, und jede neuere Version bietet einige zusätzliche Funktionen. (Ein Beispiel aus der Praxis sind die MS Office-Komponenten wie die Excel COM-Oberfläche.) Eine späte Bindung ermöglicht dies Sie schreiben Code, der mit all diesen Versionen zusammenarbeitet. Sie können zunächst die spezifische Komponentenversion ermitteln. Wenn Sie feststellen, dass nur eine ältere Version verfügbar ist, vermeiden Sie es, Funktionsaufrufe auszuführen, die mit dieser Version nicht funktionieren.
Antwort
Das vielleicht häufigste Beispiel für eine späte Bindung ist das Auflösen von Internet-URLs. Es unterstützt dynamische Systeme und große Systeme, ohne zu versuchen, jeden Standort auf der Welt zu verknüpfen und zu binden, bevor Sie einen erreichen können. Andererseits verursacht es zur Laufzeit einen gewissen Overhead (DNS-Suche, viel weniger IP-Routing).
In diesem Sinne sind die meisten Bindungsarten in Sprachumgebungen mehr oder weniger früh, zum Zeitpunkt der Kompilierung oder der Verknüpfung.
Jede Art hat Kosten und Nutzen.
Kommentare
- Können Sie eine Referenz für diese Definition der Bindung bereitstellen?Ich habe noch nie davon gehört, Internetadressen als “ Bindung “ aufzulösen, obwohl ich denke, dass jemand argumentiert hat, da das Binden das Auflösen von Namen ist dass das Konzept der frühen / späten Bindung auf die Auflösung von URI in Internetadressen angewendet werden kann. Dies ist jedoch keine übliche Interpretation, und das Konzept der frühen / späten Bindung geht auf die Zeit zurück, in der Computer üblicherweise mit dem Internet verbunden waren.
Schreibe einen Kommentar