Cylic inclusion and forward declaration and template issue.

Hi, I've two classes (Server and Network) which have a template function defined in the .h file because we must define template function to header files.

The problem is that the class Network needs to include the class Server and the class Server needs to include the class Network.

And I can't make any forward declaration otherwise I have incomplete type errors.

How can I handle solve this ?




 
C:\Program Files (x86)\ODFAEG\include\odfaeg\Graphics\application.h|138|error: invalid use of incomplete type 'class odfaeg::network::SrkServer'|


Even if I use a pointer to the server in class network it doesn't compile.

The c++ include system is a real problem...
Last edited on
The C++ #include system is fancy copy-paste. Anything that you can set up with multiple header files can also be done in a single compilation unit (i.e. a single .cpp file).

It's hard to say what exactly needs to change in your setup w/o seeing more code. Can you show some excerpts of your code so we can understand your design?

At some point, you probably need to forward declare one of the classes before you #include its respective header file.

Here is an example of it all in 1 file, but I'm trying to find a nice way to actually demonstrate multiple files online:
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
58
59
60
61
62
63
64
65
#include <iostream>


template<typename T>
class Client;


template <typename T>
class Server  {
public: 
    Server()
    : client_(nullptr) { }
    
    void SetClient(Client<T>* client)
    {
        client_ = client;   
    }
    
    void UpdateUser()
    {
         if (!client_) return;
         
         client_->UpdateUser();
    }
    
    void OnUserUpdated() {
        std::cout << "Server: User has been updated!\n";
    }
    
    Client<T>* client_;
};


template <typename T>
class Client {
public:
    Client(Server<T>* server)
    : server_(server),
      userMagic_(0) { }

    void UpdateUser() {
        
        userMagic_ += 1;
        
        std::cout << "Client: New user value: " << userMagic_ << '\n';
        
        server_->OnUserUpdated();
    }
    
        
    Server<T>* server_;
    T userMagic_;
};


    
int main()
{
    Server<int> server;
    Client<int> client(&server);
    
    server.SetClient(&client);
    
    server.UpdateUser();
}
Last edited on
Ok I've solved the issue thanks.
For others interested, here was my original example now split into multiple files:

main.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
#include <iostream>

#include "server.hpp"
#include "client.hpp"
  
int main()
{
    Server<int> server;
    Client<int> client(&server);
    
    server.SetClient(&client);
    
    server.UpdateUser();
}


server.hpp
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
#ifndef SERVER_HPP
#define SERVER_HPP

#include <iostream>

template<typename T>
class Client;

template <typename T>
class Server  {
public: 
    Server()
    : client_(nullptr) { }
    
    void SetClient(Client<T>* client)
    {
        client_ = client;   
    }
    
    void UpdateUser()
    {
         if (!client_) return;
         
         client_->UpdateUser();
    }
    
    void OnUserUpdated() {
        std::cout << "Server: User has been updated!\n";
    }
    
    Client<T>* client_;
};

#endif 


client.hpp
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
#ifndef CLIENT_HPP
#define CLIENT_HPP

#include <iostream>

template<typename T>
class Server;

template <typename T>
class Client {
public:
    Client(Server<T>* server)
    : server_(server),
      userMagic_(0) { }

    void UpdateUser() {
        
        userMagic_ += 1;
        
        std::cout << "Client: New user value: " << userMagic_ << '\n';
        
        server_->OnUserUpdated();
    }
    
        
    Server<T>* server_;
    T userMagic_;
};

#endif 


Client: New user value: 1
Server: User has been updated!
Last edited on
Registered users can post here. Sign in or register to post.