Linked lists
Eleonora Ciceri, Politecnico di Milano
Email: eleonora.ciceri@polimi.it
Array: a review
Array: pros
 Arrays are a data structure commonly used to store
collections of elements
 Why do we use them?
 They are easy to create
 They are easy to access: we can read any element in the array by
using the syntax array[]
Array: cons
 Arrays have fixed dimension
 If is often specified at the beginning of the program
 With a little effort you can move its definition later in the code,
but…
Array: cons
 Array dimension is often chosen arbitrarily
 The programmer chooses a dimension that seems “fair enough”,
but…
Array: cons
 Inserting on the head of the array is expensive
 We are forced to move forward all the elements in the array to be
able to insert on the head
15 9 10 1 7
8 15 9 10 1 7
From arrays to linked lists
 Linked lists have advantages and disadvantages, but it is
easy to discover that linked lists are strong when arrays fail
 Main advantage: we allocate the memory only if we need to store
a new element
Recap: pointers
 A pointer stores the address to a variable
 The variable the pointers point to is called pointed
 *p is called dereference operator
 This operator is applied on the pointer
 It is used to access to the pointed data
Naming convention
p
*p = 2 p
Naming convention
 Assigning a pointer to another makes the two pointers point at
the same value
 Assigning the pointer does NOT copy the pointed value!
p = q p
q
Linked lists
Linked list: definition
 An array reserves a unique block of memory to store all its
elements
 A linked list reserves space in memory for each element in
separate blocks of memory (one for each element)
 Each element is called also node
 A linked list is a data structure that connects several nodes
using pointers, in the same way one would connect links in a
chain
Scavenger hunt
“Go to the tree”
Scavenger hunt
“Go to the house”
Scavenger hunt
“Go to the car”
Scavenger hunt
End of path
Scavenger hunt
 Game features
 A player never goes back, he keeps progressing towards the
treasure
 Each hint points to the next hint, until the player reaches the
treasure (i.e., the end of the path to the treasure)
Linked list vs. Scavenger hunt
 A linked list is a chain of nodes in which:
 There is a start
 There is an end
 Every node points to the next node in the chain
 A linked list resembles the scavenger hunt game:
 Nodes: places that the player reaches
 Pointers: hints that make the player move to the next place
Linked list vs. Scavenger hunt
Tree House Car
“To the tree” “To the house” “To the car”
Linked list vs. Scavenger hunt
Data Data Data
firstPtr nextPtr nextPtr
Linked list: elements
 Each node is composed of two parts:
 A data structure containing the
data of the node
 A pointer to the next object in the
list (nextPtr)
 We will use a struct to store both the
pointer and the data
Data
nextPtr
Drawing a linked list
head
“Stack”: we reserve a memory
block for each local variable and for
everything we need to allocate
statically; when a function ends, that
memory block is “not used anymore”
and thus it can be re-used by the next
executed function
“Heap”: here we can allocate and
de-allocate a memory block at any
time, when we need it
 Remember: we need to keep
track of what is allocated and
what is free
Drawing a linked list
 The starting point of the list is stored in a pointer, called head,
which points to the first node in the list
 All the other nodes are linked together
 The first one points to the second one
 The second one points to the third one
 The third one does not point to any other node, so the pointer
stored in the node is se to NULL (to mark the end of the list)
 The end of the list is called tail
Linked lists: disadvantages
 To access a node, you have to start from the head and go through
the whole list, until you reach the node
 Indeed, we know that:
 The list is NOT stored in a unique memory block
 You have to jump between different memory areas so as to go
through it
 We do not know which are the memory blocks that are dedicated to
the list: the pointers suggest how to navigate the memory to read the
list content
 To know which is the block of memory reserved for the i-th node we
need to access to the(i-1)-th node, and thus… go through the list!
Linked lists: disadvantages
 Performing operations on the first nodes in the list (i.e., the
ones near the head) is not expensive
 I need to go through a small set of nodes to reach the element I
am interested in
 Performing operations on the last nodes in the list (i.e., the
ones near the tail) is expensive
 I need to go through a large set of nodes to reach the element I
am interested in
First examples
Creating a linked list
 First of all, we have to define what is a node for the linked list:
 The structure we have created has two fields:
 data stores an integer number
 nextPtr points to the next node in the list
Creating a linked list
 Then, we fill the list
