0% found this document useful (0 votes)
23 views

Data Structure - List

The document discusses lists as an abstract data type and describes some common list operations. It proposes designing a List class with functions for basic operations like construction, checking if empty, insertion, deletion, and traversal/display. An array-based implementation is suggested where elements are stored sequentially in an array. The class would include data members to track the array and size, and functions are described to implement common operations like insertion and deletion by shifting elements in the array.

Uploaded by

madsilveratrest
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
23 views

Data Structure - List

The document discusses lists as an abstract data type and describes some common list operations. It proposes designing a List class with functions for basic operations like construction, checking if empty, insertion, deletion, and traversal/display. An array-based implementation is suggested where elements are stored sequentially in an array. The class would include data members to track the array and size, and functions are described to implement common operations like insertion and deletion by shifting elements in the array.

Uploaded by

madsilveratrest
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 59

Lists

Hung-Ming Chen
NCTU EE
Fall 2023

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 1
Education, Inc. All rights reserved. 0-13-140909-3
Consider Every Day Lists
• Groceries to be purchased
• Job to-do list
• List of assignments for a course
• Dean's list

• Can you name some others??

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 2
Education, Inc. All rights reserved. 0-13-140909-3
Properties of Lists
• Can have a single element
• Can have no elements
• There can be lists of lists

• We will look at the list as an abstract data


