Download Doubly linked lists and stacks

Survey
yes no Was this document useful for you?
   Thank you for your participation!

* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project

Document related concepts
no text concepts found
Transcript
Lists
CS122 Algorithms and Data Structures
A list is a varying-length, linear collection of
homogeneous elements.
Linear means each list element (except the
first) has a unique predecessor, and each
element (except the last) has a unique
successor
In a linear structure, components can only
be accessed sequentially one after the
other
MW 11:00 am - 12:15 pm, MSEC 101
Instructor: Xiao Qin
Lecture 5: Doubly Linked Lists and
Linked Stacks
2
class SortedList
An Insert Algorithm for Sorted Lists
Sorted list: list elements sorted in
ascending order
SortedList
~SortedList
Private data:
IsEmpty
How would the algorithm to insert
an item into a sorted linked list?
Print
head
5
8
17
InsertTop
Insert
DeleteTop
3
Observers
– Print
– IsEmpty
4
struct NodeType
ADT SortedList Operations
Transformers
– InsertTop
– Insert
– DeleteTop
– Delete
Delete
// SPECIFICATION FILE DYNAMIC-LINKED SORTED LIST
( slist.h )
change state
typedef
int ItemType ;
observe state
struct NodeType
{
ItemType
item ;
NodeType* next ;
};
// Type of each component
// is simple type or string type
// Pointer to person’s name
// link to next node in list
typedef NodeType* NodePtr;
5
6
1
Insert algorithm for
SortedList
Inserting 12 into a Sorted List
find proper position for the new element in
the sorted list using two pointers prevPtr
and currPtr, where prevPtr trails behind
currPtr
obtain a node for insertion and place item
in it
prevPtr
currPtr
Private data:
5
head
8
17
insert the node by adjusting pointers
7
Finding Proper Position for 12
prevPtr
NULL
8
Finding Proper Position for 12
currPtr
prevPtr
Private data:
currPtr
Private data:
5
head
8
head
17
while ( currPtr != NULL && item > currPtr->info )
{
5
8
17
while ( currPtr != NULL && item > currPtr->info )
{
prevPtr = currPtr ;
currPtr = currPtr->next ;
prevPtr = currPtr ;
currPtr = currPtr->next ;
}
}
9
10
Inserting ’12’ into Proper Position
Finding Proper Position for 12
location->next = currPtr ;
if ( prevPtr == NULL )
head = location ;
prevPtr
currPtr
else
prevPtr
Private data:
prevPtr->next = location ;
currPtr
Private data:
5
head
8
17
head
5
8
17
while ( currPtr != NULL && item > currPtr->info )
{
prevPtr = currPtr ;
currPtr = currPtr->next ;
12
}
11
12
2
void SortedList :: Insert( ItemType item )
// Pre: item is assigned && list components in ascending order
// Post: new node containing item is in its proper place
//
&& list components in ascending order
{ NodePtr currPtr, prevPtr, location ;
// IMPLEMENTATION DYNAMIC-LINKED SORTED LIST
// (slist.cpp)
SortedList ::SortedList ( )
// Constructor
// Post: head == NULL
{
head = NULL ;
}
SortedList2 :: ~SortedList2 ( ) // Destructor
// Post: All linked nodes deallocated
{
ItemType temp ;
// keep deleting top node
while ( !IsEmpty )
DeleteTop ( temp );
}
location = new NodeType ;
newNodePtr->info = item ;
prevPtr = NULL ;
currPtr = head ;
while ( currPtr != NULL && item > currPtr->info )
{
prevPtr = currPtr ;
// advance both pointers
currPtr = currPtr->next ;
}
location->next = currPtr ;
// insert new node here
if ( prevPtr == NULL )
head = location ;
else
prevPtr->next = location ;
}
13
13
14
14
void SortedList :: Delete ( /* in */ ItemType item )
void SortedList :: DeleteTop ( ItemType& item )
// Pre: list is not empty && list elements in ascending order
// Post: item == element of first list node @ entry
//
&& node containing item is no longer in linked list
//
&& list elements in ascending order
{
NodePtr tempPtr = head ;
item = head->info ;
head = head->next ;
delete tempPtr ;
// Pre:
list is not empty && list elements in ascending order
//
&& item == component member of some list node
// Post:
item == element of first list node @ entry
//
&& node containing first occurrence of item is no longer
//
in linked list && list elements in ascending order
{
NodePtr delPtr ;
NodePtr currPtr ;
if ( item == head->info )
{
delPtr = head ;
head = head->next ;
// Is item in first node?
// If so, delete first node
}
else {
// search for item in rest of list
currPtr = head ;
while ( currPtr->next->info != item )
currPtr = currPtr->next ;
delPtr = currPtr->next ;
currPtr->next = currPtr->next->next ;
// obtain item
// advance head
}
}
delete delPtr ;
}
15
Doubly Linked Lists
An extension of a Singly Linked List
Each node has two pointer
–
–
One pointing to the successor
One pointing to the predecessor
They are used because they ease certain
operations like the deleteElement
They are interesting for traversal as you can
move in either directions
struct
struct NodeType
NodeType {{
<someType>
<someType> data;
data;
NodeType*
NodeType* prev;
prev;
NodeType*
NodeType* next;
next;
}}
16
16
Doubly Linked Lists (Cont.)
Most of our structures and algorithms will be
implemented with the help of Doubly Linked
Lists
Although some operations are made easier to
understand they also become a bit slower due
to the overhead of extra pointers
In addition to the head a pointer called tail is
also maintained
head
head
55
//
12
12
//
55
tail
tail
3
Inserting in the Front
Inserting in the Front (cont.)
head
head
tail
tail
head
head
tail
tail
//
55
12
12
55
//
55
//
55
12
12
//
88
temp
temp
NodeType *temp = new NodeType;
NodeType;
temp->data = 8;
temp->next = head;
head->prev = temp;
head = temp;
temp = NULL;
Inserting in the Front (cont.)
head
head
88
temp
temp
NodeType
NodeType *temp
*temp == new
new NodeType;
NodeType;
temp->data
temp->data == 8;
8;
temp->next
temp->next == head;
head;
head->prev
head->prev == temp;
temp;
head
head == temp;
temp;
temp
temp == NULL;
NULL;
Inserting in the Front (cont.)
tail
tail
head
head
tail
tail
//
55
88
temp
temp
12
12
//
55
55
NodeType *temp = new NodeType;
NodeType;
temp->data = 8;
temp->next = head;
head->prev = temp;
head = temp;
temp = NULL;
Inserting in the Front (cont.)
88
temp
temp
12
12
55
NodeType
NodeType *temp
*temp == new
new NodeType;
NodeType;
temp->data
temp->data == 8;
8;
temp->next
temp->next == head;
head;
head->prev
head->prev == temp;
temp;
head
head == temp;
temp;
temp
temp == NULL;
NULL;
Deleting element ’12’
head
head
head
head
tail
tail
tail
tail
88
//
55
12
12
//
55
//
55
88
temp
temp
12
12
55
NodeType *temp = new NodeType;
NodeType;
temp->data = 8;
temp->next = head;
head->prev = temp;
head = temp;
temp = NULL;
current
current
NodeType
NodeType *current
*current == head;
head;
while
while (current->data
(current->data !=
!= 12
12 and
and current->next
current->next !=
!= NULL)
NULL)
current
current == current->next;
current->next;
}}
current->prev->next
current->prev->next == current->next;
current->next;
current->next->prev
current->next->prev == current->prev;
current->prev;
delete
delete current;
current;
4
Deleting element ’12’ (cont.)
head
head
Deleting element ’12’ (cont.)
tail
tail
88
//
55
head
head
tail
tail
//
55
12
12
55
88
//
12
12
//
55
current
current
current
current
NodeType
NodeType *current
*current == head;
head;
while
while (current->data
(current->data !=
!= 12
12 and
and current->next
current->next !=
!= NULL)
NULL)
current
current = current->next;
}}
current->prev->next
current->prev->next = current->next;
current->next->prev
current->next->prev = current->prev;
delete
delete current;
current;
Deleting element ’12’ (cont.)
head
head
NodeType
NodeType *current
*current == head;
head;
while
while (current->data
(current->data !=
!= 12
12 and
and current->next
current->next !=
!= NULL)
NULL)
current
current == current->next;
current->next;
}}
current->prev->next
current->prev->next == current->next;
current->next;
current->next->prev
current->next->prev == current->prev;
current->prev;
delete
delete current;
current;
Circular Lists
tail
tail
88
//
//
55
55
Nodes form a ring
Each node has a successor
current
current
tail
NodeType
NodeType *current
*current == head;
head;
while
while (current->data
(current->data !=
!= 12
12 and
and current->next
current->next !=
!= NULL)
NULL)
current
=
current->next;
current
}}
current->prev->next
current->prev->next = current->next;
current->next->prev
current->next->prev = current->prev;
delete
delete current;
current;
5
8
3
28
Inserting a Node at the Tail of a
List Circular Lists
int
item = 6;
Node
*location;
location = new NodeType;
location->info = item;
tail->next = location;
tail = tail->next;
5
location
6
Inserting a Node at the Tail of a
List Circular Lists (cont.)
int
item = 6;
Node
*location;
location = new NodeType;
location->info = item;
location->next = tail->next;
tail
tail->next = location;
tail = tail->next;
tail
8
3
5
29
location
6
8
3
30
5
Inserting a Node at the Tail of a
List Circular Lists (cont.)
Inserting a Node at the Tail of a
List Circular Lists (cont.)
int
item = 6;
Node
*location;
location = new NodeType;
location->info = item;
location->next = tail->next;
tail
tail->next = location;
tail = location;
5
8
int
item = 6;
Node
*location;
location = new NodeType;
location->info = item;
location->next = tail->next;
tail->next = location;
tail = location;
3
5
8
3
tail
location
6
31
Inserting a Node at the Tail of a List
Circular Lists: A Special Case
location
32
int
item = 6;
Node
*location;
location = new NodeType;
location->info = item;
if (isEmpty()) {
tail = location;
tail->next = tail;
}
NULL
6
6
Inserting a Node at the Tail of a List
Circular Lists: A Special Case (cont.)
int
item = 6;
Node
*location;
location = new NodeType;
location->info = item;
if (isEmpty()) {
tail = location;
tail->next = tail;
}
tail
location
tail
33
Inserting a Node at the Tail of a List
Circular Lists: A Special Case (cont.)
location
6
34
Debugging Linked Lists
int
item = 6;
Node
*location;
location = new NodeType;
location->info = item;
if (isEmpty()) {
tail = location;
tail->next = tail;
}
else {
………..
}
tail
location
6
35
6
A Skip List with Evenly spaced
Nodes of different levels
Skip Lists
Linked lists require sequential scanning
for a search operation
Skip lists allow for skipping certain
nodes
55
77
88
11
11
15
15
16
16
A skip list is an ordered linked list
A Find Algorithm for Skip Lists
Stacks using Linked Lists
Find(element el)
p = the non-null list on the highest level i;
while el not found and level i >= 0
if p->key > el //eg. el = 8
p = a sublist that begins in the predecessor of p on level i--;
else if p->key < el
if p is the last node on level i; //eg. el = 16
p = a nonnull sublist begins in p on the highest level < i;
i = the number of the new level; //i = i-1
else p = p->next;
else return(TRUE);
return(FALSE);
55
77
88
11
11
15
15
16
16
A series of operations executed
on a stack
Implementation of stacks using linked lists are very
simple
The difference between a normal linked list and a
stack using a linked list is that some of the linked list
operations are not available for stacks
Being a stack we have only one insert operation called
push().
– In many ways push is the same as insert in the
front
We have also one delete operation called pop()
– This operation is the same as the operation delete
from the front
The other important operations in a stack, called
top() and isEmpty(), don't modify the structure
To implement stacks we will use a singly linked list
Pictorial view of a stack
top
top
77
push 3 push 7
pop
push 1 push 4
pop
11
4
7
3
3
3
1
1
1
88
3
3
3
//
7
push(45)
push(45)
top
top
top
top
temp
temp
temp
temp
77
77
45
45
45
45
11
11
88
//
88
//
NodeType *temp = new NodeType;
temp->data = n;
temp->next = top;
top = temp;
temp = NULL;
push(45)
NodeType
NodeType *temp
*temp == new
new NodeType;
NodeType;
temp->data
temp->data == n;
n;
temp->next
=
top;
temp->next = top;
top
top == temp;
temp;
temp
temp == NULL;
NULL;
push(45)
top
top
temp
temp
77
top
top
45
45
45
45
77
11
11
88
//
88
//
NodeType *temp = new NodeType;
temp->data = n;
temp->next = top;
top = temp;
temp = NULL;
pop()
NodeType
NodeType *temp
*temp == new
new NodeType;
NodeType;
temp->data
temp->data == n;
n;
temp->next
temp->next == top;
top;
top
top == temp;
temp;
temp
temp == NULL;
NULL;
pop()
top
top
temp
temp
top
top
temp
temp
45
45
45
45
77
77
11
11
88
//
88
//
NodeType *temp = top;
top = top->next;
int returnValue = temp->data;
delete temp;
return returnValue;
NodeType
NodeType *temp
*temp == top;
top;
top
top == top->next;
top->next;
int
int returnValue
returnValue == temp->data;
temp->data;
delete
delete temp;
temp;
return
return returnValue;
returnValue;
8
pop()
pop()
top
top
temp
temp
top
top
45
45
77
77
11
11
88
//
88
//
NodeType *temp = top;
top = top->next;
int returnValue = temp->data;
delete temp;
return returnValue;
NodeType
NodeType *temp
*temp == top;
top;
top
top == top->next;
top->next;
int
returnValue
=
int returnValue = temp->data;
temp->data;
delete
delete temp;
temp;
return
return returnValue;
returnValue;
top()
top
top
45
45
77
return
return top->data;
top->data;
11
88
//
9
Related documents