head
Computing the list length
 To compute the list length we have to:
 Go through the whole list
 Increase the count of nodes any time a node is encountered
 Note: it is important to keep always a pointer to the head of
the list
Computing the list length
head
currentNode
Computing the list length
head
currentNode
Computing the list length
head
currentNode
currentNode
Computing the list length
Position currentNode on the first
element (i.e., the first element is
pointed by currentNode)
When currentNode == NULL, we
are at the end of the list: the program
has to be stopped
Move currentNode on the next
node
Passing the list as a parameter
 The linked list is passed to functions via the head
 This does NOT copy the list!
 This copies the head pointer, so that both the caller and the
function have a pointer to the same data structure
Passing the list as a parameter
 When the function ends, currentNode is destroyed
automatically, since it is an ordinary local variable
 However, the nodes stay stored in the heap. Thus, any
modification made on the list by the function is permanent and
thus visible also when the function
 We access to the same list by using the head pointer
Passing the list as a parameter
 Q: What if at the end of the computeListLength function we
state that head = NULL;? Does this mean we lose the head
pointer in the caller too?
Passing the list as a parameter
 Q: What if at the end of the computeListLength function we
state that head = NULL;? Does this mean we lose the head
pointer in the caller too?
 A: No, because the head pointer used in the function is just a
local variable, copied from the original one. Any modification
to that pointer does NOT change the original copy the caller
has, neither this means that we lose the list itself: we still know
where it is located in the heap
Passing the list as a parameter
 Q: What if we pass an empty list to the computeListLength
function? Is this case correctly handled?
Passing the list as a parameter
 Q: What if we pass an empty list to the computeListLength
function? Is this case correctly handled?
 A: Yes. The representation of an empty list is a head pointer
set to NULL. The list length is still 0, since the while loop is
never executed
Creating lists
Inserting objects in the list
 In the previous slides we saw how to create a list statically,
i.e., by choosing a-priori which elements will be in the list, and
in which order
 However, the best solution one could implement is the one in
which an independent function adds a single node to an
existing list
Before starting: to not lose the head
 The proposed solution may modify the list’s head
 An example: if the element we want to insert is the first in the list,
the head moves to such element
 In such case, and in the most general case in which we expect
a change on the head pointer, the function accepts as a
parameter a reference to the head pointer
 As a consequence, any update to the head pointer is reflected in
the main()
Before starting: to not lose the head
 If insertNode() moves the head on a new element, the
update is visible in the main()
 Watch out!! If we overwrite the head with a wrong value, we lose
the list both in the function and in the main()!
Adding nodes to the list:
Insert at head
head
Adding nodes to the list:
Insert at head
head
newNode
Adding nodes to the list:
Insert at head
head
newNode
Adding nodes to the list:
Insert at head
 Pros
 Fast insertion: we create the object and attach it to the list, without
the necessity of going through the list
 Cons
 Non-ordered insertion: elements appear in the list in the opposite
direction with respect to how they were inserted
Adding nodes to the list:
Insert at tail
head
Adding nodes to the list:
Insert at tail
head
newNode
currentNode
Adding nodes to the list:
Insert at tail
head
currentNode
newNode
currentNode
Adding nodes to the list:
Insert at tail
head
currentNodecurrentNode
newNode
currentNode
Adding nodes to the list:
Insert at tail
head
currentNodecurrentNode currentNode
Adding nodes to the list:
Insert at tail
head Special case
The list is empty (i.e., head is NULL)
Adding nodes to the list:
Insert at tail
head
head
Special case
The list is empty (i.e., head is NULL)
Adding nodes to the list:
Insert at tail
 Pros
 Ordered insertion of elements
 Cons
 Slow insertion: we need to go through the whole list to insert an
element
 Inserting at tail is somehow not conveniente since we need to
go through the whole list to insert an element at the end of it
 Solution: keep a pointer on the list tail
 Inserting at the tail now costs as much as inserting at head
 We need to keep stored (without losing them!) both the head
and the tail
Adding nodes to the list:
“Smart” insert at tail
Adding nodes to the list:
“Smart” insert at tail
head
First insertion
Head and tail are equal
head
Other insertions
We add the element and then
move the tail
tail
tail tail
Adding nodes to the list:
Insert at a random position
 In this version, the user provides both the new element and the
position where to insert the element
head
“I want to insert 2 between 7 and 4”
position = 2
Adding nodes to the list:
Insert at a random position
 In this version, the user provides both the new element and the
