Multiple definitions

Schnelle objektorientierte, kompilierende Programmiersprache.
Benutzeravatar
naums
Beiträge: 740
Registriert: Sa Jan 02, 2010 10:40 pm
Kontaktdaten:

Multiple definitions

Beitrag von naums » So Jan 10, 2010 7:16 pm

Ein Fehler passiert in folgender Headerfile:

Code: Alles auswählen

#include <stdlib.h>
#include <stdio.h>
#include <iostream>
using namespace std;

void gotoxy(int x, int y)
{
    printf("\033[%d;%dG", y, x);
}

void home()
{
    int x[2] = {0,0};
    printf("\033[%d;%dG",x[1],x[2]);
}

void writehead(string header, string filepath)
{
    FILE *ini;
    ini=fopen(filepath.c_str(),"t");
    fprintf(ini,header.c_str());
    fclose(ini);
}
Fehler:
"Multiple Definition of gotoxy(int, int)"
"First declared here" --> zeigt auf Zeile 7

"Multiple Definition of home()"
"First declared here" --> zeigt auf Zeile 12

"Multiple Definition of writehead(std::basic_string<char, std::char_traits<char>, std::allocator<..."
"First declared here" --> zeigt auf Zeile 18

(... zeigt an dass es dann noch weiter geht, mehr Parameter als meine writehead function)
.globl truth
truth:
mov r0, #42
mov pc, lr

Benutzeravatar
Jside
Beiträge: 377
Registriert: Di Nov 11, 2008 12:56 am

Re: Multiple definitions

Beitrag von Jside » So Jan 10, 2010 7:27 pm

include guards ins Headerfile:

Code: Alles auswählen

#ifndef NAME_DES_HEADERS_H
#define NAME_DES_HEADERS_H

/* hier code */

#endif
Oder dem gcc den Parameter:
-Xlinker -zmuldefs
anhängen.

Ersteres bevorzugt.

Es ist übrigends keine gute idee in ein Headerfile ein "using namsepace XYZ;" zu schreiben ;)

AnGaiNoR
Beiträge: 212
Registriert: Sa Jul 19, 2008 7:07 pm
Wohnort: Dresden

Re: Multiple definitions

Beitrag von AnGaiNoR » So Jan 10, 2010 7:28 pm

Sowas liegt eigentlich immer daran, dass der Header irgendwo zweimal eingebunden wird. Das geschieht meistens unabsichtlich, aber das kann man umgehen.

Code: Alles auswählen

#ifndef _NAME_DES_HEADERS_HPP_
#define _NAME_DES_HEADERS_HPP_

// hier kommt der eigentlich Header hin

#endif
Beim Kompilieren wird getestet, ob der Header schon eingebunden wurde, also ob schon die Präprozessor-Konstante für den Header gesetzt wurde. Wenn das nicht der Fall ist, dann wird der Header eingebunden und die Konstante gesetzt; ansonsten wird der Header ignoriert.
Das gleiche Schema findest du auch in so ziemlich jedem Header von Programm-Bibliotheken, Standard-Bibliotheken, usw.
Physics is like sex: sure, it may give some practical result, but that's not why we do it.
(Richard P. Feynman)

Benutzeravatar
naums
Beiträge: 740
Registriert: Sa Jan 02, 2010 10:40 pm
Kontaktdaten:

Re: Multiple definitions

Beitrag von naums » So Jan 10, 2010 7:31 pm

Warum sollte ich das mit dem Define tun? Und das Problem bleibt bestehen... trotzdem. Ohne std, und mit dem define.
.globl truth
truth:
mov r0, #42
mov pc, lr

AnGaiNoR
Beiträge: 212
Registriert: Sa Jul 19, 2008 7:07 pm
Wohnort: Dresden

Re: Multiple definitions

Beitrag von AnGaiNoR » So Jan 10, 2010 7:33 pm

naums hat geschrieben:Warum sollte ich das mit dem Define tun?
Weil es jeder so macht ;)
naums hat geschrieben:Und das Problem bleibt bestehen...
Dann hast du was falsch gemacht.
Physics is like sex: sure, it may give some practical result, but that's not why we do it.
(Richard P. Feynman)

