Module 2 Linked List
Module 2 Linked List
Lists
• Content
class Node
{
int data;
Node next;
public // A simple node of a linked
Node(int list
data)
{
this.data = data;
this.next = null;
}
Linked Lists
• Linked list is a dynamic linear data structure whose size increases when
add the elements, and decreases when remove the elements from the list.
• Nodes makes linked lists.
• Nodes are structures made up of data and a pointer (Link) to another
node.
• Usually the pointer is called next.
• First node referred as the head of the list.
• The last node in the list is the tail that points to NULL.
Linked List 5
Linked list is a linear data structure that includes a series of connected nodes.
Linked list can be defined as the nodes that are randomly stored in the memory.
A node in the linked list contains two parts, i.e., first is the data part and second
is the address part. The last node of the list contains a pointer to the null.
Linked list can be represented as the connection of nodes in which each node
points to the next node of the list.
As per the above illustration, following are the important points to be considered.
Linked List contains a link element called first.
Each link carries a data field(s) and a link field called next.
Each link is linked with its next link using its next link.
Last link carries a link as null to mark the end of the list.
Types of Linked List 6
Dynamic data structure - The size of the linked list may vary according to the
requirements. Linked list does not have a fixed size.
Insertion and deletion - Unlike arrays, insertion, and deletion in linked list is
easier. Array elements are stored in the consecutive location, whereas the
elements in the linked list are stored at a random location. To insert or delete an
element in an array, we have to shift the elements for creating the space.
Whereas, in linked list, instead of shifting, we just have to update the address of
the pointer of the node.
Memory efficient - The size of a linked list can grow or shrink according to the
requirements, so memory consumption in linked list is efficient.
Implementation - We can implement both stacks and queues using linked list.
Disadvantages of Linked Lists 8
Memory usage - In linked list, node occupies more memory than array. Each node of the
linked list occupies two types of variables, i.e., one is a simple variable, and another one is
the pointer variable.
Traversal - Traversal is not easy in the linked list. If we have to access an element in the
linked list, we cannot access it randomly, while in case of array we can randomly access it by
index. For example, if we want to access the 3rd node, then we need to traverse all the nodes
before it. So, the time required to access a particular node is large.
Reverse traversing - Backtracking or reverse traversing is difficult in a linked list. In a
doubly-linked list, it is easier but requires more memory to store the back pointer.
Singly Linked List
• Each node has only one link part
• Each link part contains the address of the next node in the list
• Link part of the last node contains NULL value which signifies the end of
the node
• Schematic representation of singly-linked list (SLL):
head
a b c
d
• Each node contains a value(data) and a pointer to the next node in the list
• head is the header pointer that points at the first node in the list
Basic Operations on a Singly Linked List
• Creating a List
• Inserting an element in a list
• Deleting an element from a list
• Searching a list
• Reversing a list
• Display the list
Creating a node
public class SinglyLinkedList
{
//create a node
class Node
{
int data;
Node next;
public // A simple node of a linked list
Node(int
data)
{
this.data = data;
this.next = null;
}
}
//defining the head and tail
public Node head = null; //initialised to NULL at beginning
public Node tail = null;
} newList.display();
} //Display the data
Singly Linked List 15
A singly linked list is the simplest type of linked list in which every node
contains some data and a pointer to the next node of the same data type.
Insertion Operation
Adding a new node in linked list is a more than one step activity.
First, create a node using the same structure and find the location where it has to
be inserted
Inserting the node
There are 3 cases here:-
• Insertion at the beginning
• Insertion at the end
• Insertion after a particular node (in
between)
Insert node at the beginning
Need to do 2 steps :-
• Make the next pointer of the newNode to be inserted point to the next node (40) of the
node
(20) after which you want to insert the node.
• Make the next pointer of the node (20) points to the newNode (30) to be inserted.
Insert at a specific location of the list 24
Inserting after an element
public void insert_After(Node prev_node, int data)
{
// Check the Node is null
if (prev_node == null)
{
System.out.println("The given previous node cannot be null");
}
Node newNode = new Node(data); ///create the Node & add the data*/
newNode.next = prev_node.next; // Make next of new Node as next of prev_node
prev_node.next = newNode; // make next of prev_node as new_node
}
Deletion 26
Deletion is also a more than one step process, here first locate the target node to
be removed
head
pointer
• Make the next pointer of the node previous to the node being deleted,
point
to the successor node of the node to be deleted.
• Then delete the node.
head
pointer node3
node1 node2
To be
Deleting a particular node
void deleteNode(int position)
{
if (head == null) // When node to be deleted is head node
{
System.out.println(“List is empty "); }
Node temp = head;
if (position == 0) {
head = temp.next;
// Change head
} i = 0; temp != null && i < position – 1; i++) // Find previous node of the node to be deleted
for (int
temp = temp.next;
if (temp == null || temp.next == null) // If position is more than number of nodes
System.out.println(“Given postion is not in the List");
// Node temp.next is the node to be deleted and Store pointer to the next of node to be deleted
Node beside_node = temp.next.next;
temp.next = beside_node; // Unlink the deleted node from list
}
Searching data in SLL
2. Various techniques can be used for searching like linear search or binary
search
where binary search is more efficient in case of Arrays
3. But in case of linked list since random access is not available it would
become
complex to do binary search in it.
r
hea p q NUL
d L
p q r
hea
NUL d
head
Reversing a linked list Example
tail
100 112
100 104 108 112
2 104 4 108 6 112 8 NULL
current next
head 100 104
tail
100 100 104 108 112 112
prev 2 104 4 108 6 8 NULL
NULL 112
tail head
100 100 104 108 112 112
NULL
2 4 100 6 104 8 108
Reversing a linked list
Node reverse(Node head) {
current.next = prev;
if(head==NULL)
prev = current;
{
current = next;
System.out.print(“List is }
empty“);
}
head=prev;
Node prev = null;
return head
Node current = head;
}
Node next = null;
while (current !=
null) {
Arrays Vs Linked Lists
Arrays Linked list
previous next
Double Linked List 42
In a single linked list, every node has a link to its next node in the sequence. So,
we can traverse from one node to another node only in one direction and we can
not traverse back. We can solve this kind of problem by using a double linked
list.
In a double linked list, every node has a link to its previous node and next node.
So, we can traverse forward by using the next field and can traverse backward
by using the previous field. Every node in a double linked list contains three
fields
Structure of Node in Doubly Linked
class Node List
{
int data;
int key;
Node
prev;
Node // A simple node of a linked list
next;
public
Node(in
t data)
{
this.data = previous Data next
data; this.prev
DLL’s compared to SLL’s
Advantages: Disadvantages:
Can be traversed in Requires more space
either direction (may be List manipulations are
essential for some programs) slower (because more links
Some operations, such must be changed)
as deletion and inserting Greater chance of having
before a node, become easier bugs (because more links
must be manipulated)
Doubly Linked List with Sentinel
node
Example:
Double Linked List 46
Example
Basic Operations on a Doubly Linked List
• Insertion − add an element at the beginning of the list.
• Deletion − delete an element at the beginning of the list.
• Insert at end − add an element in the end of the list.
• Insert after − add an element after an item of the list.
• Delete − delete an element from the list using key.
• Display forward − display the list in forward direction.
• Display backward − display the list in backward direction.
Inserting at beginning
• The new node is always added before the head (start) of the given Linked
List.
• Newly added node becomes the new head (start) of DLL
head
tail
A B C
head tail
A B C
X
Inserting at beginning
public void insert_begin( int data)
{ Node newNode = new
Node(data); if(head==NULL){
head= newNode;
tail= newNode;
head.prev =
} null;
else {
tail.next
head.prev= =null;
newNode; //update head prev link
newNode.next = head; //point it to head
newNode.prev = null;
head = newNode; //point head to newNode
}
Inserting at the end
• Linked List is typically represented by the head (start).
• So, traverse the list till end and then change the next of last node to new
node.
A B C
head tail
A B C tail
head p
D
p
A B C D
head tail
Inserting at the end
public void insert_end(int data)
{ Node newNode = new
Node(data); if(head==null){
head= newNode;
tail= newNode;
}
else {
Node last = head
while (last.next != // traverse till the last
null) node
last.next last =
= newNode; //add newNode as end node
last.next;
newNode.prev = last;
}
last = newNode;
}
Inserting after a node
• Making next and previous pointer of the node to be inserted accordingly
• Adjusting the next and previous pointers of the nodes between the new node
accordingly
temp
A B C
head tail
temp
A B C
head q tail
X
q
temp
A B X C
head tail
Inserting after a node
public void insert_position(int position, int data)
{ int size = 0;
Node newNode = new Node(data);
if(head == null) {
System.out.println("This location is
not available");
}
else {
if(position == size+1){
last = newNode;
}else if(position == 1)
{ insert_begin(newNod
e);
}else{
Inserting after a node
for(int i = 1; i < position-1; i++){
current = current.next;
}
temp = current.next;
temp.prev = current;
current.next = newNode; //newNode inserted between current and
newNode.prev = current; temp
newNode.next = temp;
temp.prev = newNode;
}
size+
+;
}
}
Deletion in Doubly Linked
• List the first node
Deleting
head tail
7 9 4
Delete an element at beginning
void del_first()
{
if(head == null) //Checks if the list is empty
{
System.out.println("List is empty");
}
if(head.next == null){
tail = null;
} //If the list contains only one node. then, it removes both head and tail will point to
null
else {
head.next.prev= null;
}
head = head.next
}
Delete an element at end
• Assign the value of tail (address of the last element) to a temporary variable
(temp)
• Further there are two cases:
1. If there is only one element in the existing list, set both head and tail to
NULL.
2. 2.Assign
If there isthe
more than one
address element
of the secondinlast
thenode
list then
to tail
hea 1.Assign NULL to the next pointer field of the second last node. tai
d l
12 73 42
91
hea tai
d l
12 73 91 42
hea tai
d l
12 73 91
Delete an element at end
public void delete_end()
{
Node temp = last;
last = head;
if(head.next == null )
{
head = null;
}
else {
while(last.next !
= null)
last =
last.n
ext;
last.prev.next =
null;
}
Deleting a particular node
head tail
a b c
head tail
a c
Deleting a particular node
void del_at(int position)
{
if(head == null || position>size) {
System.out.println("\n" +position +"position is not available\
n");
}
else {
if(position == 1){
del_first();
size--;
//Decrement the
size of DDL
}else if(position == size)
{ delete_end();
Deleting a particular node
Node current = head;
//Iterate till current points to specified position
for(int i = 1; i < position; i++){
current = current.next;
}
current.next.prev = current.prev; //Delete node pointed by
current
current.prev.next = current.next;
}
System.out.println(position +" node is deleted");
}
}
APPLICATIONS OF LINKED LIST
1.Applications that have an Most Recently Used list (a linked list of file names)
2. The cache in web browser that allows to hit the BACK button (a linked list of
URLs)
4.A stack, hash table, and binary tree can be implemented using a doubly linked
list.
Applications of Linked List 64
A( x ) m 1
a m 2 . . . a 0 x e 0
x e m 1
x e m 2
a
Representation
class Node
{ int coef;
int exp;
Node next;
}
a 2x 8 1
3 xa 1 4
3 14 2 8 1 0 null
b 8 3x 1 0
10 x
6
x
b
1 4
8 14 -3 10 10 6 null
Polynomial Manipulation 67
• Résultant Polynamial
• To Perform the addition of two long integers, the following steps need to be
followed
– Traverse the two linked lists in parallel from left to right.
– During traversal, corresponding digits and a carry from prior digits sum are
added, then stored in the new node of the resultant linked list.
• The first positive long integer 543467 is represented using a linked list whose first
node is pointed by NUM1 pointer.
• The second positive long integer 48315 is represented using the second linked list whose
first node is pointed by NUM2 pointer.
• These two numbers are stored in the third linked list whose first node is pointed to by the
RESULT pointer.
• Image viewer – Previous and next images are linked and can be accessed by the
next and previous buttons.
• Previous and next page in a web browser – We can access the previous and next
URL searched in a web browser by pressing the back and next buttons since they
are linked as a linked list.
• Music Player – Songs in the music player are linked to the previous and next
songs. So you can play songs either from starting or ending of the list.
• Circular lists are useful in applications to go around the list repeatedly. For
example, when multiple applications are running on a PC, it is common for the
operating system to put the running applications on a list and then cycle through
them, giving each of them a slice of time to execute, and then making them wait
while the CPU is given to another application. It is convenient for the operating
system to use a circular list so that when it reaches the end of the list it can cycle
around to the front of the list.
next
Data
(Link / address to Next Node)
class Node
{
int data;
Node next;
public // A simple node of a linked
Node(int list
data)
{
this.data = data;
this.next = null;
}
Circular Linked List
• Last node references the first node
• Every node has a successor
• No node in a circular linked list contains NULL
Circular Linked Lists
• A Circular Linked List is a special type of Linked List
• It supports traversing from the end of the list to the beginning
by making the last node point back to the head of the list
• A tail pointer is often used instead of a head / start pointer
20 30 45 57 79
tail
Circular Linked List
Without Header Node
In single linked list, every node points to its next node in the sequence and the
last node points NULL. But in circular linked list, every node points to its next
node in the sequence but the last node points to the first node in the list.
A circular linked list is a sequence of elements in which every element has a
link to its next element in the sequence and the last element has a link to the
first element.
That means circular linked list is similar to the single linked list except that the
last node points to the first node in the list
Circular Linked List Operations
Head
Afte
r Insertion
H
ead
Insert at beginning in circular list
• The first Node is the Head when new Linked List is instantiated, it just has
the
Head, which is Null.
• Else, the Head holds the pointer to the first Node of the List.
• When we want to add any Node at the front, we must make the head point to
it.
And the Next pointer of the newly added Node, must point to the
•
previous Head, whether it be NULL(in case of new List) or the pointer to the
first Node of the List.
• The previous Head Node is now the second Node of Linked List, because
the
Insert at beginning in circular list
Before Insertion
Head
After Insertion
Head
Insert at end of circular list
• If the Linked List is empty then we simply, add the new Node as the
Head of the Linked List.
• If the Linked List is not empty then we find the last node, and make it'
next to the new Node.
• Then make the next of the Newly added Node point to the Head of the
List.
Insert at end of circular list
void add_end(int data) Node temp = head;
{ while (temp.next != head)
Node newNode = new Node(data); { temp = temp.next;
if (head== null) { }
head = newnode; temp.next = newNode; // Add new node at end
tail = newNode; newNode.next = head;
tail.next = head; }
}
Inserting after an element in circular lists
Before Insertion
Head
After Insertion
Head
Inserting after an element in circular
lists
void insert_after(int data, int position)
{ Node newNode = new
Node(data); if(head == null){
head = newNode;
tail = newNode;
newNode.next =
head;
}
else{
Node temp,
current;
temp = head;
After Deletion
Delete at beginning in circular lists
void delete_first( )
{
Node temp = head;
if(head.next == null)
{
head = null;
}
head = head.next;
}
Delete after a node in circular lists
Before Deletion
After Deletion
Delete after a node in circular lists
• The delete after and insert after functions of the linear lists and the circular
lists
are almost the same.
void del_after(int
position){ Node current,
temp;
if(head == null) {
System.out.print(“Em
pty list”);
}
else {
if( head != tail )
{ temp = head;
Delete after a node in circular lists
for(int i = 0; i < position; i++){
current = temp;
temp =
temp.next;
}
if(current != null)
{ current.next =
temp.next;
temp = null;
//Delete temp;
} else { //Current points to null then head and tail will point to next to
temp. head = tail = temp.next;
Delete after a node in circular lists
}
//If list contains only one element then both head and tail will
point to null else {
head = tail = null;
}
}
size--;
}
Delete end node in circular
lists Before Deletion
After Deletion
Delete end node in circular
void del_last() lists
{
if(head == null) {
System.out.print(“Empty list”);
}
else { //Checks whether contain only one
element if(head != tail ) {
Node current = head;
//get second last element as current.next is points to tail
while(current.next != tail) {
current = current.next;
}
tail = current; //Second last will be new tail
tail.next = //Tail point to head
} head;
Delete end node in circular
lists
//If list contains only one element, Then both head and tail will point to
null else {
head = tail = null;
}
}
}
Circular linked lists Applications
• All the running applications are kept in a circular linked list and the OS gives
a fixed time slot to all for running. The Operating System keeps on iterating
over the linked list until all the applications are completed.
• Multiplayer games. All the Players are kept in a Circular Linked List and
the pointer keeps on moving forward as a player's chance ends.
• Circular Linked List can also be used to create Circular Queue. In a Queue
we have to keep two pointers, FRONT and REAR in memory all the time,
where as in Circular Linked List, only one pointer is required.
References
1. Goodrich, Michael T & Roberto Tamassia, and “Data Structures & Algorithms in
Java”, WILEY publications 2015.
2. Sartaj Sahni, “Data Structures, Algorithms and Applications in Java”, Second
Edition, Universities Press.
3. Mark Allen Weiss, “Data Structures & Algorithm Analysis in Java”, Third
Edition,
Pearson Publishing.