it-swarm.com.de

Was ist externe Verknüpfung und interne Verknüpfung?

Ich möchte die externe Verknüpfung und die interne Verknüpfung und ihren Unterschied verstehen. 

Ich möchte auch die Bedeutung von kennen

const-Variablen werden standardmäßig intern verknüpft, sofern nicht anders als extern deklariert.

297
rkb

Wenn Sie eine Implementierungsdatei schreiben (.cpp, .cxx usw.), generiert Ihr Compiler eine Übersetzungseinheit . Dies ist die Objektdatei aus Ihrer Implementierungsdatei sowie alle Header, die Sie #included darin enthalten. 

Interne Verknüpfung bezieht sich nur auf alles im Umfang einer Übersetzungseinheit .

Externe Verknüpfung bezieht sich auf Dinge, die über eine bestimmte Übersetzungseinheit hinaus existieren. Mit anderen Worten, durch das gesamte Programm zugänglich , das ist die Kombination aller Übersetzungseinheiten (oder Objektdateien).

239
dudewat

Wie dudewat sagteexternal - Verknüpfung bedeutet, dass das Symbol (Funktion oder globale Variable) im gesamten Programm verfügbar ist, und interne - Verknüpfung bedeutet, dass es nur in einer Übersetzungseinheit verfügbar ist. 

Sie können die Verknüpfung eines Symbols mithilfe der Schlüsselwörter extern und static explizit steuern. Wenn die Verknüpfung nicht angegeben ist, lautet die Standardverbindung extern für Symbole, die keine const-Symbole sind, und static (intern) für const-Symbole.

// in namespace or global scope
int i; // extern by default
const int ci; // static by default
extern const int eci; // explicitly extern
static int si; // explicitly static

// the same goes for functions (but there are no const functions)
int foo(); // extern by default
static int bar(); // explicitly static 

Beachten Sie, dass Sie anstelle von static für die interne Verknüpfung besser anonyme Namespaces verwenden, in die Sie auch classes einfügen können. Die Verknüpfung für anonyme Namespaces wurde zwischen C++ 98 und C++ 11 geändert. Die Hauptsache ist jedoch, dass sie von anderen Übersetzungseinheiten nicht erreichbar sind.

namespace {
   int i; // external linkage but unreachable from other translation units.
   class invisible_to_others { };
}
259
Motti
  • Eine globale Variable hat standardmäßig external linkage. Der Gültigkeitsbereich kann auf andere Dateien als die darin enthaltenen Dateien erweitert werden, indem in der anderen Datei eine entsprechende extern - Deklaration angegeben wird.
  • Der Gültigkeitsbereich einer globalen Variablen kann auf die Datei beschränkt werden, die ihre Deklaration enthält, indem der Deklaration das Schlüsselwort static vorangestellt wird. Solche Variablen sollen internal linkage haben.

Betrachten Sie folgendes Beispiel:

1.cpp

void f(int i);
extern const int max = 10;
int n = 0;
int main()
{
    int a;
    //...
    f(a);
    //...
    f(a);
    //...
}
  1. Die Signatur der Funktion f deklariert f als Funktion mit external linkage (Standard). Ihre Definition muss später in dieser Datei oder in einer anderen Übersetzungseinheit (unten angegeben) angegeben werden.
  2. max ist als Ganzzahlkonstante definiert. Die Standardverknüpfung für Konstanten lautet internal. Seine Verknüpfung wird mit dem Schlüsselwort extern nach extern geändert. Nun kann auf max in anderen Dateien zugegriffen werden. 
  3. n ist als ganzzahlige Variable definiert. Die Standardverknüpfung für außerhalb von Funktionskörpern definierte Variablen lautet external.

2.cpp

#include <iostream>
using namespace std;

extern const int max;
extern int n;
static float z = 0.0;

