Über vorläufige Definition

Lesezeit: 4 Minuten

Benutzeravatar von Sadique
Sadique

Ich habe aus einem Buch über vorläufige Definitionen gelesen, dass

Eine vorläufige Definition ist jede externe Datendeklaration, die keinen Speicherklassenbezeichner und keinen Initialisierer hat. Eine vorläufige Definition wird zu einer vollständigen Definition, wenn das Ende der Übersetzungseinheit erreicht ist und keine Definition mit einem Initialisierer für die Kennung erschienen ist

Bitte erläutern Sie, was die obige Aussage bedeutet. Auch der Unterschied zwischen Deklaration und Definition? Ich bin deswegen durcheinander gekommen. 🙁 Und warum gibt dieses Programm keinen Fehler aus:

#include <stdio.h>

int a;      //Tentative definition
int a;      //similarly this declaration too.
int main()  //not getting any error with this code why its so?
{
    printf("hi");
} 

Außerdem, was ist falsch an diesem Code:

#include<stdio.h>
printf("Hi");
int main(void){
    return 0;
}

  • In welchem ​​Buch haben Sie über vorläufige Definitionen gelesen?

    – Destruktor

    27. Oktober 2015 um 12:55 Uhr

  • Siehe auch Was ist der Grund für vorläufige Definitionen in C?

    – Shafik Yaghmour

    13. August 2018 um 15:57 Uhr

Benutzeravatar von Tyler McHenry
Tyler McHenry

Eine Variable Erklärung sagt, “es gibt eine Variable mit folgendem Namen und Typ im Programm”.

Eine Variable Definition sagt: “Sehr geehrter Herr Compiler, bitte weisen Sie jetzt Speicher für eine Variable mit dem folgenden Namen und Typ zu.”

Es kann also mehrere Deklarationen für dieselbe Variable geben, aber es sollte nur eine Definition geben.

In C wird reinen Deklarationen (die nicht gleichzeitig Definitionen sind) das Schlüsselwort vorangestellt extern. Da Sie dieses Schlüsselwort also in Ihrem ersten Beispiel nicht haben, haben Sie zwei Definitionen. Auf den ersten Blick scheint dies ein Problem zu sein (und ist tatsächlich ein Fehler in C++), aber C hat eine spezielle “vorläufige Definitions”-Regel, die mehrere Definitionen für dieselbe Variable in derselben Übersetzungseinheit zulässt, solange sie alle passen und höchstens man hat einen Initialisierer. Der C-Compiler kombiniert hinter den Kulissen alle vorläufigen Definitionen zu einer einzigen Definition.

Hätten Sie versucht, beide Definitionen wie folgt zu initialisieren:

int a = 1;
int a = 2;

Dann hättest du einen Fehler gehabt.

Ihre zweite Frage ist einfacher. In C können Sie einfach keine ausführbaren Anweisungen außerhalb des Hauptteils einer Funktion haben. Es ist einfach nicht erlaubt. Denken Sie darüber nach: Wann würden Sie damit rechnen, dass es läuft, wenn es erlaubt wäre?

  • @TylerMcHenry: Es ist sowohl in C als auch in C++ illegal, aber C-Compiler implementieren dies als gemeinsame Erweiterung. Siehe diese Antwort.

    – legends2k

    3. März 2014 um 12:23 Uhr

  • @legends2k Nein, das ist in C nicht illegal … in der Frage, auf die Sie verlinken (und auch in der Frage, auf die die Antwort, auf die Sie verlinken, verweist), sind mehrere Dateien enthalten. Mehrere (kompatible) vorläufige Definitionen in derselben Datei stellen keinen Verstoß dar. Der Verstoß in dieser Frage kommt daher, weil am Ende der Übersetzungseinheit, wenn vorläufige Definitionen ohne vollständige Definition vorhanden sind, eine vollständige Definition impliziert wird. Das plus mehrere Dateien führt zu mehreren Definitionen zum Zeitpunkt des Verknüpfens (mit Ausnahme der üblichen Erweiterung der vorläufigen Definitionsregeln, um mehrere Dateien zu umfassen).

    – Theodor Murdock

    18. Mai 2015 um 21:59 Uhr

  • Warum ist es nur mit globalen Variablen zulässig, nicht mit lokalen Variablen? Bei lokalen Variablen gibt es einen Neudeklarationsfehler?

    – Rishab Shinhal

    24. Dezember 2017 um 14:13 Uhr

  • @RishabShinghal: Der einzige Grund, warum C es zulässt, ist, dass es mit Code kompatibel ist, der geschrieben wurde, bevor das Schlüsselwort “extern” hinzugefügt wurde. Und extern gilt nicht für lokale Variablen, bei denen Duplikate nie erlaubt waren.

    – Zan Luchs

    15. Januar 2018 um 19:02 Uhr


  • “C hat eine spezielle Regel für “vorläufige Definitionen”, die mehrere Definitionen für dieselbe Variable in derselben Übersetzungseinheit zulässt, solange sie alle übereinstimmen und höchstens eine einen Initialisierer hat.” Wenn Sie in C eine Variable im Dateibereich deklarieren und weder eine Verknüpfung noch einen Initialisierer angeben, ist dies normalerweise eine Deklaration und keine Definition. Nur wenn keine Definition in der Übersetzungseinheit existiert, wird eine Art implizite Definition erstellt. Auch das stimmt nicht wirklich, da der Linker alle Übersetzungseinheiten nach einer echten Definition durchsucht und alle findet, die er findet (gemeinsames Symbol).

    – jschultz410

    6. März 2021 um 22:10 Uhr

Die erste funktioniert, weil Ihre beiden Definitionen von a sind vorläufig, die beliebig oft dupliziert werden können. Am Ende der Übersetzungseinheit wurde keine nicht vorläufige Definition gesehen, also wird das, was Sie für Attribute angegeben haben, mit Standardwerten kombiniert, um eine endgültige Definition von zu geben aalso hat es eine externe Verknüpfung, eine statische Speicherdauer und wird auf 0 initialisiert.

Das Problem mit dem zweiten hat nichts mit vorläufigen Definitionen zu tun. Dein printf("Hi"); muss sich innerhalb einer Funktion befinden, um zu funktionieren – es ist keine Deklaration oder Definition (vorläufig oder anderweitig); dort ist es einfach nicht erlaubt.

1397590cookie-checkÜber vorläufige Definition

This website is using cookies to improve the user-friendliness. You agree by using the website further.

Privacy policy