type
– Homogeneous
– Finite length
– Sequential elements
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 3
Education, Inc. All rights reserved. 0-13-140909-3
Basic Operations
• Construct an empty list
• Determine whether or not empty
• Insert an element into the list
• Delete an element from the list
• Traverse (iterate through) the list to
– Modify
– Output
– Search for a specific value
– Copy or save
– Rearrange

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 4
Education, Inc. All rights reserved. 0-13-140909-3
Designing a List Class
• Should contain at least the following function
members
– Constructor
– empty()
– insert()
– delete()
– display()
• Implementation involves
– Defining data members
– Defining function members from design phase
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 5
Education, Inc. All rights reserved. 0-13-140909-3
Array-Based Implementation
of Lists
• An array is a viable choice for storing list elements
– Elements are sequential
– It is a commonly available data type
– Algorithm development is easy
• Normally sequential orderings of list elements
match with array elements

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 6
Education, Inc. All rights reserved. 0-13-140909-3
Implementing Operations
• Constructor
– Static array allocated at compile time
• Empty
– Check if size == 0
• Traverse
– Use a loop from 0th element to size – 1
• Insert
– Shift elements to
right of insertion point Also adjust
size up or
• Delete down
– Shift elements back

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 7
Education, Inc. All rights reserved. 0-13-140909-3
List Class with Static Array
• Must deal with issue of declaration of
CAPACITY
• Use typedef mechanism
typedef Some_Specific_Type ElementType
ElementType array[CAPACITY];
• For specific implementation of our class we
simply fill in desired type for
Some_Specific_Type

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 8
Education, Inc. All rights reserved. 0-13-140909-3
List Class with Static Array
• Can put typedef declaration inside or
outside of class
– Inside: must specify List::ElementType
for reference to the type outside the class
– Outside: now able to use the template
mechanism (this will be our choice)
• Also specify the CAPACITY as a const
– Also choose to declare outside class (why not
inside?)
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 9
Education, Inc. All rights reserved. 0-13-140909-3
List Class Example
• Declaration file, Fig. 6.1A
– Note use of typedef mechanism outside the
class
– This example good for a list of int
• Definition, implementation Fig. 6.1B
– Note considerable steps required for insert()
and erase() functions
• Program to test the class, Fig 6.1C

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 10
Education, Inc. All rights reserved. 0-13-140909-3
Class List: static array
/*-- List.h ---------------------------------------------------------------
/***** insert and erase *****/
This header file defines the data type List for processing lists. void insert(ElementType item, int pos);
Basic operations are: /*----------------------------------------------------------------------
Constructor Insert a value into the list at a given position.
empty: Check if list is empty Precondition: item is the value to be inserted; there is room in
insert: Insert an item
erase: Remove an item the array (mySize < CAPACITY); and the position satisfies
display: Output the list 0 <= pos <= mySize.
<<, >> : input and output operators Postcondition: item has been inserted into the list at the position
-------------------------------------------------------------------------*/ determined by pos (provided there is room and pos is a legal
position).
#include <iostream>
-----------------------------------------------------------------------*/
#ifndef LIST void erase(int pos);
#define LIST /*----------------------------------------------------------------------
Remove a value from the list at a given position.
const int CAPACITY = 1024; Precondition: The list is not empty and the position satisfies
typedef int ElementType;
0 <= pos < mySize.
class List Postcondition: element at the position determined by pos has been
{ removed (provided pos is a legal position).
public: ----------------------------------------------------------------------*/
/******** Function Members ********/ /***** output *****/
/***** Class constructor *****/
List(); void display(ostream & out) const;
/*---------------------------------------------------------------------- /*----------------------------------------------------------------------
Construct a List object. Display a list.
Precondition: out is a reference parameter
Precondition: None Postcondition: The list represented by this List object has been
Postcondition: An empty List object has been constructed;
inserted into ostream out.
mySize is 0.
-----------------------------------------------------------------------*/ -----------------------------------------------------------------------*/
private:
/***** empty operation *****/ /******** Data Members ********/
bool empty() const; int mySize; // current size of list stored in myArray
/*----------------------------------------------------------------------
ElementType myArray[CAPACITY]; // array to store list elements
Check if a list is empty.
}; //--- end of List class
Precondition: None
Postcondition: true is returned if the list is empty, //------ Prototype of output operator
false if not. ostream & operator<< (ostream & out, const List & aList);
-----------------------------------------------------------------------*/
#endif
11
#include <cassert>
using namespace std; List Implementation if (pos < 0 || pos > mySize)
#include "List.h"
{
cerr << "*** Illegal location to insert -- " << pos
//--- Definition of class constructor << ". List unchanged. ***\n";
List::List() return;
: mySize(0) }
{ // First shift array elements right to make room for item
}
for(int i = mySize; i > pos; i--)
//--- Definition of empty() myArray[i] = myArray[i - 1];
bool List::empty() const
{ // Now insert item at position pos and increase list size
return mySize == 0;
myArray[pos] = item;
mySize++;
}
}
//--- Definition of display()
// Definition of erase()
void List::display(ostream & out) const void List::erase(int pos)
{ {
for (int i = 0; i < mySize; i++) if (mySize == 0)
out << myArray[i] << " "; {
} cerr << "*** List is empty ***\n";
return;
//--- Definition of output operator }
ostream & operator<< (ostream & out, const List & aList) if (pos < 0 || pos >= mySize)
{ {
aList.display(out);
cerr << "Illegal location to delete -- " << pos
<< ". List unchanged. ***\n";
return out;
return;
}
}

//--- Definition of insert() // Shift array elements left to close the gap
void List::insert(ElementType item, int pos) for(int i = pos; i < mySize; i++)
{ myArray[i] = myArray[i + 1];
if (mySize == CAPACITY)
{ // Decrease list size
cerr << "*** No space for list element -- terminating " mySize--;
"execution ***\n"; }
exit(1);
12
}
Test Driver
//--- Program to test List class.
cout << "\nTry to insert at position -1" << endl;
#include <iostream> intList.insert(0, -1);
using namespace std;
cout << "\nTry to insert at position 10" << endl;
intList.insert(0, 10);
#include "List.h"
// Test erase()
int index;
int main() cout << endl;
{ while (!intList.empty())
// Test the class constructor {
List intList; cout << "Give an index of a list element to remove: ";
cout << "Constructing intList\n"; cin >> index;
intList.erase(index);
// Test empty() and output of empty list
cout << intList << endl;
}
if (intList.empty())
cout << "List is empty" << endl;
cout << "Empty List: \n"
<< intList << endl; // Test output of empty list cout << "\nInserting " << CAPACITY<< " integers\n";
for (int i = 0; i < CAPACITY; i++)
// Test insert() intList.insert(i, i);
for (int i = 0; i < 9; i++) cout << "Attempting to insert one more integer:\n";
{ intList.insert(-1, 0);
cout << "Inserting " << i << " at position " << i/2 << endl;
intList.insert(i, i/2); // -- Insert i at position i/2 return 0;
//Test output
}
cout << intList << endl;
}
cout << "List empty? " << (intList.empty() ? "Yes" : "No") << endl;

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 13
Education, Inc. All rights reserved. 0-13-140909-3
Execution Trace for Test Program

14
List Class with Static Array -
Problems
• Stuck with "one size fits all"
– Could be wasting space
– Could run out of space
• Better to have instantiation of specific list
specifying what the capacity should be
• Thus we consider creating a List class with
dynamically-allocated array

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 15
Education, Inc. All rights reserved. 0-13-140909-3
Dynamic-Allocation for List Class
• Changes required in data members
– Eliminate const declaration for CAPACITY
– Add variable data member to store capacity specified by
client program
– Change array data member to a pointer
– Constructor requires considerable change
• Little or no changes required for
– empty()
– display()
– erase()
– insert()

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 16
Education, Inc. All rights reserved. 0-13-140909-3
Dynamic-Allocation for List Class

• Note data changes in Fig. 6.2A, List.h


• Note implementation file Fig. 6.2B, List.cpp
– Changes to constructor
– Addition of other functions to deal with
dynamically allocated memory
• Note testing of various features in Fig. 6.2C,
the demo program

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 17
Education, Inc. All rights reserved. 0-13-140909-3
#include <iostream>
Class List: dynamic array /***** empty operation *****/
bool empty() const;
#ifndef LIST /*----------------------------------------------------------------------
#define LIST Check if a list is empty.
Precondition: None
typedef int ElementType; Postcondition: true is returned if the list is empty,
class List false if not.
{ -----------------------------------------------------------------------*/
public: /***** insert and erase *****/
/******** Function Members ********/ void insert(ElementType item, int pos);
/***** Class constructor *****/
List(int maxSize = 1024); /*----------------------------------------------------------------------
/*---------------------------------------------------------------------- Insert a value into the list at a given position.
Construct a List object. Precondition: item is the value to be inserted; there is room in
Precondition: maxSize is a positive integer with default value 1024. the array (mySize < CAPACITY); and the position satisfies
Postcondition: An empty List object is constructed; myCapacity == 0 <= pos <= mySize.
maxSize (default value 1024); myArrayPtr points to a run-time Postcondition: item has been inserted into the list at the position
array with myCapacity as its capacity; and mySize is 0. determined by pos (provided there is room and pos is a legal
-----------------------------------------------------------------------*/ position).
/***** Class destructor *****/ -----------------------------------------------------------------------*/
~List(); void erase(int pos);
/*---------------------------------------------------------------------- /*----------------------------------------------------------------------
Destroys a List object. Remove a value from the list at a given position.
Precondition: The life of a List object is over. Precondition: The list is not empty and the position satisfies
Postcondition: The memory dynamically allocated by the constructor 0 <= pos < mySize.
for the array pointed to by myArrayPtr has been returned to Postcondition: element at the position determined by pos has been
the heap. removed (provided pos is a legal position).
------------------------------------------------------------------*/
/***** Copy constructor *****/ ----------------------------------------------------------------------*/
List(const List & origList); /***** output *****/
/*---------------------------------------------------------------------- void display(ostream & out) const;
Construct a copy of a List object. /*----------------------------------------------------------------------
Precondition: A copy of origList is needed; origList is a const Display a list.
reference parameter. Precondition: The ostream out is open.
Postcondition: A copy of origList has been constructed. Postcondition: The list represented by this List object has been
-----------------------------------------------------------------------*/ inserted into out.
/***** Assignment operator *****/
List & operator=(const List & origList); -----------------------------------------------------------------------*/
/*---------------------------------------------------------------------- private:
Assign a copy of a List object to the current object. /******** Data Members ********/
Precondition: none int mySize; // current size of list stored in array
Postcondition: A copy of origList has been assigned to this int myCapacity; // capacity of array
object. A reference to this list is returned. ElementType * myArrayPtr; // pointer to dynamically-allocated array
-----------------------------------------------------------------------*/
}; //--- end of List class
//------ Prototype of output operator
ostream & operator<< (ostream & out, const List & aList);
18
#endif
#include <cassert>
#include <new>
Implementation //-- Allocate a new array if necessary
using namespace std;
if (myCapacity != origList.myCapacity)
#include "List.h" {
delete[] myArrayPtr;
//--- Definition of class constructor
myArrayPtr = new(nothrow) ElementType[myCapacity];
List::List(int maxSize)
: mySize(0), myCapacity(maxSize)
{ if (myArrayPtr == 0) // check if memory available
myArrayPtr = new(nothrow) ElementType[maxSize];
{
assert(myArrayPtr != 0);
} cerr << "*Inadequate memory to allocate stack ***\n";
exit(1);
//--- Definition of class destructor
}
List::~List()
{ }
delete [] myArrayPtr; //--- Copy origList's array into this new array
}
for(int i = 0; i < myCapacity; i++)
//--- Definition of the copy constructor myArrayPtr[i] = origList.myArrayPtr[i];
List::List(const List & origList) }
: mySize(origList.mySize), myCapacity(origList.myCapacity)
return *this;
{ }
//--- Get new array for copy
myArrayPtr = new(nothrow) ElementType[myCapacity];
//--- Definition of empty()
if (myArrayPtr != 0) // check if memory available bool List::empty() const
//--- Copy origList's array into this new array {
for(int i = 0; i < myCapacity; i++)
return mySize == 0;
myArrayPtr[i] = origList.myArrayPtr[i];
else }
{
cerr << "*Inadequate memory to allocate stack ***\n";
//--- Definition of display()
exit(1);
} void List::display(ostream & out) const
} {
for (int i = 0; i < mySize; i++)
//--- Definition of the assignment operator
List & List::operator=(const List & origList) out << myArrayPtr[i] << " ";
{ }
if (this != &origList) // check for list = list
{
mySize = origList.mySize; //--- Definition of output operator
ostream & operator<< (ostream & out, const List & aList)
{
aList.display(out);
return out; 19
}
Implementation (cont’d)
//--- Definition of insert()
//--- Definition of erase()
void List::insert(ElementType item, int pos)
void List::erase(int pos)
{
{
if (mySize == myCapacity)
if (mySize == 0)
{ {
cerr << "*** No space for list element -- terminating " cerr << "*** List is empty ***\n";
"execution ***\n"; return;
exit(1); }
} if (pos < 0 || pos >= mySize)
if (pos < 0 || pos > mySize) {
{ cerr << "Illegal location to delete -- " << pos
<< ". List unchanged. ***\n";
cerr << "*** Illegal location to insert -- " << pos
return;
<< ". List unchanged. ***\n";
}
return;
} // Shift array elements left to close the gap
for(int i = pos; i < mySize; i++)
// First shift array elements right to make room for item myArrayPtr[i] = myArrayPtr[i + 1];

for(int i = mySize; i > pos; i--) // Decrease list size


myArrayPtr[i] = myArrayPtr[i - 1]; mySize--;
}

// Now insert item at position pos and increase list size


myArrayPtr[pos] = item;
mySize++;
}

20
Dynamic-Allocation for List Class

• Now possible to specify different sized lists


cin >> maxListSize;
List aList1 (maxListSize);
List aList2 (500);

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 21
Education, Inc. All rights reserved. 0-13-140909-3
New Functions Needed
• Destructor
– When class object goes out of scope the pointer
to this memory is reclaimed automatically

– The dynamically allocated memory is not

– The destructor reclaims dynamically allocated


memory
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 22
Education, Inc. All rights reserved. 0-13-140909-3
New Functions Needed
• Copy Constructor – makes a "deep copy" of an
object
– When argument passed as value parameter
– When function returns a local object
– When temporary storage of object needed
– When object initialized by another in a declaration

• If copy is not made,


observe results
(aliasing problem,
"shallow" copy)
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 23
Education, Inc. All rights reserved. 0-13-140909-3
New Functions Needed
• Assignment operator
– Default assignment operator makes shallow
copy
– Can cause memory leak, dynamically-allocated
memory has nothing pointing to it

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 24
Education, Inc. All rights reserved. 0-13-140909-3
Notes on Class Design
If a class allocates memory at run time using
the new, then it should provide …
• A destructor
• A copy constructor
• An assignment operator
• Three Amigos
• Note Fig. 6.3 which exercises constructors
and destructor
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 25
Education, Inc. All rights reserved. 0-13-140909-3
Calls to Constructors and Destructor
#include <iostream>
using namespace std; cout << "\n*** Next Statement: List list2 = list1;\n";
List list2 = list1;
#include "List.h" cout << "\n*** Next Statement: print(list2);\n";
print(list2);
void print (List aList) cout << "\n*** Next Statement: List list3;\n";
/*------------------------------------------------------------------------- List list3;
Function to print a list.
cout << "\n*** Next Statement: list3 = list2;\n";
list3 = list2;
Precondition: aList is a value parameter
cout << "\n*** Next Statement: print(list3);\n";
Postcondition: Contents of aList have been displayed
-------------------------------------------------------------------------*/
print(list3);
{
cout << aList << endl; cout << "\n*** Next Statement: return 0;\n";
} return 0;
}
int main()
{
int listLimit;
cout << "Enter maximum number of list elements: ";
cin >> listLimit;

cout << "\n*** Next Statement: List list1(listLimit);\n";


List list1(listLimit);
for (int i = 0; i <= 4; i++)
{
cout << "*** Next Statement: list1.insert(i, i);\n";
list1.insert(i, i);
}
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 26
Education, Inc. All rights reserved. 0-13-140909-3
Execution Trace for Constructors and
Destructor

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 27
Education, Inc. All rights reserved. 0-13-140909-3
Future Improvements to Our
List Class
• Problem 1: Array used has fixed capacity
Solution:
– If larger array needed during program execution
– Allocate, copy smaller array to the new one
• Problem 2: Class bound to one type at a
time
Solution:
– Create multiple List classes with differing
names
– Use class template
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 28
Education, Inc. All rights reserved. 0-13-140909-3
Recall Inefficiency of
Array-Implemented List
• insert() and erase() functions inefficient for
dynamic lists
– Those that change frequently
– Those with many insertions and deletions

So …
We look for an alternative implementation.

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 29
Education, Inc. All rights reserved. 0-13-140909-3
Linked List
For the array-based implementation:
1. First element is at location 0
2. Successor of item at location i is at location
i + 1
3. End is at location size – 1
Fix:
1. Remove requirement that list elements be stored
in consecutive location.
2. But then need a "link" that connects each element
to its successor
Linked Lists !!
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 30
Education, Inc. All rights reserved. 0-13-140909-3
Linked List
• Linked list nodes contain
– Data part – stores an element of the list
– Next part – stores link/pointer to next element
(when no next element, null value)

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 31
Education, Inc. All rights reserved. 0-13-140909-3
Linked Lists Operations
• Construction: first = null_value;
• Empty: first == null_value?
• Traverse
– Initialize a variable ptr to point to first node

– Process data where ptr points

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 32
Education, Inc. All rights reserved. 0-13-140909-3
Linked Lists Operations
• Traverse (ctd)
– set ptr = ptr->next, process ptr->data

– Continue until ptr == null

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 33
Education, Inc. All rights reserved. 0-13-140909-3
Operations: Insertion
predptr

• Insertion newptr
20

– To insert 20 after 17
– Need address of item before point of insertion
– predptr points to the node containing 17
– Get a new node pointed to by newptr and store 20 in it
– Set the next pointer of this new node equal to the next
pointer in its predecessor, thus making it point to its
successor.
– Reset the next pointer of its predecessor to point to this
new node
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 34
Education, Inc. All rights reserved. 0-13-140909-3
Operations: Insertion
• Note: insertion also works at end of list
– pointer member of new node set to null
• Insertion at the beginning of the list
– predptr must be set to first
– pointer member of newptr set to that value
– first set to value of newptr

 Note: In all cases, no shifting of list


elements is required !

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 35
Education, Inc. All rights reserved. 0-13-140909-3
Operations: Deletion
predptr ptr

To free
• Delete node containing 22 from list. space
– Suppose ptr points to the node to be deleted
– predptr points to its predecessor (the 17)
• Do a bypass operation:
– Set the next pointer in the predecessor to
point to the successor of the node to be deleted
– Deallocate the node being deleted.
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 36
Education, Inc. All rights reserved. 0-13-140909-3
Linked Lists - Advantages
• Access any item as long as external link
to first item maintained
• Insert new item without shifting
• Delete existing item without shifting
• Can expand/contract as necessary

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 37
Education, Inc. All rights reserved. 0-13-140909-3
Linked Lists - Disadvantages
• Overhead of links:
– used only internally, pure overhead
• If dynamic, must provide
– destructor
– copy constructor
• No longer have direct access to each element of
the list
– Many sorting algorithms need direct access
– Binary search needs direct access
• Access of nth item now less efficient
– must go through first element, and then second, and
then third, etc.
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 38
Education, Inc. All rights reserved. 0-13-140909-3
Linked Lists - Disadvantages
• List-processing algorithms that require fast access to each
element cannot be done as efficiently with linked lists.
• Consider adding an element at the end of the list

Array Linked List


a[size++] = value; Get a new node;
set data part = value
next part = null_value
If list is empty
Set first to point to new node.
Else
Traverse list to find last node
This is the inefficient part Set next part of last node to
point to new node.
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 39
Education, Inc. All rights reserved. 0-13-140909-3
Using C++ Pointers and Classes
• To Implement Nodes
class Node
{
public:
DataType data;
Node * next;
};

• Note: The definition of a Node is recursive


– (or self-referential)
• It uses the name Node in its definition
• The next member is defined as a pointer to a Node
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 40
Education, Inc. All rights reserved. 0-13-140909-3
Working with Nodes
• Declaring pointers
Node * ptr; or
typedef Node * NodePointer;
NodePointer ptr;
• Allocate and deallocate
ptr = new Node; delete ptr;
• Access the data and next part of node
(*ptr).data and (*ptr).next
or
ptr->data and ptr->next

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 41
Education, Inc. All rights reserved. 0-13-140909-3
Working with Nodes
• Note data members class Node
{ public:
are public DataType data;
Node * next; };

• This class declaration will be placed inside


another class declaration for List
• The data members data and next of
struct Node will be public inside the class
– will be accessible to the member and friend
functions
– will not be accessible outside the class
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 42
Education, Inc. All rights reserved. 0-13-140909-3
Class List
typedef int ElementType;
class List
{
private: • data is public inside
class Node class Node
{ • class Node is private
public: inside List
ElementType data;
Node * next;
};
typedef Node * NodePointer;
. . .

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 43
Education, Inc. All rights reserved. 0-13-140909-3
Data Members for Linked-List
Implementation

• A linked list will be characterized by:


– A pointer to the first node in the list.
– Each node contains a pointer to the next node in
the list
– The last node contains a null pointer
• As a variation first may
– be a structure
– also contain a count of the elements in the list
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 44
Education, Inc. All rights reserved. 0-13-140909-3
Function Members for Linked-List
Implementation
• Constructor
– Make first a null pointer and 0

– set mySize to 0
• Destructor
– Nodes are dynamically allocated by new
– Default destructor will not specify the delete
• All the nodes from that point on would be
"marooned memory"
– A destructor must be explicitly implemented to
do the delete
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 45
Education, Inc. All rights reserved. 0-13-140909-3
Function Members for Linked-List
Implementation

Shallow Copy

• Copy constructor for deep copy


– By default, when a copy is made of a List
object, it only gets the head pointer
– Copy constructor will make a new linked list of
nodes to which copy will point to
Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 46
Education, Inc. All rights reserved. 0-13-140909-3
Array-Based Implementation of
Linked Lists
• Node structure
struct NodeType
Shh! Here shows how
C++ standard list class
{ template implements
DataType data; linked list

int next;
};
const int NULL_VALUE = -1;
// Storage Pool
const int NUMNODES = 2048;
NodeType node [NUMNODES];
int free;

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 47
Education, Inc. All rights reserved. 0-13-140909-3
Array-Based Implementation of
Linked Lists
• Given a list with names

• Implementation looks
like this

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 48
Education, Inc. All rights reserved. 0-13-140909-3
Array-Based Implementation of
Linked Lists
• To traverse
ptr = first;
while (ptr != NULL_VALUE)
{
// process data at node[ptr].data
ptr = node[ptr].next;
}

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 49
Education, Inc. All rights reserved. 0-13-140909-3
Organizing Storage Pool
• In the array
– Some locations are storing nodes of the list
– Others are free nodes, available for new data
• Could initially link all nodes as free

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 50
Education, Inc. All rights reserved. 0-13-140909-3
Organizing Storage Pool
• Then use nodes as required for adds and
inserts
– Variable free points to beginning of linked nodes
of storage pool

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 51
Education, Inc. All rights reserved. 0-13-140909-3
Organizing Storage Pool
• Links to actual list and storage pool
maintained as new data nodes are added
and deleted

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 52
Education, Inc. All rights reserved. 0-13-140909-3
A Peek in list’s Memory
Management
• To reduce the inefficiency of using the
system’s heap manager for large numbers of
allocations and deallocations, it does its own
management of a free list of available nodes

• It uses new only when this free list is empty

• Rest will be discussed later


Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 53
Education, Inc. All rights reserved. 0-13-140909-3
“Programming Proverbs” -1
Don’t take a long walk off a short linked list.

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 54
Education, Inc. All rights reserved. 0-13-140909-3
“Programming Proverbs” -1
Don’t take a long walk off a short linked list.

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 55
Education, Inc. All rights reserved. 0-13-140909-3
“Programming Proverbs” -1
Don’t take a long walk off a short linked list.

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 56
Education, Inc. All rights reserved. 0-13-140909-3
“Programming Proverbs” -1
Don’t take a long walk off a short linked list.

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 57
Education, Inc. All rights reserved. 0-13-140909-3
“Programming Proverbs” -2
You can’t get water from an empty well.

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 58
Education, Inc. All rights reserved. 0-13-140909-3
“Programming Proverbs” -3
Don’t burn bridges before you cross them.

Nyhoff, ADTs, Data Structures and Problem Solving with C++, Second Edition, © 2005 Pearson 59
Education, Inc. All rights reserved. 0-13-140909-3

You might also like