position where to insert the element
head
currentNode
Adding nodes to the list:
Insert at a random position
 In this version, the user provides both the new element and the
position where to insert the element
head
currentNode currentNode
Adding nodes to the list:
Insert at a random position
 How much do we need to move currentNode?
 The position in which we’ll insert the node is stored in the variable
named position
 We stop at the last node before it
 What if the required position is too large, so that it go beyond
the list tail?
 currentNode becomes NULL because it is at the end of the list
 In this case, we report the error
Adding nodes to the list:
Insert at a random position
Adding nodes to the list:
Insert at a random position
head
currentNode currentNode
Adding nodes to the list:
Insert at a random position
 Special cases
 Empty list
 Insertion at position 0 (i.e., as first element in the list)
 We handle these cases as a unique special case
head
Printing lists
Printing lists
 We use the same procedure used to go through the list
 Algorithm
 currentNode (i.e., the pointer used to go through the list) is set
to head
 At each step:
 We print the data contained in the node (data field)
 We move currentNode on the following node (i.e.,
currentNode is set to currentNode->nextPtr)
Printing lists
List elements:
head
currentNode
Printing lists
head
currentNode
List elements:
- 1
Printing lists
head
currentNode
List elements:
- 1
Printing lists
List elements:
- 1
- 7
head
currentNode
Printing lists
List elements:
- 1
- 7
head
currentNode
Printing lists
List elements:
- 1
- 7
- 4
head
currentNode
Printing lists
List elements:
- 1
- 7
- 4
head
currentNode
Copy a list
Copy a list
 We are going to write a function that takes a list as an input
and returns a copy of such list
 As usual:
 List nodes are stored in memory
 A head pointer keeps a reference to the head of each list
 As a consequence, after executing the copy function, we’ll
have two head pointers:
 The first one points to the original list copy
 The second one points to the copy
Copy a list
head
copyHead
copyTail
Copy a list
head
copyHead
copyTail
currentNode
Copy a list
head
copyHead
copyTail
newNode
currentNode
Copy a list
head
copyHead
copyTail
Special case
The head is empty
currentNode
Copy a list
head
copyHead
copyTail
currentNode
currentNode
Copy a list
head
currentNode
currentNode
copyHead
copyTail
newNode
Copy a list
head
currentNode
currentNode
copyHead
copyTail
General case
The head is not empty
copyTail
Copying lists using recursion
 How can we copy a list with recursion?
 Base case
 The currentNode pointer is NULL
 Return: NULL
 Recursion step
 The currentNode pointer is not NULL
 Return: a copy of the element pointed by currentNode, followed
by a copy of the remaining section of the list (from
currentNode->nextPtr to tail)
Copying lists using recursion
During the first iteration
currentNode=head
Base case: if we arrived at the end of the list,
there isn’t any other node to copy
Recursion step:
currentNode->nextPtr
points to the remaining section
of the list
Delete list elements
Delete list elements
 Node deletion is done by skipping (bypassing) the element we
need to delete
head
Delete list elements
 Node deletion is done by skipping (bypassing) the element we
need to delete
head
Delete list elements
 Node deletion is done by skipping (bypassing) the element we
need to delete
head
Delete list elements
 Steps needed to delete the element element
 Look for element in the list, moving currentNode a node after
another starting from the head
 Delete the element bypassing it
 If currentNode is NOT positioned on the element we need to
delete, how can we go back to the previous node and bypass
it?
Delete list elements
 Steps needed to delete the element element
 Look for element in the list, moving currentNode a node after
another starting from the head
 Delete the element bypassing it
 If currentNode is NOT positioned on the element we need to
delete, how can we go back to the previous node and bypass
it?
head currentNode
previousNode
Delete list elements
head
previousNode
currentNode
Initialization
Delete list elements
head
previousNode currentNode
Looking for the element
Delete list elements
head
previousNode currentNode
Deletion
The element we
want to delete is the
first in the list
The element we
want to delete is
NOT the first in the
list
We free the memory and
exit the function
Deleting a list
Deleting a list
 This process is similar to the previous one (needed to delete a
single node from the list)
 We go through the list element after element
 We delete elements one by one
 Note
 Since we expect to have head=NULL at the end, we can allow
ourselves to modify the head in the process
 The head has to be modified in the main() too, thus we will pass
