A linked-list is a type of data structure that is made up of elements called nodes. Unlike an array, where elements are stored in contagious memory locations, the nodes in a linked-list are scattered in memory. The nodes are connected through the use of pointers, each node contains a reference to the location of the next node in the list.
There are various types of linked lists. In this article we will focus on doubly-linked lists.
In a doubly linked list, each node contains a reference to both the next node and the previous node. This allows for efficient traversal of the list in both forward and backward directions.
In most practical cases, doubly-linked lists are used for implementing other data structures such as queues. In the next parts we will learn how to implement a double-ended queue using doubly-linked list.
The Node class
To represent a node in a doubly linked lists, we will create a non-public class called _Node
with the following attributes:
_element
: Will store the value of the node._next
: Will store a reference to the next node in the list._prev
: Will store a reference to the previous node in the list.
The implementation of the _Node class is as shown below
Linked double-ended Queue
A double-ended queue, popularly known as deque(pronounced as "deck"), is a type of queue in which elements can be added or removed from either side. These makes it more versatile than a regular queue in which elements can only be added in one end and removed from the other.
A Double ended queue typically supports the following operations.
insert_front(e) |
Add element e at the front of the queue. |
insert_back(e) |
Add element e at the back end of the queue. |
remove_front() |
remove and return the element at front. |
remove_back() |
remove and return the element at back. |
front() |
Return the element at the front of the queue without removing it. |
back() |
Return the element at the back without removing it. |
is_empty() |
Return True if the queue is empty, otherwise False. |
len() |
Return the number of elements in the queue. |
In the following parts we will go on to implement the LinkedDeque
class to represent a double-ended queue using doubly-linked list.
Implement the basic structure
In this part we will implement the basic structure of the LinkedDeque
class. The _Node
class will be implemented as a non-public subclass.
We will use sentinel/dummy nodes, _head
and _tail
at the front and the back of the list respectively, doing this simplifies the insertion and removal operations, as we will see in a while. The front sentinel will always point to the beginning of the list, and the back sentinel will always point to the end of the list.
Implementing the __len__()
method makes it possible to use the builtin len()
function to check the number of elements in the deque
.
Implement front()
and back()
In this part we will implement front()
and back()
methods. The methods will raise an error if the deque
is empty.
Implement insert_front()
and insert_back()
In this section we will implement the insert_front()
and insert_back()
methods. However to prevent redundancy, we will implement a more generic non-public method, _insert_between()
which we will call within the insert_front()
and insert_back()
methods.
The _insert_between()
method in the above example, helps us to avoid repetition when implementing the insert_front()
and insert_back()
methods. By using _insert_between(), we are able to pass in the correct parameters to specify where the new node should be inserted without having to duplicate the code for creating and updating the pointers.
The implementation and usefulness of the _insert_between()
method above illustrates the importance of using sentinel nodes.
Implement remove_front()
and remove_back()
In this final step we will implement the remove_front() and remove_back()
methods. Like in previous section, we will use a non-public methods _remove_node()
that will be called by the two public methods.
Combining all the LinkedDeque
segments
After Combining all the previous segments we get:
Using the class
front: Javascript
back: PHP
Removing from back:
PHP
C++
Python
Java
Javascript
You can experiment with the class more on your own.