void f(int i)
{
    static int nCall = 0;
    int a;
    //...
    nCall++;
    n++;
    //...
    a = max * z;
    //...
    cout << "f() called " << nCall << " times." << endl;
}
  1. max wird als external linkage deklariert. Eine übereinstimmende Definition für max (mit externer Verknüpfung) muss in einer Datei enthalten sein. (Wie in 1.cpp)
  2. n wird als external linkage deklariert.
  3. z ist defined als globale Variable mit internal linkage.
  4. Die Definition von nCall gibt an, dass nCall eine Variable ist, die ihren Wert bei Aufrufen der Funktion f () beibehält. Im Gegensatz zu lokalen Variablen mit der standardmäßigen Auto-Storage-Klasse wird nCall nur einmal beim Start des Programms und nicht einmal für jeden Aufruf von f () initialisiert. Der Speicherklassenspezifizierer static beeinflusst die Lebensdauer der lokalen Variablen und nicht deren Gültigkeitsbereich.

NB: Das Schlüsselwort static spielt eine doppelte Rolle. Bei Verwendung in den Definitionen globaler Variablen gibt es internal linkage an. Bei Verwendung in den Definitionen der lokalen Variablen wird angegeben, dass die Lebensdauer der Variablen die Dauer des Programms und nicht die Dauer der Funktion ist.

Hoffentlich hilft das!

82
Rajendra Uppal

In Bezug auf 'C' (Weil das statische Schlüsselwort eine unterschiedliche Bedeutung zwischen 'C' und 'C++' hat)

Reden wir über verschiedene Bereiche in 'C'

UMFANG: Es ist grundsätzlich, wie lange ich etwas sehen kann und wie weit.

  1. Lokale Variable: Der Gültigkeitsbereich befindet sich nur innerhalb einer Funktion. Es befindet sich im STACK-Bereich von RAM . Dies bedeutet, dass jedes Mal, wenn eine Funktion alle Variablen aufgerufen wird das sind der Teil dieser Funktion, einschließlich der Funktionsargumente sind frisch erstellt und zerstört, sobald die Kontrolle aus der Funktion. (Da der Stack jedes Mal geleert wird, wenn die Funktion zurückkehrt)

  2. Statische Variable: Der Gültigkeitsbereich bezieht sich auf eine Datei. Es ist überall in der Datei zugänglich
    in dem es erklärt wird. Es befindet sich im DATA-Segment des RAM. Schon seit Darauf kann nur innerhalb einer Datei und somit auf eine INTERNE Verknüpfung zugegriffen werden. Irgendein
    Andere Dateien können diese Variable nicht sehen. In der Tat ist das Schlüsselwort STATIC das Nur so können wir ein gewisses Maß an Daten oder Funktionen einführen
    versteckt sich in 'C'

  3. Globale Variable: Der Geltungsbereich gilt für eine gesamte Anwendung. Es ist von jedem Ort aus zugänglich wo des Antrags. Globale Variablen befinden sich auch im DATA-Segment Da kann überall auf die Anwendung zugegriffen werden und somit EXTERNE Verknüpfung

Standardmäßig sind alle Funktionen global. Falls Sie einige Funktionen in einer Datei von außen verbergen müssen, können Sie das statische Schlüsselwort Der Funktion voranstellen. :-)

25
Libin Jose

Bevor Sie über die Frage sprechen, ist es besser, den Begriff translation unit , program und einige Grundbegriffe von C++ zu kennen ( Tatsächlich ist die Verknüpfung eine von ihnen im Allgemeinen). Sie müssen auch wissen, was ein scope ist.

Ich werde einige wichtige Punkte hervorheben, insbes. die in vorherigen Antworten fehlten.

Linkage ist eine Eigenschaft eines name, die durch eine Deklaration eingeführt wird. Verschiedene Namen können dieselbe entity (normalerweise ein Objekt oder eine Funktion) bezeichnen. Über linkage einer Entität zu sprechen, ist in der Regel Unsinn, es sei denn, Sie sind sicher, dass die Entität nur durch den eindeutigen Namen von bestimmten Deklarationen (normalerweise einer Deklaration) referenziert wird.

Beachten Sie, dass ein Objekt eine Entität ist, eine Variable jedoch nicht. Bei der Verknüpfung einer Variablen ist eigentlich der Name der bezeichneten Entität (die durch eine bestimmte Deklaration eingeführt wird) betroffen. Die Verknüpfung des Namens erfolgt in einer der drei Kategorien: Keine Verknüpfung, interne Verknüpfung oder externe Verknüpfung.

