Reputation: 57
I am having some linker errors that I can't for the life of me sort out. I simply have a .h file and a .cc file that will not compile into an executable I won't post all my code except the makefile here:
# Compiler variables
CCFLAGS = -Wall
# Rule to link object code files to create executable file
assignment5.exe: assignment5.cc
g++ -Wall -g -std=c++11 assignment5.cc assignment5.h -o assignment5.exe
clean:
rm assignment5.exe
I have both assignment5.h and assignment5.cc in the same directory and when running 'make' I get this error:
assignment5.cc:113: undefined reference to `binTree::inorder(void (*)(int))'
assignment5.cc:116: undefined reference to `binTree::preorder(void (*)(int))'
assignment5.cc:119: undefined reference to `binTree::postorder(void (*)(int))'
If anyone can help me I'd be eternally grateful EDIT: Code for those who asked .h File:
#ifndef ASSIGNMENT5
#define ASSIGNMENT5
class binTree; class BST;
class Node {
public:
// the value
int data;
// the left and right
Node * left;
Node * right;
// the constructor
Node(int data)
{
// set the data
this->data = data;
// set left and right to null
this->right = nullptr;
this->left = nullptr;
}
};
class binTree
{
public:
binTree();
virtual void insert( int ); //Inserts a node into the tree
unsigned height() const; //Returns height of the tree
unsigned size() const; //Returns size of the tree
void inorder( void(*)(int) ); //Inorder traversal of tree
void preorder( void(*)(int) ); //Preorder traversal
void postorder( void(*)(int) ); //Postorder traversal
protected:
Node* root; //root of the tree
private:
void insert( Node*&, int ); //Private version of insert()
unsigned height( Node* ) const; //Private version of height
unsigned size( Node* ) const; //Private version of size()
void inorder( Node*, void(*)(int) ); //Private version of inorder()
void preorder( Node*, void(*)(int) ); //Private version of preorder()
void postorder( Node*, void(*)(int) ); //Private version of postorder()
};
#endif
.cc File:
#include "assignment5.h"
#include <iostream>
#include <iomanip>
#include <algorithm>
#include <vector>
using namespace std;
const int MAX_SIZE = 40;
const int MAX_COUNT = 40;
const int WIDTH = 5;
const int ROW_SIZE = 8;
int mcount = 0;
int rcount = 0;
void display(int d)
{
if (mcount < MAX_COUNT) {
cout << setw(WIDTH) << d;
mcount++;
rcount++;
if (rcount == ROW_SIZE) {
cout << endl;
rcount = 0;
}
}
}
binTree::binTree()
{
// set the root to null pointer
root = nullptr;
}
void binTree::insert( int v ) //Inserts a node into the tree
{
// insert this value into the root
insert(root,v);
}
unsigned binTree::height() const //Returns height of the tree
{
// return the height of this tree
return height(root);
}
unsigned binTree::size() const //Returns size of the tree
{
// return the size
return size(root);
}
void binTree::inorder( void(*)(int) p ) //Inorder traversal of tree
{
// use the local inorder
inorder(root, p);
}
void binTree::preorder( void(*)(int) p ) //Preorder traversal
{
// use the local preorder
inorder(root, p);
}
void binTree::postorder( void(*)(int) p ) //Postorder traversal
{
// use the local inorder
postorder(root, p);
}
void binTree::insert( Node*& node, int n ) //Private version of insert()
{
// if this is null, create new node
if( node == nullptr )
{
// create new node
node = new Node(n);
}
// if node is less or more
if( n < node->data )
{
// go left
insert(node->left,n);
}
else if( n > node->data )
{
// go right
insert(node->right, n);
}
}
unsigned binTree::height( Node* node ) const //Private version of height
{
// if this is null, return 0
if( node == nullptr )
return 0;
// left height and right height
unsigned leftHeight = 0;
unsigned rightHeight = 0;
// check if left height
if( node->left != nullptr )
leftHeight = height( node->left );
// right height
if( node->right != nullptr )
rightHeight = height( node->right );
// return max
if( leftHeight > rightHeight )
return leftHeight + 1;
else
return rightHeight+1;
}
unsigned binTree::size( Node* node) const //Private version of size()
{
// if this is null
if( node == nullptr )
return 0;
// return size
return 1 + size(node->left) + size(node->right);
}
#define BINTREE_MAIN
#ifdef BINTREE_MAIN
int main() {
vector<int> v(MAX_SIZE);
for (int i=1; i<MAX_SIZE; i++)
v[i] = i;
random_shuffle( v.begin(), v.end());
binTree bt;
vector<int>::iterator it;
for (it=v.begin(); it!=v.end(); it++)
bt.insert( *it );
cout << "Height: " << bt.height() << endl;
cout << "Size: " << bt.size() << endl;
cout << "In order traverse (displaying first " << MAX_COUNT << " numbers): " << endl;
mcount = rcount = 0;
bt.inorder( display );
cout << "\n\nPre order traverse (displaying first " << MAX_COUNT << " numbers): " << endl;
mcount = rcount = 0;
bt.preorder( display );
cout << "\n\nPost order traverse (displaying first " << MAX_COUNT << " numbers): " << endl;
mcount = rcount = 0;
bt.postorder( display );
cout << endl;
return 0;
}
#endif
Upvotes: 1
Views: 120
Reputation: 15810
You have two bintree classes. Fix that first and report back.
class binTree; class BST;
class Node {
....
};
....
class binTree {
};
Upvotes: 0
Reputation: 2224
The Makefile is not (the only one) to blame. Your example is plagued with problems. For starters, it is not a complete example, as a half of methods is not defined, only declared, and there is no main()
, even a dummy one, when you are trying to build an executable, not an object file. Such an incomplete example really complicates helping you.
And you seem not telling the whole truth. My g++
invocation breaks even earlier, at this line:
void inorder( void(*)(int) ); //Inorder traversal of tree
expected primary-expression before ‘void’
Did you attempt to declare a method which accepts a parameter that is a pointer to a function(int)? You need to understand what is the syntax for that in C++.
Your recipe line in the makefile is also flawed: you do not need to pass header files to a compiler, they are included automatically when you #include
them in .cc files. Your build line should be similar to:
g++ $(CCFLAGS) -g -std=c++11 assignment5.cc -o assignment5.o
Upvotes: 1
Reputation: 2868
You haven't implemented the private functions:
void inorder( Node*, void(*)(int) ); //Private version of inorder()
void preorder( Node*, void(*)(int) ); //Private version of preorder()
void postorder( Node*, void(*)(int) ); //Private version of postorder()
Upvotes: 0