it by reference to the function
Deleting a list
head
currentNode
Deleting a list
head
currentNode
Deleting a list
head
currentNode
References
References
 Programmare in C++, Steve Oualline, O’Reilly
 Nick Parlante, Linked Lists Basics

Linked lists

  • 1.
  • 2.
  • 3.
    Array: pros  Arraysare a data structure commonly used to store collections of elements  Why do we use them?  They are easy to create  They are easy to access: we can read any element in the array by using the syntax array[]
  • 4.
    Array: cons  Arrayshave fixed dimension  If is often specified at the beginning of the program  With a little effort you can move its definition later in the code, but…
  • 5.
    Array: cons  Arraydimension is often chosen arbitrarily  The programmer chooses a dimension that seems “fair enough”, but…
  • 6.
    Array: cons  Insertingon the head of the array is expensive  We are forced to move forward all the elements in the array to be able to insert on the head 15 9 10 1 7 8 15 9 10 1 7
  • 7.
    From arrays tolinked lists  Linked lists have advantages and disadvantages, but it is easy to discover that linked lists are strong when arrays fail  Main advantage: we allocate the memory only if we need to store a new element
  • 8.
  • 9.
     A pointerstores the address to a variable  The variable the pointers point to is called pointed  *p is called dereference operator  This operator is applied on the pointer  It is used to access to the pointed data Naming convention p *p = 2 p
  • 10.
    Naming convention  Assigninga pointer to another makes the two pointers point at the same value  Assigning the pointer does NOT copy the pointed value! p = q p q
  • 11.
  • 12.
    Linked list: definition An array reserves a unique block of memory to store all its elements  A linked list reserves space in memory for each element in separate blocks of memory (one for each element)  Each element is called also node  A linked list is a data structure that connects several nodes using pointers, in the same way one would connect links in a chain
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
    Scavenger hunt  Gamefeatures  A player never goes back, he keeps progressing towards the treasure  Each hint points to the next hint, until the player reaches the treasure (i.e., the end of the path to the treasure)
  • 18.
    Linked list vs.Scavenger hunt  A linked list is a chain of nodes in which:  There is a start  There is an end  Every node points to the next node in the chain  A linked list resembles the scavenger hunt game:  Nodes: places that the player reaches  Pointers: hints that make the player move to the next place
  • 19.
    Linked list vs.Scavenger hunt Tree House Car “To the tree” “To the house” “To the car”
  • 20.
    Linked list vs.Scavenger hunt Data Data Data firstPtr nextPtr nextPtr
  • 21.
    Linked list: elements Each node is composed of two parts:  A data structure containing the data of the node  A pointer to the next object in the list (nextPtr)  We will use a struct to store both the pointer and the data Data nextPtr
  • 22.
    Drawing a linkedlist head “Stack”: we reserve a memory block for each local variable and for everything we need to allocate statically; when a function ends, that memory block is “not used anymore” and thus it can be re-used by the next executed function “Heap”: here we can allocate and de-allocate a memory block at any time, when we need it  Remember: we need to keep track of what is allocated and what is free
  • 23.
    Drawing a linkedlist  The starting point of the list is stored in a pointer, called head, which points to the first node in the list  All the other nodes are linked together  The first one points to the second one  The second one points to the third one  The third one does not point to any other node, so the pointer stored in the node is se to NULL (to mark the end of the list)  The end of the list is called tail
  • 24.
    Linked lists: disadvantages To access a node, you have to start from the head and go through the whole list, until you reach the node  Indeed, we know that:  The list is NOT stored in a unique memory block  You have to jump between different memory areas so as to go through it  We do not know which are the memory blocks that are dedicated to the list: the pointers suggest how to navigate the memory to read the list content  To know which is the block of memory reserved for the i-th node we need to access to the(i-1)-th node, and thus… go through the list!
  • 25.
    Linked lists: disadvantages Performing operations on the first nodes in the list (i.e., the ones near the head) is not expensive  I need to go through a small set of nodes to reach the element I am interested in  Performing operations on the last nodes in the list (i.e., the ones near the tail) is expensive  I need to go through a large set of nodes to reach the element I am interested in
  • 26.
  • 27.
    Creating a linkedlist  First of all, we have to define what is a node for the linked list:  The structure we have created has two fields:  data stores an integer number  nextPtr points to the next node in the list
  • 28.
    Creating a linkedlist  Then, we fill the list head
  • 29.
    Computing the listlength  To compute the list length we have to:  Go through the whole list  Increase the count of nodes any time a node is encountered  Note: it is important to keep always a pointer to the head of the list
  • 30.
    Computing the listlength head currentNode
  • 31.
    Computing the listlength head currentNode
  • 32.
    Computing the listlength head currentNode currentNode
  • 33.
    Computing the listlength Position currentNode on the first element (i.e., the first element is pointed by currentNode) When currentNode == NULL, we are at the end of the list: the program has to be stopped Move currentNode on the next node
  • 34.
    Passing the listas a parameter  The linked list is passed to functions via the head  This does NOT copy the list!  This copies the head pointer, so that both the caller and the function have a pointer to the same data structure
  • 35.
    Passing the listas a parameter  When the function ends, currentNode is destroyed automatically, since it is an ordinary local variable  However, the nodes stay stored in the heap. Thus, any modification made on the list by the function is permanent and thus visible also when the function  We access to the same list by using the head pointer
  • 36.
    Passing the listas a parameter  Q: What if at the end of the computeListLength function we state that head = NULL;? Does this mean we lose the head pointer in the caller too?
  • 37.
    Passing the listas a parameter  Q: What if at the end of the computeListLength function we state that head = NULL;? Does this mean we lose the head pointer in the caller too?  A: No, because the head pointer used in the function is just a local variable, copied from the original one. Any modification to that pointer does NOT change the original copy the caller has, neither this means that we lose the list itself: we still know where it is located in the heap
  • 38.
    Passing the listas a parameter  Q: What if we pass an empty list to the computeListLength function? Is this case correctly handled?
  • 39.
    Passing the listas a parameter  Q: What if we pass an empty list to the computeListLength function? Is this case correctly handled?  A: Yes. The representation of an empty list is a head pointer set to NULL. The list length is still 0, since the while loop is never executed
  • 40.
  • 41.
    Inserting objects inthe list  In the previous slides we saw how to create a list statically, i.e., by choosing a-priori which elements will be in the list, and in which order  However, the best solution one could implement is the one in which an independent function adds a single node to an existing list
  • 42.
    Before starting: tonot lose the head  The proposed solution may modify the list’s head  An example: if the element we want to insert is the first in the list, the head moves to such element  In such case, and in the most general case in which we expect a change on the head pointer, the function accepts as a parameter a reference to the head pointer  As a consequence, any update to the head pointer is reflected in the main()
  • 43.
    Before starting: tonot lose the head  If insertNode() moves the head on a new element, the update is visible in the main()  Watch out!! If we overwrite the head with a wrong value, we lose the list both in the function and in the main()!
  • 44.
    Adding nodes tothe list: Insert at head head
  • 45.
    Adding nodes tothe list: Insert at head head newNode
  • 46.
    Adding nodes tothe list: Insert at head head newNode
  • 47.
    Adding nodes tothe list: Insert at head  Pros  Fast insertion: we create the object and attach it to the list, without the necessity of going through the list  Cons  Non-ordered insertion: elements appear in the list in the opposite direction with respect to how they were inserted
  • 48.
    Adding nodes tothe list: Insert at tail head
  • 49.
    Adding nodes tothe list: Insert at tail head newNode currentNode
  • 50.
    Adding nodes tothe list: Insert at tail head currentNode newNode currentNode
  • 51.
    Adding nodes tothe list: Insert at tail head currentNodecurrentNode newNode currentNode
  • 52.
    Adding nodes tothe list: Insert at tail head currentNodecurrentNode currentNode
  • 53.
    Adding nodes tothe list: Insert at tail head Special case The list is empty (i.e., head is NULL)
  • 54.
    Adding nodes tothe list: Insert at tail head head Special case The list is empty (i.e., head is NULL)
  • 55.
    Adding nodes tothe list: Insert at tail  Pros  Ordered insertion of elements  Cons  Slow insertion: we need to go through the whole list to insert an element
  • 56.
     Inserting attail is somehow not conveniente since we need to go through the whole list to insert an element at the end of it  Solution: keep a pointer on the list tail  Inserting at the tail now costs as much as inserting at head  We need to keep stored (without losing them!) both the head and the tail Adding nodes to the list: “Smart” insert at tail
  • 57.
    Adding nodes tothe list: “Smart” insert at tail head First insertion Head and tail are equal head Other insertions We add the element and then move the tail tail tail tail
  • 58.
    Adding nodes tothe list: Insert at a random position  In this version, the user provides both the new element and the position where to insert the element head “I want to insert 2 between 7 and 4” position = 2
  • 59.
    Adding nodes tothe list: Insert at a random position  In this version, the user provides both the new element and the position where to insert the element head currentNode
  • 60.
    Adding nodes tothe list: Insert at a random position  In this version, the user provides both the new element and the position where to insert the element head currentNode currentNode
  • 61.
    Adding nodes tothe list: Insert at a random position  How much do we need to move currentNode?  The position in which we’ll insert the node is stored in the variable named position  We stop at the last node before it  What if the required position is too large, so that it go beyond the list tail?  currentNode becomes NULL because it is at the end of the list  In this case, we report the error
  • 62.
    Adding nodes tothe list: Insert at a random position
  • 63.
    Adding nodes tothe list: Insert at a random position head currentNode currentNode
  • 64.
    Adding nodes tothe list: Insert at a random position  Special cases  Empty list  Insertion at position 0 (i.e., as first element in the list)  We handle these cases as a unique special case head
  • 65.
  • 66.
    Printing lists  Weuse the same procedure used to go through the list  Algorithm  currentNode (i.e., the pointer used to go through the list) is set to head  At each step:  We print the data contained in the node (data field)  We move currentNode on the following node (i.e., currentNode is set to currentNode->nextPtr)
  • 67.
  • 68.
  • 69.
  • 70.
    Printing lists List elements: -1 - 7 head currentNode
  • 71.
    Printing lists List elements: -1 - 7 head currentNode
  • 72.
    Printing lists List elements: -1 - 7 - 4 head currentNode
  • 73.
    Printing lists List elements: -1 - 7 - 4 head currentNode
  • 74.
  • 75.
    Copy a list We are going to write a function that takes a list as an input and returns a copy of such list  As usual:  List nodes are stored in memory  A head pointer keeps a reference to the head of each list  As a consequence, after executing the copy function, we’ll have two head pointers:  The first one points to the original list copy  The second one points to the copy
  • 76.
  • 77.
  • 78.
  • 79.
    Copy a list head copyHead copyTail Specialcase The head is empty currentNode
  • 80.
  • 81.
  • 82.
  • 83.
    Copying lists usingrecursion  How can we copy a list with recursion?  Base case  The currentNode pointer is NULL  Return: NULL  Recursion step  The currentNode pointer is not NULL  Return: a copy of the element pointed by currentNode, followed by a copy of the remaining section of the list (from currentNode->nextPtr to tail)
  • 84.
    Copying lists usingrecursion During the first iteration currentNode=head Base case: if we arrived at the end of the list, there isn’t any other node to copy Recursion step: currentNode->nextPtr points to the remaining section of the list
  • 85.
  • 86.
    Delete list elements Node deletion is done by skipping (bypassing) the element we need to delete head
  • 87.
    Delete list elements Node deletion is done by skipping (bypassing) the element we need to delete head
  • 88.
    Delete list elements Node deletion is done by skipping (bypassing) the element we need to delete head
  • 89.
    Delete list elements Steps needed to delete the element element  Look for element in the list, moving currentNode a node after another starting from the head  Delete the element bypassing it  If currentNode is NOT positioned on the element we need to delete, how can we go back to the previous node and bypass it?
  • 90.
    Delete list elements Steps needed to delete the element element  Look for element in the list, moving currentNode a node after another starting from the head  Delete the element bypassing it  If currentNode is NOT positioned on the element we need to delete, how can we go back to the previous node and bypass it? head currentNode previousNode
  • 91.
  • 92.
    Delete list elements head previousNodecurrentNode Looking for the element
  • 93.
    Delete list elements head previousNodecurrentNode Deletion The element we want to delete is the first in the list The element we want to delete is NOT the first in the list We free the memory and exit the function
  • 94.
  • 95.
    Deleting a list This process is similar to the previous one (needed to delete a single node from the list)  We go through the list element after element  We delete elements one by one  Note  Since we expect to have head=NULL at the end, we can allow ourselves to modify the head in the process  The head has to be modified in the main() too, thus we will pass it by reference to the function
  • 96.
  • 97.
  • 98.
  • 99.
  • 100.
    References  Programmare inC++, Steve Oualline, O’Reilly  Nick Parlante, Linked Lists Basics