i tried to create BST on cpp
i done the class Node in the class Tree because it's logical.
header:
class Node;
class Tree
{
public:
Node* root;
Tree();
Tree(int val);
void insert(int val);
class Node
{
public:
Node();
Node(int val);
Node* right;
Node* left;
int val;
};
};
implamation:
Tree::Tree()
{
this->root = NULL;
}
Tree::Node::Node()
{
}
Tree::Node::Node(int val)
{
this->val = val;
this->left = NULL;
this->right = NULL;
}
void Tree::insert(int val)
{
this->root = new Node(3);
}
i got an error on
this->root = new Node(3);
IntelliSense: a value of type "Tree::Node *" cannot be assigned to an entity of type "Node *"
error C2440 : '=' : cannot convert from 'Tree::Node *' to 'Node *'
what did i done wrong please?
root this Node*
and new Node (3) return Node*
what is the problem?
thanks!!!
To my understanding, in your current implementation, you are declaring two classes with the name Node; one is in the global scope while the other one is in the scope of the class Tree. This can be solved by using only one class.
Related
I'm trying to define a custom template container, and then add custom class objects (Students) into it. Here's my code:
class Student{
public:
string subject;
Student(string _subject){
subject = _subject;
}
};
And here's my LinkedList template code
template <class T>
class LinkedList{
private:
struct Node{
Node *next;
T value;
};
Node *root;
Node *curr;
int count;
public:
LinkedList() : count(0), root(NULL){}
void add(T val){
if (root == NULL){
root = new Node;
root->value = val;
root->next = NULL;
curr = root;
}
else{
curr->next = new Node;
curr = curr->next;
curr->value = val;
curr->next = NULL;
}
count++;
}
void print(){
for (Node *itr=root; itr != NULL; itr = itr->next){
cout << itr->value << endl;
}
}
};
int main(){
LinkedList<Student> a;
Student sam("Math");
a.add(sam)
}
When I run it, I get
linkedlist.cpp: In constructor ‘LinkedList::Node::Node()’:
linkedlist.cpp:27: instantiated from ‘void LinkedList::add(T) [with T = Student]’
linkedlist.cpp:133: instantiated from here
linkedlist.cpp:27: error: no matching function for call to ‘Student::Student()’
linkedlist.cpp:18: note: candidates are: Student::Student(std::string)
linkedlist.cpp:15: note: Student::Student(const Student&)
linkedlist.cpp: In member function ‘void LinkedList::add(T) [with T = Student]’:
linkedlist.cpp:40: note: synthesized method ‘LinkedList::Node::Node()’ first required here
I have no clue what that error really means, and what it's asking me to do. If I do this instead:
int main(){
LinkedList<Student*> a;
Student sam("Math");
a.add(&sam);
}
It works just fine.
But storing references to objects is not what I'm after. How can I get my LinkedList to make copies of the object I wish to add to it?
Thanks in advance!
First of all...
#include <utility>
Now, change this...
struct Node {
Node* next;
T value;
};
For...
struct Node {
Node* next;
T value;
inline Node(const T &value) : value(value), next(nullptr) {}
inline Node(T &&value) : value(std::move(value)), next(nullptr) {}
};
And, this...
void add(T val) {
if(this->root == nullptr) {
this->root = new Node;
this->root->value = val;
root->next = NULL;
curr = root;
} else {
curr->next = new Node;
curr = curr->next;
curr->value = val;
curr->next = NULL;
}
count++;
}
For this...
void add(const T &val){
if(this->root == nullptr) {
this->root = new Node(val);
this->curr = root;
} else {
this->curr->next = new Node(val);
this->curr = this->curr->next;
}
this->count++;
}
void add(T &&val){
if(this->root == nullptr) {
this->root = new Node(std::move(val));
this->curr = root;
} else {
this->curr->next = new Node(std::move(val));
this->curr = this->curr->next;
}
this->count++;
}
What happens is that you're creating a Node object with new Node with it's implicit default constructor. That implies that the default constructor for Node::value is called. Then, can you tell me if there's any? No. Student does not have a default constructor, so this won't work.
BTW, I made some minor redesigns to your code, so to avoid several issues that appeared by the way. As a bonus, you can now use move semantics (try list.add(Student("Joe")))!
Also, remember to initialize curr to nullptr in the constructor initialization list!
Student must provide a default constructor. Try that:
Student(string _subject = "")
Because when you do new Node it creates a Node object, so it creates the Node* and T attributes of the Node class. And if T class has no default constructor, the compiler does not know how to create the object.
That's what the error message says:
error: no matching function for call to ‘Student::Student()’ linkedlist.cpp:18: note: candidates are: Student::Student(std::string)
It cannot find a default constructor Student::Student(), it only found one taking a string as argument Student::Student(std::string)
I have a header file containing this class definition:
class visitorlist {
struct Node {
visitor vis;
Node* next;
};
Node* head;
Node* tail;
public:
visitorlist() { //written here to have it as inline.
head = NULL;
tail= NULL;
}
~visitorlist();
int lengthvl();
void add(const visitor);
void popandexit();
void transfer(visitorlist);
void deletenode(Node*);
int refiprio();
int refioffno();
int refifloor();
visitor reravi();
bool isempty();
Node* rehead();
};
and in a source file with the above header included I have:
Node* visitorlist::rehead() {
return head;
}
This causes an error: 'Node' does not name a type.
Isn't Node on the scope of the function?
Use
visitorlist::Node* visitorlist::rehead() {
return head;
}
Or, since C++11:
auto visitorlist::rehead() -> Node* {
return head;
}
I having some doubt with struct.
struct node
{
int data;
node* next;
}node; <---- what does this actually do?
Thanks.
add on::
Hi, trying to fix this error..
Line 11: error: expected constructor, destructor, or type conversion before '*' token
compilation terminated due to -Wfatal-errors.
#include <iostream>
using namespace std;
struct node
{
int data;
node* next;
}node;
node* nodeNew(int newData, node* newNext) // line 11
{
node* n= new node;
n->data= newData;
n->next= newNext;
return n;
}
void listPrint(node* p)
{
while( p!=NULL )
{
cout << p->data << " "; p= p->next;
}
}
int main()
{
}
Is happens when i add that "node" in the struct.
The final line:
}node;
creates a variable with the type struct node, named node. It's equivalent to:
struct node {
int data;
node* next;
};
struct node node;
EDIT: In response to your edit, the line:
node* nodeNew(int newData, node* newNext)
is erroring because node isn't a type. Either change it to:
struct node* nodeNew(int newData, struct node* newNext)
or change the structure declaration to:
typedef struct node node;
struct node {
int data;
node* next;
};
To be exact, it creates an object from given struct in given scope. Word 'variable' is a too generic term.
i'm attempting to implement three methods currently a get_first(), get_last() and print_node(). get_first() will return the head of a list, get_last() the tail, and print_node() will just print the data field of a node sent to it. im trying to implement but continually getting pointer errors for any changes that i make.
here's my node.h header:
class Node
{
private:
int data;
Node *next;
Node *prev;
friend class LinkedList;
};
class LinkedList
{
private:
Node *head;
Node *tail;
public:
LinkedList();
~LinkedList();
bool empty();
void insert_left(int v);
void insert_right(int v);
Node* get_first();
Node* get_last();
void print_list();
void print_node(Node *n);
void remove_left();
void remove_right();
protected:
void add(Node *v, int d);
void remove(Node *v);
};
here are the relevant portions of my list.cpp class implementation file:
#include <iostream>
#include "node.h"
using namespace std;
LinkedList :: LinkedList()
{
head = new Node;
tail = new Node;
head->next = tail;
tail->prev = head;
}
LinkedList :: ~LinkedList()
{
while(!empty())
{
remove_left();
}
delete head;
delete tail;
}
void LinkedList :: add(Node *v, int d)
{
Node *u = new Node;
u->data = d;
u->next = v;
u->prev = v->prev;
v->prev->next = v->prev = u;
}
void LinkedList :: print_list()
{
Node *tmp = head;
while(tmp != NULL)
{
cout << tmp->data << endl;
tmp = tmp->next;
}
}
void LinkedList :: print_node(Node *n)
{
Node *tmp = n;
cout << tmp->data << endl;
}
Node LinkedList :: get_first()
{
return head;
}
Node LinkedList :: get_last()
{
return tail;
}
finally here's my main function in a file called main.cpp:
#include <cstdlib>
#include <iostream>
#include "list.cpp"
using namespace std;
int main(int agrc, char **argv)
{
LinkedList *l = new LinkedList();
//LinkedList *m = new LinkedList();
l->insert_left(200);
l->insert_left(700);
l->insert_left(300);
Node *temp = l->get_first();
//l->print_list();
l->print_node(temp);
delete l;
return 0;
}
here's the current error output:
g++ main.cpp -o main
In file included from main.cpp:3:
list.cpp:85: error: prototype for ‘Node LinkedList::get_first()’ does not match any in class ‘LinkedList’
node.h:24: error: candidate is: Node* LinkedList::get_first()
list.cpp:90: error: prototype for ‘Node LinkedList::get_last()’ does not match any in class ‘LinkedList’
node.h:25: error: candidate is: Node* LinkedList::get_last()
make: *** [main] Error 1
i'm not sure of the exact changes to make but i think it has to do with how i'm returning the head in the get_first() and last() functions. Please excuse the length of the post.
You are returning Node* in function declaration but in definition you have Node as the return type. Use this
Node* LinkedList :: get_first()
{
return head;
}
Node* LinkedList :: get_last()
{
return tail;
}
Data members head and tail are defined as
Node *head;
Node *tail;
that is they are pointers to Node. So if any function returns either head or tail then its return type has to be Node *
So these member function definitions
Node LinkedList :: get_first()
{
return head;
}
Node LinkedList :: get_last()
{
return tail;
}
are wrong. They return head and tail but have no the return type Node * and their definitions do not coinside with theor declarations in the class.
Also the constructor definition is wrong. It shoild look as
LinkedList :: LinkedList() : head( nullptr ), tail( nullptr )
{
}
In this case member function empty should be declared as
bool empty() const;
and defined as
bool empty() const { return ( head == nullptr ); }
Just started learning c++ for a class, I can't figure out what is wrong with this code! I'm making a stack class with a helper class nested inside it called node that acts as a linked list. The error I'm getting is on line 12 and is:
Stack.cpp: In destructor ‘Stack::~Stack()’:
Stack.cpp:12:24: error: request for member ‘getNext’ in ‘((Stack*)this)->Stack::node’, which is of non-class type ‘Stack::Node*’
Here's my code:
#include "Stack.h"
Stack:: Stack ()
{
height = 0;
node = 0;
}
Stack:: ~Stack()
{
while(node != 0){
Node *next = *node.getNext();
delete node;
node = next;
}
node = 0;
}
And Here's my header file:
using namespace std;
class Stack
{
private:
int height;
class Node{
private:
int data;
Node* next;
public:
void setData(int x){
data = x;
}
void setNext(Node* x){
next = x;
}
int getData(){
return data;
}
Node* getNext(){
return next;
}
};
Node* node;
public:
Stack();
~Stack();
void push(int x);
int pop();
int peek();
int getHeight();
bool isEmpty();
};
Node *next = *node.getNext();
should be
Node *next = (*node).getNext();
Since . operator has higher precedence than * deference operator.
You can also use:
Node *next = node->getNext();