Benutzeravatar
cloidnerux
Moderator
Beiträge: 3125
Registriert: Fr Sep 26, 2008 4:37 pm
Wohnort: Ram (Gibts wirklich)

Re: Multiple definitions

Beitrag von cloidnerux » So Jan 10, 2010 7:39 pm

Und das Problem bleibt bestehen... trotzdem. Ohne std, und mit dem define.
Du musst bei dem #ifndef und #define das gleiche stehen haben, ansonsten nutzt dir das überhaupt nichts.
Außerdem ist es schlechter Stil, in Headerdateien die Funktionen zu Deklarieren.
Und in wie fern bleibt dien problem bestehen? Keine änderungen an den Ausgaben des Compilers?
Redundanz macht wiederholen unnötig.
quod erat expectandum

Benutzeravatar
naums
Beiträge: 740
Registriert: Sa Jan 02, 2010 10:40 pm
Kontaktdaten:

Re: Multiple definitions

Beitrag von naums » So Jan 10, 2010 7:40 pm

Code: Alles auswählen

#ifndef Linux_Console
#define Linux_Console
#include <stdlib.h>
#include <stdio.h>
#include <iostream>


void gotoxy(int x, int y)
{
    printf("\033[%d;%dG", y, x);
}

void home()
{
    int x[2] = {0,0};
    printf("\033[%d;%dG",x[1],x[2]);
}

void writehead(string header, string filepath)
{
    FILE *ini;
    ini=fopen(filepath.c_str(),"t");
    fprintf(ini,header.c_str());
    fclose(ini);
}
#endif
genau, die gleichen Ausgaben des Compilers. Aber warum ist das schlechter stil?
.globl truth
truth:
mov r0, #42
mov pc, lr

AnGaiNoR
Beiträge: 212
Registriert: Sa Jul 19, 2008 7:07 pm
Wohnort: Dresden

Re: Multiple definitions

Beitrag von AnGaiNoR » So Jan 10, 2010 7:49 pm

Im Header (englisch für Kopfball, aber hier gehts jetzt mal nur um Kopf, Endung h/hpp/hxx) geht es darum Funktionsköpfe zu vereinbaren.
Die Funktionsrümpfe werden in den Quellcode-Dateien geschrieben (Endung c/cpp/cxx).

Bindet nun eine Datei den Header ein, dann ist die Existenz der darin deklarierten Funktionen bekannt; der Funktionsrumpf ist in dem Moment erstmal egal. Beim Zusammenfügen der einzelnen Teilquellen sorgt der Linker dann dafür, dass der eingebundene Funktionskopf dann auch auf den richtigen Rumpf verweist. Das klappt natürlich nicht, wenn der Rumpf mehrere Male da ist ("multiple definition"), oder auch wenn er gar nicht da ist ("undefined reference").
Physics is like sex: sure, it may give some practical result, but that's not why we do it.
(Richard P. Feynman)

Benutzeravatar
cloidnerux
Moderator
Beiträge: 3125
Registriert: Fr Sep 26, 2008 4:37 pm
Wohnort: Ram (Gibts wirklich)

Re: Multiple definitions

Beitrag von cloidnerux » So Jan 10, 2010 7:54 pm

genau, die gleichen Ausgaben des Compilers.
Kann es sein, das du die Funktionen auch für Windows geschrieben hast, mit den selben Namen, und diese Datei dann auch mit einbindest?
Redundanz macht wiederholen unnötig.
quod erat expectandum

Benutzeravatar
naums
Beiträge: 740
Registriert: Sa Jan 02, 2010 10:40 pm
Kontaktdaten:

Re: Multiple definitions

Beitrag von naums » So Jan 10, 2010 7:57 pm

schuldigung, die Datei heißt Console.cpp. Sorry, ich dachte auch das wäre eine Headerfile, ist aber eben nur der Quellcode... eben eine cpp.
.globl truth
truth:
mov r0, #42
mov pc, lr

Antworten