Unterschiedliche Übersetzungseinheiten können dieselbe Deklaration nach Header-/Quelldatei (ja, es ist der Wortlaut des Standards) enthalten. Sie können also in verschiedenen Übersetzungseinheiten auf denselben Namen verweisen. Wenn der angegebene Name über eine externe Verknüpfung verfügt, wird auch die Identität der Entität, auf die der Name verweist, gemeinsam genutzt. Wenn der deklarierte Name über eine interne Verknüpfung verfügt, bezeichnet derselbe Name in verschiedenen Übersetzungseinheiten verschiedene Entitäten. Sie können jedoch auf die Entität in verschiedenen Bereichen derselben Translationseinheit verweisen. Wenn der Name keine Verknüpfung hat, können Sie die Entität einfach nicht aus anderen Bereichen referenzieren.

(Hoppla ... Ich habe festgestellt, dass das, was ich geschrieben habe, nur die Wiederholung von dem Standardwortlaut ...) ist.

Es gibt auch einige andere verwirrende Punkte, die nicht in der Sprachspezifikation enthalten sind.

  1. Sichtbarkeit (eines Namens). Es ist auch eine Eigenschaft des deklarierten Namens, aber mit einer anderen Bedeutung als Verknüpfung .
  2. Sichtbarkeit (eines Nebeneffekts) . Das hat nichts mit diesem Thema zu tun.
  3. Sichtbarkeit (eines Symbols). Dieser Begriff kann von tatsächlichen Implementierungen verwendet sein. In solchen Implementierungen ist ein Symbol mit einer bestimmten Sichtbarkeit im Objektcode (binär) normalerweise das Ziel, das der Entitätsdefinition zugeordnet wird, deren Namen im Quellcode (C++) die gleiche spezifische Verknüpfung haben. Es ist jedoch in der Regel nicht eins zu eins garantiert. Beispielsweise kann ein Symbol in einem dynamischen Bibliotheksabbild nur innerhalb dieses Abbilds intern aus Quellcode (bei einigen Erweiterungen, normalerweise __attribute__ oder __declspec) oder Compileroptionen gemeinsam genutzt werden, und das Abbild ist nicht das gesamte Programm oder die Objektdatei übersetzt aus einer Übersetzungseinheit, daher kann kein Standardkonzept es genau beschreiben. Da das Symbol in C++ kein normativer Begriff ist, handelt es sich nur um ein Implementierungsdetail, auch wenn die zugehörigen Erweiterungen von Dialekten möglicherweise weit verbreitet sind.
  4. Zugänglichkeit. In C++ geht es normalerweise um Eigenschaft von Klassenmitgliedern oder Basisklassen , was wiederum ein anderes Konzept ist, das nicht mit dem Thema zusammenhängt.
  5. Global. In C++ bezieht sich "global" auf etwas von globalem Namespace oder globalem Namespace-Bereich. Letzteres entspricht in etwa dem file scope in der C-Sprache. Sowohl in C als auch in C++ hat die Verknüpfung nichts mit dem Gültigkeitsbereich zu tun, obwohl der Gültigkeitsbereich (wie Verknüpfung) auch stark mit einem Bezeichner (in C) oder einem Namen (in C++) beschäftigt ist, der durch eine Deklaration eingeführt wurde.

Die Verknüpfungsregel des Namespace-Bereichs const variable ist etwas Besonderes (und unterscheidet sich insbesondere von dem const-Objekt, das im Dateibereich in C-Sprache deklariert ist und auch das Konzept der Verknüpfung von Bezeichnern hat). Da ODR von C++ erzwungen wird, ist es ist wichtig, dass nicht mehr als eine Definition derselben Variablen oder Funktion im gesamten Programm verwendet wird, mit Ausnahme von inline-Funktionen . Wenn es keine solche Sonderregel für const gibt, wird eine einfachste Deklaration der Variable const mit Initialisierern (z. B. = xxx) in einem Header oder einer Quelldatei (häufig eine "Headerdatei") in mehreren Übersetzungseinheiten (oder in einer weiteren Übersetzungseinheit) enthalten mehr als einmal, wenn auch selten) in einem Programm verstößt gegen ODR, wodurch die Verwendung der Variable const als Ersatz für objektartige Makros unmöglich ist.

