Professional Documents
Culture Documents
Linked List Double (!!!)
Linked List Double (!!!)
#DynamicStructure
[[Linked List]] [[Linked List.Clear]] [[Linked List.Final]] [[Linked List Double
(!!!)]]
---
# Theory
---
## Overview
## Double-linked list
![[Pasted image 20230317180128.png]]
## Node Class
A node class is needed to represent each element in the list. The node class will
contain the data and two pointers - one to the next node and one to the previous
node. Here's an example implementation:
```cpp
template<typename T>
class Node {
public:
T data;
Node<T>* next;
Node<T>* prev;
Node(T val) {
data = val;
next = nullptr;
prev = nullptr;
}
};
```
## List Class
The list class will contain a pointer to the head and tail of the list, as well as
the size of the list. Here's an example implementation of the list class:
```cpp
template<typename T>
class DoubleLinkedList {
public:
DoubleLinkedList() {
head = nullptr;
tail = nullptr;
size = 0;
}
void deleteFront();
void deleteBack();
void deleteAt(int index);
void printList();
int getSize();
private:
Node<T>* head;
Node<T>* tail;
int size;
};
```
## Insertion
![[Pasted image 20230319143258.png]]
To insert an element in a double-linked list, we must create a new node and update
the pointers of the adjacent nodes. Here are three methods for inserting an element
into a double-linked list:
```cpp
template<typename T>
void DoubleLinkedList<T>::insertFront(T val) {
Node<T>* newNode = new Node<T>(val);
if (head == nullptr) {
head = newNode;
tail = newNode;
}
else {
newNode->next = head;
head->prev = newNode;
head = newNode;
}
size++;
}
template<typename T>
void DoubleLinkedList<T>::insertBack(T val) {
Node<T>* newNode = new Node<T>(val);
if (tail == nullptr) {
head = newNode;
tail = newNode;
}
else {
tail->next = newNode;
newNode->prev = tail;
tail = newNode;
}
size++;
}
template<typename T>
void DoubleLinkedList<T>::insertAt(T val, int index) {
if (index < 0 || index > size) {
cout << "Invalid index" << endl;
return;
}
if (index == 0) {
insertFront(val);
return;
}
if (index == size) {
insertBack(val);
return;
}
size++;
}
```
### Deletion
```cpp
template<typename T>
void DoubleLinkedList<T>::deleteFront() {
if (head == nullptr) {
cout << "List is empty" << endl;
return;
```
---
# Implementation
```cpp
#include <iostream>
template<typename T>
class List {
public:
List() {
size = 0;
head = nullptr;
tail = nullptr;
}
~List() {
clear();
}
return current->data;
}
private:
template<typename T>
class Node {
public:
Node(T data = T(), Node* prev = nullptr, Node* next = nullptr) {
this->data = data;
this->prev = prev;
this->next = next;
}
T data;
Node* prev;
Node* next;
};
int size;
Node<T>* head;
Node<T>* tail;
};
template<typename T>
void List<T>::PushFront(T data) {
if (IsEmpty()) {
head = tail = new Node<T>(data);
}
else {
Node<T>* newHead = new Node<T>(data, nullptr, head);
head->prev = newHead;
head = newHead;
}
size++;
}
template<typename T>
void List<T>::PushBack(T data) {
if (IsEmpty()) {
head = tail = new Node<T>(data);
}
else {
Node<T>* newTail = new Node<T>(data, tail, nullptr);
tail->next = newTail;
tail = newTail;
}
size++;
}
template<typename T>
void List<T>::InsertAt(T data, int index) {
if (index < 0 || index > size) {
throw std::out_of_range("Index out of range");
}
if (index == 0) {
PushFront(data);
return;
}
if (index == size) {
PushBack(data);
return;
}
template<typename T>
void List<T>::RemoveAt(int index) {
if (index < 0 || index >= size) {
throw std::out_of_range("Index out of range");
}
if (index == 0) {
PopFront();
return;
}
if (index == size - 1) {
PopBack();
return;
}
current->prev->next = current->next;
current->next->prev = current->prev;
delete current;
size--;
```