Du bist nicht angemeldet.

Stilllegung des Forums
Das Forum wurde am 05.06.2023 nach über 20 Jahren stillgelegt (weitere Informationen und ein kleiner Rückblick).
Registrierungen, Anmeldungen und Postings sind nicht mehr möglich. Öffentliche Inhalte sind weiterhin zugänglich.
Das Team von spieleprogrammierer.de bedankt sich bei der Community für die vielen schönen Jahre.
Wenn du eine deutschsprachige Spieleentwickler-Community suchst, schau doch mal im Discord und auf ZFX vorbei!

Werbeanzeige

1

16.03.2012, 00:22

Forward Declaration mit Namespace

Ich habe mal wieder ein Problem (das wird noch öfter kommen :D ),
ich möchte in Klasse a auf Klasse b zugreifen und in b auf a. Die Klassen sehe ca. so aus:

C-/C++-Quelltext

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
// a.h
#include "b.h"

namespace Test
{
    class a
    {
    public:
        void foo();
        void bar();
    private:
        b* m_bPointer;
    };
}

// a.cpp
#include "a.h"

namespace Test
{
    void a::foo()
    {
        m_bPointer->MachWas();
    }
    void a::bar()
    {
             //Code
    }
}

// b.h
#include "a.h"

namespace Test
{
    class b
    {
    public: 
        void MachWas();
    private:
        a m_a;
    };
}
// b.cpp
#include "b.h"

namespace Test
{
    void b::MachWas()
    {
        m_a.bar();
    }
}


Ich weis nicht so recht wie ich das ganze auflösen muss damit der Compiler zufrieden ist, hat jemand eine Idee?
greate minds discuss ideas;
average minds discuss events;
small minds discuss people.

drakon

Supermoderator

Beiträge: 6 513

Wohnort: Schweiz

Beruf: Entrepreneur

  • Private Nachricht senden

2

16.03.2012, 00:30

Das geht so nicht. Schau mal hier:
Definitionen und Deklarationen in C++
Das erklärt das Problem und zeigt auf was du machen kannst.

3

16.03.2012, 00:43

Das kann ich irgendwie nicht auf mein Problem anwenden da sowohl a als auch b eine Funktion des anderen Typs aufrufen. Oder kann man Funktionen auch "forward deklaraieren"?
greate minds discuss ideas;
average minds discuss events;
small minds discuss people.

dot

Supermoderator

Beiträge: 9 757

Wohnort: Graz

  • Private Nachricht senden

4

16.03.2012, 01:16

C-/C++-Quelltext

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
// a.h

namespace Test
{
  class b;

  class a
  {
  public:
    void foo();
    void bar();
  private:
    b* m_bPointer;
  };
}

// a.cpp
#include "a.h"
#include "b.h"

namespace Test
{
  void a::foo()
  {
    m_bPointer->MachWas();
  }
  void a::bar()
  {
    //Code
  }
}


// b.h
#include "a.h"

namespace Test
{
  class b
  {
  public: 
    void MachWas();
  private:
    a m_a;
  };
}

// b.cpp
#include "b.h"

namespace Test
{
  void b::MachWas()
  {
    m_a.bar();
  }
}

;)

drakon

Supermoderator

Beiträge: 6 513

Wohnort: Schweiz

Beruf: Entrepreneur

  • Private Nachricht senden

5

16.03.2012, 01:21

Das kann ich irgendwie nicht auf mein Problem anwenden da sowohl a als auch b eine Funktion des anderen Typs aufrufen. Oder kann man Funktionen auch "forward deklaraieren"?

Das ist genau das gleiche Problem, wie dort gezeigt wird.
Wie du das bei deinem Beispiel machen musst siehst du ja jetzt bei dot, aber lies den Artikel nochmal und probier die Problematik zu verstehen. Das wird nicht das letzte mal (und auch nicht die schwierigste Form) gsehen haben. Sobald du mehrere Klassen, mit mehr Abhängigkeiten hast wirst du wieder auf solche zyklischen Abhängigkeiten stossen und dann solltest du das exakt verstehen.

6

16.03.2012, 09:56

Ahhh danke Dot! Ich war etwas zu versteift darauf das die Übersetzungseinheit nur den dazugehörigen Header includieren muss. *shame on me*

Aber um zyklische Abhänigkeiten zu vermeiden sollte man forward declaration nur dann benutzen wenn nur der Pointer zu einer Instanz benötigt wird da bei eigenen Instanz ja die Größe bekannt sein muss? (Ich denke die Antwort auf die Frage ist ja aber ich geh gern auf nurmal sicher :D )
greate minds discuss ideas;
average minds discuss events;
small minds discuss people.

drakon

Supermoderator

Beiträge: 6 513

Wohnort: Schweiz

Beruf: Entrepreneur

  • Private Nachricht senden

7

16.03.2012, 11:07

Der Linker wird dich darauf hinweisen, wenn du lediglich eine forward declaration hast, er aber die komplette Deklaration benötigt.

Die Faustregel sollte also lauten: Benutze immer forward declarations und verwende das include nur, wenn es auch wirklich nötig ist.

David Scherfgen

Administrator

Beiträge: 10 382

Wohnort: Hildesheim

Beruf: Wissenschaftlicher Mitarbeiter

  • Private Nachricht senden

8

16.03.2012, 12:23

Wann ist es wirklich notwendig?
- Wenn man von der betreffenden Klasse ableiten möchte
- Wenn man eine Instanz der Klasse als Member benutzt oder als Parameter (by Value)
- Wenn man in einer Inline-Implementierung auf Member der Klasse zugreifen will
- Wenn die Größe einer Instanz der Klasse bekannt sein muss

To be continued?

9

17.03.2012, 19:29

Die Liste von David hab ich mir als Postit an den Monitor geklebt genau das habe ich gebraucht, danke dafür. Ich habe zu dem Thema noch eine Frage: Wenn ich eine Klasse a habe die einen protected member *b hat. Soll dann Klasse c welche von a erbt b.h nur in der c.cpp includieren?
greate minds discuss ideas;
average minds discuss events;
small minds discuss people.

10

17.03.2012, 21:04

Ja.
Wenn man wegen dem *b die im Header inkludieren sollte, sollte man das auch im Header von A machen und nicht erst in C. Sonst würde ja A alleine nicht funktionieren.
Lieber dumm fragen, als dumm bleiben!

Werbeanzeige