This is a thread I started from here. I organized my code to make it more organized. Everything works well, but I have not made all the changes from the last link (namely namespace since I am exactly sure why or what to do).
Overall I just wanted to show my generic single linked list I made and see if there are any errors or improvements I should make.
Here is my header file:
#ifndef SingleLinkedLists_h
#define SingleLinkedLists_h
#include <iostream>
template <class T>
class SingleLinkedLists {
private:
struct Node {
T data;
Node* next;
};
Node* head;
Node* tail;
public:
// Constructors
SingleLinkedLists() : head(nullptr), tail(nullptr) {}
SingleLinkedLists(SingleLinkedLists const& value);
~SingleLinkedLists();
// Overloaded operators
SingleLinkedLists& operator=(SingleLinkedLists const& rhs);
friend std::ostream& operator<<(std::ostream& str, SingleLinkedLists<T>& data) {
data.display(str);
return str;
}
// Operators in Single Linked List
void swap(SingleLinkedLists& other) noexcept;
void createNode(const T& theData);
void createNode(T&& theData);
void display(std::ostream& str) const;
void display() const;
void insertHead(const T& theData);
void insertTail(const T& theData);
void insertPosition(int pos, const T& theData);
void deleteHead();
void deleteTail();
void deletePosition(int pos);
bool search(const T& x);
};
template <class T>
SingleLinkedLists<T>::SingleLinkedLists(SingleLinkedLists const& value) : head(nullptr), tail(nullptr) {
for(Node* loop = value->head; loop != nullptr; loop = loop->next) {
createNode(loop->data);
}
}
template <class T>
SingleLinkedLists<T>::~SingleLinkedLists() {
while(head != nullptr)
deleteHead();
}
template <class T>
SingleLinkedLists<T>& SingleLinkedLists<T>::operator=(SingleLinkedLists const& rhs) {
SingleLinkedLists copy(rhs);
swap(copy);
}
template <class T>
void SingleLinkedLists<T>::swap(SingleLinkedLists& other) noexcept {
using std::swap;
swap(head, other.head);
swap(tail, other.tail);
}
template <class T>
void SingleLinkedLists<T>::createNode(const T& theData) {
Node* newNode = new Node;
newNode->data = theData;
newNode->next = nullptr;
if(head == nullptr) {
head = newNode;
tail = newNode;
newNode = nullptr;
}
else {
tail->next = newNode;
tail = newNode;
}
}
template <class T>
void SingleLinkedLists<T>::createNode(T&& theData) {
Node* newNode = new Node;
newNode->data = std::move(theData);
newNode->next = nullptr;
if(head == nullptr) {
head = newNode;
tail = newNode;
newNode = nullptr;
}
else {
tail->next = newNode;
tail = newNode;
}
}
template <class T>
void SingleLinkedLists<T>::display(std::ostream& str) const {
for(Node* loop = head; loop != nullptr; loop = loop->next) {
str << loop->data << "\t";
}
str << "\n";
}
template <class T>
void SingleLinkedLists<T>::display() const {
Node* newNode = head;
while(newNode != nullptr) {
std::cout << newNode->data << "\t";
newNode = newNode->next;
}
}
template <class T>
void SingleLinkedLists<T>::insertHead(const T& theData) {
Node* newNode = new Node;
newNode->data = theData;
newNode->next = head;
head = newNode;
}
template <class T>
void SingleLinkedLists<T>::insertTail(const T& theData) {
Node* newNode = new Node;
newNode->data = theData;
tail->next = newNode;
tail = newNode;
}
template <class T>
void SingleLinkedLists<T>::insertPosition(int pos, const T& theData) {
Node* previous = new Node;
Node* current = head;
Node* newNode = new Node;
for(int i = 1; i < pos; i++) {
previous = current;
current = current->next;
}
newNode->data = theData;
previous->next = newNode;
newNode->next = current;
}
template <class T>
void SingleLinkedLists<T>::deleteHead() {
Node* old = head;
head = head->next;
delete old;
}
template <class T>
void SingleLinkedLists<T>::deleteTail() {
Node* previous = nullptr;
Node* current = head;
while(current->next != nullptr) {
previous = current;
current = current->next;
}
tail = previous;
previous->next = nullptr;
delete current;
}
template <class T>
void SingleLinkedLists<T>::deletePosition(int pos) {
Node* previous = new Node;
Node* current = head;
for(int i = 1; i < pos; i++) {
previous = current;
current = current->next;
}
previous->next = current->next;
}
template <class T>
bool SingleLinkedLists<T>::search(const T &x) {
Node* current = head;
while(current != nullptr) {
if(current->data == x)
return true;
current = current->next;
}
return false;
}
#endif /* SingleLinkedLists_h */
Here is the main.cpp file that tests the functions:
#include <iostream>
#include "SingleLinkedLists.h"
int main(int argc, const char * argv[]) {
SingleLinkedLists<int> obj;
obj.createNode(2);
obj.createNode(4);
obj.createNode(6);
obj.createNode(8);
obj.createNode(10);
std::cout<<"\n--------------------------------------------------\n";
std::cout<<"---------------Displaying All nodes---------------";
std::cout<<"\n--------------------------------------------------\n";
std::cout << obj << std::endl;
std::cout<<"\n--------------------------------------------------\n";
std::cout<<"-----------------Inserting At End-----------------";
std::cout<<"\n--------------------------------------------------\n";
obj.insertTail(20);
std::cout << obj << std::endl;
std::cout<<"\n--------------------------------------------------\n";
std::cout<<"----------------Inserting At Start----------------";
std::cout<<"\n--------------------------------------------------\n";
obj.insertHead(50);
std::cout << obj << std::endl;
std::cout<<"\n--------------------------------------------------\n";
std::cout<<"-------------Inserting At Particular--------------";
std::cout<<"\n--------------------------------------------------\n";
obj.insertPosition(5,60);
std::cout << obj << std::endl;
std::cout<<"\n--------------------------------------------------\n";
std::cout<<"----------------Deleting At Start-----------------";
std::cout<<"\n--------------------------------------------------\n";
obj.deleteHead();
std::cout << obj << std::endl;
std::cout<<"\n--------------------------------------------------\n";
std::cout<<"----------------Deleting At End-----------------";
std::cout<<"\n--------------------------------------------------\n";
obj.deleteTail();
std::cout << obj << std::endl;
std::cout<<"\n--------------------------------------------------\n";
std::cout<<"--------------Deleting At Particular--------------";
std::cout<<"\n--------------------------------------------------\n";
obj.deletePosition(4);
std::cout << obj << std::endl;
std::cout << std::endl;
obj.search(8) ? printf("Yes"):printf("No");
return 0;
}
As an aside I want to thank everyone who has contributed to improving my generic single linked list, I really appreciate the help and expertise that strengthened my understanding of data structures and C++.
I organized my code to make it more organized.The perfect description for any refactoring. \$\endgroup\$