Try doing this with your code:
devf.h
#ifndef DEVF_H // Add this line
#define DEVF_H // Add this line
// #include <iostream> // removed this as not needed from what is shown
#include <string> // added this as is needed
struct A {
int ax() const; // added const as it doesn't change
std::string ay( const std::string& jj ) const; // changed string to const ref & added const
};
struct B {
/*struct*/ A* f; // keyword struct not needed here.
int bx() const { // added const
return f->ax();
}
std::string by( const std::string& jj ) const { // changed to const ref & added const
return f->ay( jj );
}
};
#endif // !DEVF_H // Add this line
devf.cpp
#include "devf.h"
int A::ax() const {
return 5;
}
std::string A::ay( const std::string& jj ) const {
return jj;
}
Then you asked this or made this statement:
How can I solve this problem? I want the definitions of ax and ay functions in header file and the implementions in .cpp
devf.h
#ifndef DEVF_H
#define DEVF_H
#include <string>
struct A {
int ax() const;
std::string ay( const std::string& jj ) const;
};
struct B {
A* f;
int bx() const;
std::string by( const std::string& jj ) const;
};
#endif // !DEVF_H
devf.cpp
#include "devf.h"
int A::ax() const {
return 5;
}
std::string A::ay( const std::string& jj ) const {
return jj;
}
int B::bx() const {
return f->ax();
}
std::string B::by( const std::string& ) const {
return f->ay( jj );
}
This should help from what you have shown.
I've tried it with this:
main.cpp
#include <iostream>
#include "devf.h"
int main() {
B b;
std::cout << b.bx() << std::endl;
std::cout << b.by( "hello world" ) << std::endl;
std::cout << "\nPress any key and enter to quit." << std::endl;
char q;
std::cin >> q;
return 0;
}
output
5
hello world
Press any key and enter to quit.
-
EDIT
I asked the OP: Are you including other header files?
The OP answered with:
Yes, the header "devf.h" is included in other headers
And I believe this is where the OP's problem resides. I believe that the OP is a victim of Circular Includes
which will result in multiple definitions.
Example:
A.h
#ifndef A_H
#define A_H
#include "B.h" // circular include
struct A {
int a;
B b;
};
#endif // !A_H
B.h
#ifndef B_H
#define B_H
#include "A.h" // circular include
struct B {
int b;
};
#endif // !B_H
To resolve this circular include problem...
- You need to use
class
or struct prototypes
- forward declarations
in the headers; works with pointer & reference types
.
- Only include other header files within a header file if the
definition
not the declaration
is needed.
- Once you have the
class
or struct's forward declaration
in the header file
remove that class's
include directive
and put it within its cpp file
fixing the above example:
A.h
#ifndef A_H
#define A_H
// Since A has a pointer to B we remove the include from here
// and replace it with a forward declaration or class prototype...
// #include "b.h" // cicular include
class B;
struct A {
int a;
B b;
};
#endif // !A_H
A.cpp
#include "A.h"
#include "B.h" // moved the include to here - prevents circular includes
B.h
#ifndef B_H
#define B_H
// Since B does not require A we can omit this all together.
//#include "A.h" // circular include
struct B {
int b;
};
#endif // !B_H
B.cpp
#include "B.h"
You can refer to this Q & A
Resolve build errors due to circular dependency amongst classes on stack for a more detailed explanation.
Once you go through the rest of your code base and fix all of the circular includes you should have no error as the above set of classes do compile and run without error.