10
FrankHB

Ich denke, Interne und externe Verknüpfung in C++ gibt eine klare und knappe Erklärung: 

Eine Übersetzungseinheit bezieht sich auf eine Implementierungsdatei (.c/.cpp) und alle Header-Dateien (.h/.hpp) enthalten. Wenn ein Objekt oder eine Funktion in eine solche Übersetzungseinheit hat eine interne Verknüpfung, dann die spezifische Das Symbol ist nur für den Linker in dieser Übersetzungseinheit sichtbar. Ob Wenn ein Objekt oder eine Funktion eine externe Verknüpfung hat, kann der Linker sie auch sehen bei der Verarbeitung anderer Übersetzungseinheiten. Das statische Schlüsselwort, wenn es verwendet wird Erzwingt im globalen Namespace die interne Verknüpfung eines Symbols. Das Ein externes Schlüsselwort führt zu einem Symbol mit externer Verknüpfung.

Der Compiler setzt die Verknüpfung von Symbolen standardmäßig wie folgt: 

Nicht-konstante globale Variablen verfügen standardmäßig über eine externe Verknüpfung
Globale Const-Variablen verfügen standardmäßig über eine interne Verknüpfung
Funktionen haben standardmäßig eine externe Verknüpfung

5
Nan Xiao

Die Verknüpfung bestimmt, ob Bezeichner mit identischen Namen sich auf dasselbe Objekt, dieselbe Funktion oder eine andere Entität beziehen, selbst wenn diese Bezeichner in unterschiedlichen Übersetzungseinheiten erscheinen. Die Verknüpfung eines Bezeichners hängt davon ab, wie er deklariert wurde .. Es gibt drei Arten von Verknüpfungen:

  1. Interne Verknüpfung: Bezeichner können nur innerhalb einer Übersetzungseinheit gesehen werden.
  2. Externe Verknüpfung: Bezeichner können in anderen Übersetzungseinheiten gesehen (und referenziert) werden.
  3. Keine Verknüpfung: Bezeichner können nur in dem Bereich gesehen werden, in dem sie definiert sind .. _. Die Verknüpfung wirkt sich nicht auf den Bereich aus

Nur C++: Sie können auch eine Verknüpfung zwischen C++ - und Nicht-C++ - Codefragmenten haben, die als language linkage bezeichnet wird.

Quelle: IBM-Programmverknüpfung

4
arun pal

Grundsätzlich gilt

  • Die extern linkage-Variable ist in allen Dateien sichtbar
  • Die internal linkage-Variable ist in einer einzelnen Datei sichtbar.

Explain: const-Variablen werden standardmäßig intern verknüpft, sofern nicht anders als extern deklariert.

  1. die globale Variable ist standardmäßig external linkage.
  2. const globale Variable ist internal linkage
  3. zusätzlich ist extern const globale Variable external linkage

Ein ziemlich gutes Material über die Verknüpfung in C++

http://www.goldsborough.me/c/c++/linker/2016/03/30/19-34-25-internal_and_external_linkage_in_c++/

3
Color

In C++  

Jede Variable im Dateibereich, die nicht in einer Klasse oder Funktion verschachtelt ist, ist in allen Übersetzungseinheiten eines Programms sichtbar. Dies wird als external linkage bezeichnet, da der Name zum Linker für den Linker überall außerhalb der Übersetzungseinheit sichtbar ist. 

Globale Variablen und gewöhnliche Funktionen haben eine externe Verknüpfung.

Statisch Der Objekt- oder Funktionsname im Dateibereich ist lokal für die Übersetzungseinheit. Das ist Als Internal Linkage bezeichnet.

Verknüpfung bezieht sich nur auf Elemente, die zum Zeitpunkt des Verbindens/Ladens Adressen haben. Klassendeklarationen und lokale Variablen haben daher keine Verknüpfung.

0
Saurabh Raoot