I'm trying to build a Linked List who's elements are of my own specified type. Now I'm not going to lie I'm winging a lot of this having not had much experience with OOP in C++ but I'm stuck with a single error.
My LinkedList:
#include "Vehicle.h"
#include "string"
using namespace std;
class LinkedList
{
private:
struct Node
{
Vehicle data;
Node* next;
};
Node* root;
int noofitems;
public:
LinkedList();
int getNoOfItems();
Vehicle getItemByIndex(int index);
void addItem(Vehicle itemIn);
void deleteItem();
void insertItem(Vehicle itemIn);
~LinkedList();
};
The Constructor and addItem()
LinkedList::LinkedList() : root(NULL), noofitems(0) {}
void LinkedList::addItem(Vehicle itemIn)
{
Node* temp;
temp = new Node();
temp->data = itemIn;
temp->next = this->root;
this->root = temp;
}
My compiler is giving me this error:
error C2512: 'LinkedList::Node' : no appropriate default constructor available. Now I've tried giving the struct a constructor like so:
struct Node
{
Vehicle data;
Node* next;
Node() : next(NULL) {}
};
But then I get a new error on top of the old one: IntelliSense: no default constructor exists for class "Vehicle". The word constructor is starting to look wrong and I'm really frustrated. Thanks In advance.
By the way if details of the vehicle class are needed:
class Vehicle
{
protected:
string make;
string model;
string regNo;
int engineSize;
bool rented;
public:
Vehicle(string makeIn, string modelIn, string regNoIn, int engineSizeIn);
string getMakeModel(); // return two values concatinated
string getRegNo();
int getEngineSize();
bool getRented();
void setRented(bool rentedIn);
~Vehicle();
};
Vehicle::Vehicle(string makeIn, string modelIn, string regNoIn, int engineSizeIn) :
make(makeIn), model(modelIn), regNo(regNoIn), engineSize(engineSizeIn),
rented(false)
{}
string Vehicle::getMakeModel()
{
return make + " " + model;
}
string Vehicle::getRegNo()
{
return regNo;
}
int Vehicle::getEngineSize()
{
return engineSize;
}
bool Vehicle::getRented()
{
return rented;
}
void Vehicle::setRented(bool rentedIn)
{
rented = rentedIn;
}
Vehicle::~Vehicle(){}
Node has a member of type Vehicle. Since you cannot default construct a Vehicle the default constructor for Node is marked as deleted. You will need to provide your own default constructor that constructs the Vehicle member to some state like
struct Node
{
Vehicle data;
Node* next;
Node() : data("", "", "", 0), next(nullptr) {}
};
or provide a default constructor for Vehicle like
class Vehicle
{
//...
public:
Vehicle() = default;
//...
};
The error is self explanatory. You have not explicitly initialized vehicle in your Node class as shown:
struct Node
{
Vehicle data;
Node* next;
Node() : next(NULL) {} // NO initialization for vehicle
};
The compiler will try and then construct a Vehicle using it's default constructor, but it finds none. In your vehicle class you have defined a constructor taking arguments:
Vehicle(string makeIn, string modelIn, string regNoIn, int engineSizeIn);
Thus the compiler will not generate one for you. To fix this you can either define a default constructor yourself, or you can declare one with the word default which will force the compiler too generate one:
Related
Hi I wanted to make my personal stack class with template
and make a stack with personal class.
template <class T>
class stack{
public:
stack(T);
~stack();
void insert(T);
T pop();
void printstack();
private:
int top;
int capacity;
T *list;
};
template <class T>
stack<T>::stack(T first){
top=0;
capacity=10;
list = new T[capacity];
memset(cards, 0, sizeof(T)*10);
list[0]=first;
}
and I wanted make a stack with card method
class node{
public:
node(int i=0,int j=0);
~node();
private:
int node_num;
int nodenum;
};
class list{
public:
list();
~list();
private:
stack<node> nodelist;
};
list::list(){
stack<node> nodelist(node(1,1));
}
But when I run the code error shows up
"Constructor for 'deck' must explicitly initialize the member 'decklist' which does not have a default constructor"
it works fine when I use stack deck1(1); what might be the problem?
Thank you for reading.
You wrote this
deck::deck(){
stack<card> decklist(card(1,1));
}
but that just declares a variable in your constructor called decklist which is different from the decklist in your class.
To initialise the decklist in your class you should use an initialiser list. Like this
deck::deck() : decklist(card(1,1)) {
}
I created a class BST and I am facing problem in creating constructor of a struct node in it.
class BST{
private:
struct node{
int key;
node* left;
node* right;
};
node* root;
public:
//constructor for BST
BST();
//constructor for node
node(int x);
};
I get an error expected unqualified-id before 'int'.
So,I read what is an unqualified-id but didn't understand why is it needed here.
Constructors for classes and structs must be declared within the definition of the class/struct. Your version does not do this, as node(int) is declared outside the node class.
Change your code to this:
class BST
{
private:
struct node
{
int key;
node* left;
node* right;
node(int x);
};
node* root;
public:
BST();
};
Then if you decide to implement the node constructor outside of the BST class:
BST::node::node(int x)
{
// code here
}
I am building a linked list, where nodes are all linked to Head. The Head is derived from node, but the Head requires a pointer to last node. See the comment at the top of code.
/* Base <= node <= node <= node
* | ^
* | ptr to last node |
* -------------------------
*/
class Node {
private:
Node* prev;
public:
explicit Node(Node* parent) : prev(parent) {
Node* foo_ptr = this;
while (foo_ptr->prev != 0) {
foo_ptr = foo_ptr->prev;
}
// foo_ptr points to Base, how can I now change Base::last?
}
};
class Base : public Node {
private:
Node* last;
public:
Base() : Node(0), last(this) {}
};
How can I change change variable Base::last when adding new node, for example:
Node* n = new Base;
new Node(n); // can Node constructor update n->last?
I was thinking to use virtual function to update the variable, but according to this post: Calling virtual functions inside constructors, its a no no so I do not want to do it. So is there a good way of achieving this type of linked list?
Thanks...
http://coliru.stacked-crooked.com/a/213596aa1ffe7602
I added a flag value so we can tell that we actually accessed the Base class:
#include <iostream>
class Node {
private:
Node* prev;
public:
inline void changeBaseLast(Node* base);
explicit Node(Node* parent) : prev(parent) {
Node* foo_ptr = this;
while (foo_ptr->prev != 0) {
foo_ptr = foo_ptr->prev;
}
// foo_ptr points to Base
// now change Base::last
changeBaseLast(foo_ptr);
}
int data;
};
class Base : public Node {
private:
Node* last;
public:
int flag;
Base() : Node(0), last(this), flag(0) {}
};
//Here, we can see that we change the base_ptr to 1.
void Node::changeBaseLast(Node* base) {
Base* base_ptr = static_cast<Base*>(base);
base_ptr->flag=1;
}
int main() {
Node* n = new Base;
new Node(n);
std::cout << static_cast<Base*>(n)->flag << std::endl;
}
If you pull out the part that refers to the derived class and then inline it, there should be no problems with this. Notice, though, that I need to define the functions that refer to the derived class after I define the derived class.
If you're sure that the last node will always be a Base object, then using static_cast<Base*> may not be that bad.
class Base : public Node {
...
// Factory method to create child nodes
Node* getNode(Node* parent) {
Node* newNode = new Node(parent);
last = newNode;
return newNode;
}
}
This one should be even easier to understand and still uses static_cast, for you want to append by means of the Base class.
class Node {
private:
Node* prev;
public:
explicit Node() : prev{nullptr} { }
void setParent(Node *parent) {
prev = parent;
}
};
class Base : public Node {
private:
Node* last;
public:
Base() : Node{}, last{this} { }
void append(Node *node) {
node->setParent(last);
last = node;
}
};
int main() {
Node* n = new Base;
static_cast<Base*>(n)->append(new Node{});
}
Anyway, I don't understand the need of the Base class.
Can't you simply store somewhere (as an example a struct) two pointers, one for the head of the list and one for the last node?
I have been implementing the Red Black Trees in C++ using inheritence. I have 4 Classes, Node, Tree, RBNode, RBTree.
class Node
{
protected:
int data;
Node *left;
Node *right;
Node *parent;
public:
Node();
Node(int data);
void print_node(ofstream &file);
Node * find_node(int data);
void insert_node(Tree *t);
void left_rotate_node(Tree *t);
void right_rotate_node(Tree *t);
void delete_node(Tree *t);
}
class Tree
{
protected:
Node * root;
list<int> treedata;
public:
Tree();
virtual Node * get_root();
virtual void set_root(Node *root_node);
void insert_into_tree();
void delete_from_tree();
virtual void print_tree();
}
RBNode and RBTree inherit Node, Tree respectively. But I am not able to use the functions of the Node class. For example, the function void Tree::insert_node(Tree *t);
Even in the class RBNode, this function does the same work except that the funntion receives RBTree as the parameter. How can I make use of the same function without redeclaring it in RBNode. I thought of using casting inside function, but how will I know which classes object is calling the function.
Please give me some suggestions. I am new to C++.
Either the inheritance was not properly defined, or there is a confuson on insert_node(Tree *t) which is defined in the Node and not in the Tree.
Anyway, the following minimal code example compiles well:
class Tree;
class Node
{
protected:
int data;
Node *left,*right, *parent;
public:
Node(int data=0) : data(data), left(nullptr), right(nullptr), parent(nullptr) {}
void insert_node(Tree *t) { cout << "Insert" << endl; }
};
class Tree
{
protected:
Node * root;
list<int> treedata;
public:
Tree() : root(nullptr) {}
};
class RBSnode : public Node {}; // public inheritance
class RBStree : public Tree {};
...
RBSnode n;
RBStree t;
n.insert_node(&t);
Note that in absence of the public inheritance specifier, private inheritance is assumed: within the class you have acces to all the protected and public members of the base class, but outside, the class, you don't see the inherited members. I guess it's what happenned to you.
say in a header file can I have a helper class fully defined and use it in the class file that includes the header. what is the correct way of doing it?
//HEader
class LinkedList() {
public:
LinkedList(int a);
private:
Node *root;
class Node {
int data;
Node *next;
};
};
//cpp file
#include "LinkedList"
LinkedList::LinkedList(int a) {
root = new Node();
root.data = a;
root->next = NULL;
}
when i try doing something like that it ends up saying Node is not a name of type in my header file.
That is totally fine. I made some fixes to your code.
LinkedList.h
class LinkedList
{
public:
LinkedList(int a);
private:
class Node {
public:
int data;
Node *next;
};
Node *root;
};
LinkedList.cpp
LinkedList::LinkedList(int a) {
root = new Node();
root->data = a;
root->next = NULL;
}
You tried to use Node before you even declared and defined it. Default access level in C++ classes is private, so you could not access private data members of Node in LinkedList constructor.