I am using a linked list to implement a set class. In order to hide my struct Node from the users, I put the struct Node declaration into private. Furthermore, I overloaded the operator +, which denotes union operation between two sets. Because I want to implement it by recursion, I overloaded the operator + in the private field called unionMerge. However, it produced an error "error: ‘unionMerge’ was not declared in this scope", but I did put the unionMerge declaration above the operator+ in the Set.cpp file. Could someone help me out?
Set.h is an interface file.
Set.cpp is the implementation for the interface.
Here is the interface file, Set.h:
#ifndef SET_H
#define SET_H
#include <iostream>
using namespace std;
class Set{
public:
Set();
friend const Set operator+(const Set& a, const Set& b);
private:
struct Node{ //private Node
int value;
Node* next;
};
Set(Node *p); //private constructor
Node* list;
//overload the public operator+ above
static Node* unionMerge(const Node* p, const Node *q);
};
#endif
Here is the implementation file, Set.cpp:
#include <iostream>
#include "Set.h"
Set::Set():list(nullptr){
}
Set::Set(Node* p){
list = p;
}
Set::Node* Set::unionMerge(const Node *p, const Node *q){
// to debug, I return nullptr
return nullptr;
}
const Set operator+(const Set& a, const Set& b){
//error: ‘unionMerge’ was not declared in this scope
return Set(unionMerge(a.list,b.list));
Set::Node *p = unionMerge(a.list,b.list);
Set s;
s.list = p;
return s;
}
operator+() is not a member of Set (friends are not members), so if you want to access a static member of Set you have to qualify it:
return Set(Set::unionMerge(a.list,b.list));
Related
I have to make a linked list. I'm not sure if I'm doing this right first of all. But basically the project says I'm not allowed to make a .cpp file but I have to create 4 inline statements through the .h file.
class Queue{
private:
struct QueueNode{
int size;
std::string party;
QueueNode *next;
};
QueueNode *front;
QueueNode *rear;
public:
// Constructor
Queue();
// Destructor
~Queue();
// Queue operations
std::string getPartyName() const { return party; } // This and next 3 lines give error with the private variables
int getSize() const { return size; }
void setPartyName(std::string p) const{ party = p; }
void setSize(int s) const{ size = s; }
};
You are halfway there. You need to declare the functions in the header file, as you have done.
The missing step is that you need to not define the functions within the class body but instead define them below the class declaration using the class name with the scope resolution operator and the inline operator.
The other piece you are missing is that you are declaring functions in your Queue class that are likely meant for your QueueNode struct.
class Queue{
private:
struct QueueNode{
int size;
std::string party;
QueueNode *next;
};
QueueNode *front;
QueueNode *rear;
public:
// Constructor
Queue();
// Destructor
~Queue();
// Queue operations
std::string getPartyName( const QueueNode * const node ) const;
int getSize( const QueueNode * const node ) const;
void setPartyName( QueueNode & out_node, std::string & p);
void setSize( QueueNode & out_node, int s);
};
inline std::string Queue::getPartyName( const QueueNode * const node ) const
{
return node->party;
}
inline int getSize( const QueueNode * const node ) const {
return node->size;
}
inline void Queue::setPartyName( QueueNode & out_node, std::string & p) {
out_node.party = p;
}
inline void Queue::setSize( QueueNode & out_node, int s) {
out_node.size = s;
}
It isn't clear what nodes you intend to set these values for, so I'll fill in the functions with some assumptions.
Either way I think you get the point. If you want to define inline functions within a header class, you cannot define the body within the class itself. You must declare it inline, which is a compiler suggestion, outside the body of the class. I know I didn't complete define the functionality of a linked list, I will leave that to you. But, this should answer the inline question.
Everything was working before I introduced templates to my code
EDIT:
Here is the problem to which I was able to narrow it down, thanks to your tips:
In file included from main.cpp:4:
stack.cpp: In member function void Stack<TYPE>::push(Stack<TYPE>&, TYPE)':
stack.cpp:35: error:node' is not a type
I wonder if a similar problem could appear later in the pop function, but it seems like it does not.
I'm confused as to why it seems to insist that node is not a type.
EDIT#2:
this statement in the main.cpp file is now causing trouble. I have moved all the definitions out of stack.cpp to stack.h. After this Stack<int> list;my compiles says Segmentation fault (core dumped).
stack.h:
#include <iostream>
using namespace std;
template <typename TYPE>
struct node {
TYPE data;
node<Type> *next;
node(){
data = NULL;
next = NULL;
}
~node(){
if (data!=0)
delete next;
}
explicit node(int i){
data = i;
}
};
template <typename TYPE>
class Stack {
private:
node<TYPE> *top;
void init();
public:
Stack(); // default constructor
virtual ~Stack(); // destructor
bool empty();
void push(Stack&,TYPE);
TYPE pop(Stack&);
int peek();
void clear();
ostream& printf(ostream&, node<TYPE> *);
ostream& print(ostream&);
ostream& sequentialPrint(Stack&,ostream&);
ostream& reversePrint(Stack&,ostream&);
friend ostream& operator<<(ostream&, Stack&);
};
stack.cpp:
template <typename TYPE>
void Stack<TYPE>::push(Stack<TYPE> &s, TYPE i) {
node<TYPE> * n = new node(i);
n->next = top;
top = n;
}
template <typename TYPE>
TYPE Stack<TYPE>::pop(Stack<TYPE> &s){
if (empty()) {
cerr<<"Stack is empty \n";
}
TYPE temp = s.top->data;
top = top->next;
return temp;
}
friend ostream& operator<<(ostream&, Stack&); is not needed
you can't define template methods in cpp file. Every element of template which is template parameter depended must be defined in header file.
Node is a struct which defined in a class List_set private.
struct List_set::Node
{
element_t str_l;
link_t next_ptr ;
static link_t* find(link_t* current, element_t string_t);
Node();
};
List_set::List_set():link_(nullptr)
{}
List_set::Node::Node():next_ptr{0}
{}
I want to use a constructor to initialize the Node, however the compiler always report an error:
no matching constructor for initialization of 'list_set::List_set::Node'
Can you please help to figure it out?
The next is the definition of class List_set hope it can provide some reference.
class List_set
{
public:
using element_t = std::string;
List_set();
List_set(std::initializer_list<element_t>);
bool is_empty() const;
size_t size() const;
bool contains(const element_t&) const;
void insert(element_t);
private:
struct Node;
using link_t = std::shared_ptr<Node>;
link_t link_;
};
I have been trying for quite a while to figure out how to get pointers for my nodes to merge two linked lists. I have to do it with the following function definition (NB I have found plenty of answers when the pointers are arguments to a member function but in my case I have to do it with a reference. Any pointers :) would be appreciated. NB I know that my code is not yet fully developed but I really need to get pointers to both OrderedList objects to make it work. ie if I can get two pointers to the _head of each ordered link list I think I can generate the code.
Any help to get a valid reference for curr and mov would be appreciated.
OrderedList operator+(OrderedList&second) // merges two OrderedLists
{
int i=1;
int j=1;
Node* prev = NULL;
Node* curr = this->_head;
Node* mov = second._head;
while (curr!=NULL and mov!=NULL)
{
if (this->operator [](i)<= second->operator [](j) or mov->next == NULL)
{
i++;
}else{
prev->next = mov;
mov = mov->next;
mov = curr;
}
}
return OrderedList;
}
so this is for an assignment so I want to learn how to do it correctly. I am not just interested in answers but mainly understanding. I am new to c++. So basically we have been given a header file and have to make all the member and friend functions work. I am stuck on how to make this operator function work. So the header file is:
#ifndef ORDEREDLIST_H_
#define ORDEREDLIST_H_
#include <iostream>
using namespace std;
class Node
{
public:
double item; // data item
Node *next; // pointer to next node
};
class OrderedList
{
// friend operator functions
friend ostream &operator<<(ostream &, const OrderedList &);
friend istream &operator>>(istream &, OrderedList &);
public:
// constructors
OrderedList():_head(NULL),_size(0) {};
OrderedList(const OrderedList &); // copy constructor
// destructor
~OrderedList();
// operator functions
OrderedList operator+(OrderedList&); // merges two OrderedLists
double operator[](int) const; // subscript operator returns rvalue
const OrderedList &operator=(const OrderedList &); // assignment
void insert(double); // inserts an item
bool remove(int); // remove i th item
void pop(); // pop the first item
//void printlist(Node*);
private:
Node *_head;
int _size;
};
#endif /* ORDEREDLIST_H_ */
Can I only get a pointer if the overloaded operator is a friend of OrderedList or if it is a member function? That is what I am seeing but I am very new to C++.
Hi I am trying to implement a linked list using templates and ADT. At the moment I have two classes. One is an iterator for linked list and the other is the base class for linked lists that I will use to derive linked list classes from.
When trying to implement two functions that will give me an iterator at the start and end of the list respectivly I get compile error saying "ISO C++ forbids declaration of 'linkedListIterator' with no type"
Here is the code for the definition of the iterator:
#ifndef LINKEDLISTITERATOR_H
#define LINKEDLISTITERATOR_H
#include <stddef.h> //for NULL
#include "nodetype.h"
#include "linkedlisttype.h"
template <class Type>
class linkedListIterator
{
public:
linkedListIterator();
linkedListIterator(nodeType<Type> *ptr);
Type operator*();
linkedListIterator<Type> operator++();
bool operator==(const linkedListIterator<Type>& right) const;
bool operator!=(const linkedListIterator<Type>& right) const;
private:
nodeType<Type> *current;
};
#endif // LINKEDLISTITERATOR_H
Here is the code for the definition of the node Type
#ifndef NODETYPE_H_INCLUDED
#define NODETYPE_H_INCLUDED
//Definition of the node
template <class Type>
struct nodeType
{
Type info;
nodeType<Type> *link;
};
#endif // NODETYPE_H_INCLUDED
Here is the definition of the linkedlist base class:
#ifndef LINKEDLISTTYPE_H
#define LINKEDLISTTYPE_H
#include "nodetype.h"
#include "linkedlistiterator.h"
//Definition of linked list
template <class Type>
class linkedListType
{
public:
const linkedListType<Type>& operator=
(const linkedListType<Type>&);
void initializeList();
bool isEmptyList() const;
void print() const;
int length() const;
void destroyList();
Type front() const;
Type back() const;
virtual bool search(const Type& searchItem) const = 0;
virtual void insertFirst(const Type& newItem) = 0;
virtual void insertLast(const Type& newItem) = 0;
virtual void deleteNode(const Type& deleteItem) = 0;
// this is where the error comes
linkedListIterator<Type> begin();
// and here as well
linkedListIterator<Type> end();
linkedListType();
linkedListType(const linkedListType<Type>& otherList);
~linkedListType();
protected:
int count;
nodeType<Type> *first;
nodeType<Type> *last;
private:
void copyList(const linkedListType<Type>& otherList);
};
#endif // LINKEDLISTTYPE_H
I am new to templates and ADT so trying to wrap my mind around this. Any help will be most appreciated please.
You have two headers which each try to include each other. The result is that, if you #include "linkedlistiterator.h", the definition of linkedListType appears before that of linkedListIterator; hence the error due to linkedListIterator not being declared at that point.
In this case, it looks like the iterator type does not depend on the list type at all, so you can simply remove the #include "linkedlistlype.h" from "linkedlistiterator.h".
Seems that both linkedlisttype.h and linkedlistiterator.h include each other.
That indicates rather close coupling in your mind. You probably want to have LinkedList<T> class and nested LinkedList<T>::Iterator class.