Multiple Definitions error

So I get this nasty multiple definitions error when I compile my program with g++. The program uses two classes, cbt (complete binary tree), and node which are both defined in tree.h


from the terminal:
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
make
g++ -c -Wall tree.cpp
g++ -g -Wall -o cbtfun cbtfun.cpp tree.o
tree.o: In function `cbt::distance(Node*, Node*)':
tree.cpp:(.text+0x0): multiple definition of `cbt::distance(Node*, Node*)'
/tmp/ccZYPpvM.o:/fs/home1/student/b/bfurlong/workspace/cbtfun/tree.cpp:81: first defined here
tree.o: In function `cbt::findDistances()':
tree.cpp:(.text+0x8a): multiple definition of `cbt::findDistances()'
/tmp/ccZYPpvM.o:/fs/home1/student/b/bfurlong/workspace/cbtfun/tree.cpp:63: first defined here
tree.o: In function `log2(unsigned int)':
tree.cpp:(.text+0xfa): multiple definition of `log2(unsigned int)'
/tmp/ccZYPpvM.o:/fs/home1/student/b/bfurlong/workspace/cbtfun/tree.cpp:141: first defined here
tree.o: In function `cbt::deleteSubtree(Node*&)':
tree.cpp:(.text+0x1dc): multiple definition of `cbt::deleteSubtree(Node*&)'
/tmp/ccZYPpvM.o:/fs/home1/student/b/bfurlong/workspace/cbtfun/tree.cpp:119: first defined here
tree.o: In function `cbt::~cbt()':
tree.cpp:(.text+0x232): multiple definition of `cbt::~cbt()'
/tmp/ccZYPpvM.o:/fs/home1/student/b/bfurlong/workspace/cbtfun/tree.cpp:134: first defined here
tree.o: In function `cbt::~cbt()':
tree.cpp:(.text+0x26e): multiple definition of `cbt::~cbt()'
/tmp/ccZYPpvM.o:/fs/home1/student/b/bfurlong/workspace/cbtfun/tree.cpp:134: first defined here
tree.o: In function `cbt::~cbt()':
tree.cpp:(.text+0x2aa): multiple definition of `cbt::~cbt()'
/tmp/ccZYPpvM.o:/fs/home1/student/b/bfurlong/workspace/cbtfun/tree.cpp:134: first defined here
tree.o: In function `cbt::preOrderShow(Node*) const':
tree.cpp:(.text+0x2e6): multiple definition of `cbt::preOrderShow(Node*) const'
/tmp/ccZYPpvM.o:/fs/home1/student/b/bfurlong/workspace/cbtfun/tree.cpp:102: first defined here
tree.o: In function `cbt::preOrderShow() const':
tree.cpp:(.text+0x344): multiple definition of `cbt::preOrderShow() const'
/tmp/ccZYPpvM.o:/fs/home1/student/b/bfurlong/workspace/cbtfun/tree.cpp:113: first defined here
tree.o: In function `cbt::cbt(int)':
tree.cpp:(.text+0x362): multiple definition of `cbt::cbt(int)'
/tmp/ccZYPpvM.o:/fs/home1/student/b/bfurlong/workspace/cbtfun/tree.cpp:17: first defined here
tree.o: In function `cbt::cbt(int)':
tree.cpp:(.text+0x5c2): multiple definition of `cbt::cbt(int)'
/tmp/ccZYPpvM.o:/fs/home1/student/b/bfurlong/workspace/cbtfun/tree.cpp:17: first defined here


tree.h:
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
#ifndef TREE_H
#define TREE_H

    class cbt; //forward declaration

    class Node
    {
    public:
        Node( ) : parent(NULL), left(NULL), right(NULL), next(NULL){}
        Node(int theData, Node* parentLink, Node* leftLink, Node* rightLink, Node* nextLink)
            : data(theData), parent(parentLink), left(leftLink), right(rightLink), next(nextLink){}
        friend class cbt;
        int data;
        int level;
        Node *parent;
        Node *left;
        Node *right;
        Node *next;
    };









    class cbt
    {
    public:
        cbt( ) : root(NULL){}
        cbt(int numberOfNodes);
        void findDistances();
        void deleteSubtree(Node*& subTreeRoot);
        virtual ~cbt( );
        int distance(Node* self, Node* relative);
        void preOrderShow( ) const;
        void preOrderShow(Node* subTreeRoot) const;
        Node *root;
    };


#endif 


tree.cpp:
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
#include <iostream>
#include <cstddef>
#include <cstdlib>
#include "tree.h"
using namespace std;
int log2(unsigned int n);

//Preconditions: numberOfNodes >= 0
//Postconditions: constructs CBT with data = -1 and level = 0 for root, 1 for next level, etc.
cbt::cbt(int numberOfNodes) // MULT DEF ERROR
{
...
}

// PREC: Valid CBT
// POSTC: Valid CBT has its total distances in data field of its nodes.
void cbt::findDistances()  // MULT DEFINITION ERROR
{
...
}

// PREC: takes two nodes of a valid CBT
// POSTC: returns the distance between the two nodes
int cbt::distance(Node* self, Node* relative)
{
...
}

void cbt::preOrderShow(Node* subTreeRoot) const // MULT DEF ERROR
{
...
}


void cbt::preOrderShow( ) const  // MULT DEF ERROR
{
...
}


void cbt::deleteSubtree(Node*& subTreeRoot) // MULT DEF ERROR
{
...
}


cbt::~cbt( ) // ERROR HERE
{
...
}

// precondition: takes any integer
// postcondition: gives floored binary log of the integer.  returns -1 if integer is 0.
int log2(unsigned int n) { // ERROR here
...
}


I have no idea what to do to fix this so please help...
It's gotta be that forward declaration. You declare class cbt twice. Since all of your Node methods are public, do you need cbt to be a friend class? If not then you can get rid of that declaration at the top. If you do, you might try putting the node and the cbt stuff in separate headers which include each other... Hopefully that works
No, mutual inclusion only leads to compiler errors.
I've never actually encountered this problem myself, but I once asked my favorite teacher about how to solve such a problem and his answer was "derive one class from the other".
Alternatively, you could merge both classes into one and add a type value to keep the methods from messing up the data. It would also be advisable to make the data private, just in case.
Inheritance doesn't really make sense in this case because the node doesn't inherit properties of the tree.

I think maybe the correct solution would be to nest the Node class inside the tree class.

like:
1
2
3
4
5
6
7
8
class cbt{

    class Node {
         // Node stuff....
    };

    // cbt stuff...
};
Last edited on
Ok, this is a link error. Changing code isn't going to do much. The posted code does not look like it should generate a link error, however the source for cbtfun.cpp is not posted.
What does cbtfun.cpp #include? It's not including tree.cpp is it?
header for cbtfun.cpp

1
2
3
#include <iostream>
#include "tree.h"
#include "tree.cpp" 
Yup, remove #include "tree.cpp" and it will work.

EDIT: never #include .cpp files. Only header files.
Last edited on
Topic archived. No new replies allowed.