TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 1 J. Maluszynski, IDA, Linköpings Universitet, 2005. TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 2 J. Maluszynski, IDA, Linköpings Universitet, 2005. Lists Overview: Lists, stacks, queues A list L is a sequence of elements x0 xn 1 Sequences of data items appear in many applications; How to represent them in memory? What are typical and specific operations? How to implement them? Length L n empty list with length 0 L i selects the i-th element, xi [Lewis/Denenberg 3.1] Stack / Queue representation [Lewis/Denenberg 3.2] – in contiguous memory – in linked memory ADT List, Stack, Queue Concatenation L1 L2 x0 xn 1 , L2 for given lists L1 L1 L2 x0 xn 1 y0 ym 1 y0 ym 1 , Linked representations for traversals – singly linked lists – doubly linked lists [Lewis/Denenberg 3.3] [Lewis/Denenberg 3.4 p. 87] Stack implementation of recursive procedures. TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 3 [Lewis/Denenberg 3.3] J. Maluszynski, IDA, Linköpings Universitet, 2005. ADT List TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 4 ADT Stack (Last In First Out) abc Domain: lists cba top Operations: Access L i returns L i top Length L returns L Concat L1 L2 returns the concatenation L1 MakeEmptyList J. Maluszynski, IDA, Linköpings Universitet, 2005. L2 returns 0 and false otherwise Delete L i removes the i-th element of L Insert L i x inserts x before the i-th element of L d . . . Top S returns the top element of stack S Pop S removes and returns the top element of S Push S x adds x on the top of S MakeEmptyStack creates a new, empty stack IsEmptyStack S returns true iff S is empty IsEmptyList L returns true if L Operations: d . . . a b c top d . . . or an error code, if S is empty or an error code, if S is empty TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 5 J. Maluszynski, IDA, Linköpings Universitet, 2005. ADT Queue (First In First Out) TDDB57 DALG – Lecture 3: Lists, stacks, queues. first . . . a b c ... Operations: S Page 8 J. Maluszynski, IDA, Linköpings Universitet, 2005. Implementing a Stack in Linked Memory function MakeEmptyStack() : pointer S NewCell(StackListHead) Λ ptop S return S x2 Info Next x0 Info Next ptop function Pop( pointer S ) : dataitem if ptop S Λ then error else y ptop S x In f o y ptop S Next y FreeCell y return x ... procedure Push( pointer S, dataitem x ) y NewCell(StackListItem) In f o y x ptop S Next y ptop S y S x1 Info Next function IsEmptyStack( pointer S ) : boolean return Length S 0 function Top( pointer S ) : dataitem if Length S 0 then error else return A S Length S 1 J. Maluszynski, IDA, Linköpings Universitet, 2005. TDDB57 DALG – Lecture 3: Lists, stacks, queues. Implementing a Stack in Contiguous Memory (2) Length(S) = k + 1 <= n Page 7 A Length n function Pop( pointer S ) : dataitem if Length S 0 then error else Length S Length S 1 return A S Length S Typical application of ADT Queue: S n-1 0 Serving requests in incoming order. Did you try to book a SAS ticket by phone? 1) xk . . . . . . x0 0 n procedure Push( pointer S, dataitem x ) if Length S n then error else A S Length S x Length S Length S 1 x0 Front Q returns the first element of Q Dequeue Q removes and returns the first element of Q Enqueue Q x adds x at the end of Q MakeEmptyQueue creates a new, empty queue IsEmptyQueue Q returns true iff Q is empty . . . abc function MakeEmptyStack() : pointer NewCell(StackTableHead) S AS NewCell(table dataitem 0 Length S return S xk All operations take O 1 time. J. Maluszynski, IDA, Linköpings Universitet, 2005. Implementing a Stack in Contiguous Memory (1) last TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 6 + maximum size need not be known in advance – call to NewCell in each Push operation and to FreeCell in each Pop operation TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 9 J. Maluszynski, IDA, Linköpings Universitet, 2005. x0 . . . x0 x1 0 A x1 Info Next J. Maluszynski, IDA, Linköpings Universitet, 2005. x2 Info Next Info Next n-1 Q S Page 10 Implementing a Queue in Linked Memory Implementing a Queue by a Ring Buffer x2 x3 TDDB57 DALG – Lecture 3: Lists, stacks, queues. Back pFront pBack Pseudocode for the Queue operations: see course book, [Lewis/Denenberg, Algorithm 3.4] Front Length = k < n+1 + maximum size need not be known in advance + pointer pBack allows Enqueue to run in O 1 time (without pBack: need to traverse the entire list needs Θ k time) Pseudocode for the Queue operations: see course book, [Lewis/Denenberg, Algorithm 3.2] – overhead for NewCell in Enqueue, for FreeCell in Dequeue TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 11 J. Maluszynski, IDA, Linköpings Universitet, 2005. Implementing ADT List TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 12 Operations on Singly Linked Lists ADT List: operations Access, Delete, Insert, Concat, ... Contiguous memory representation: Access in O 1 ; what about other operations? L Insertion time Singly linked memory representation: Access, Delete, Insert require traversal up to i-th element Concat L1 L2 requires traversal of L1 but with a pBack pointer to the last element in O 1 P L function traverseSList ( pointer P, integer i ) : pointer return pointer to the i-th list item, if existing; Λ otherwise. while P Λ and i 0 P Next P i i 1 return P P Deletion L P J. Maluszynski, IDA, Linköpings Universitet, 2005. TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 13 J. Maluszynski, IDA, Linköpings Universitet, 2005. TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 14 J. Maluszynski, IDA, Linköpings Universitet, 2005. Doubly Linked Lists Backward Scan? Example: Room Guest Book, stored as singly linked list Format: (Date, Guest name), stored as a list ordered by date, for simplicity: at most one guest per day Info Info x0 x1 Prev Next Prev Info x2 Next Prev Next D Find out when was the previous visit of the guest of January 18 Prev Next (pFront) (pBack) A more efficient backward search is supported by doubly linked lists. Page 15 J. Maluszynski, IDA, Linköpings Universitet, 2005. Insertion in a Doubly Linked List Info Info x0 x2 x3 Prev Next ...... Prev Next The programming language implementation (compiler + run-time system) uses internally a stack to keep track of recursion. P Insertion: ...... function fact (integer n) : integer if n 0 then return 1 else f n f act n 1 ; return f Info Prev Next Page 16 Info Info x0 x2 Prev Prev Next J. Maluszynski, IDA, Linköpings Universitet, 2005. Stack application: Implementing recursive procedures ...... TDDB57 DALG – Lecture 3: Lists, stacks, queues. Info x3 Next Prev Next ...... for each function call: push arguments, local variables, return address (which form the function’s activation record), enter the procedure (free) 1 return address 1 fact(1) 2 return address 2 fact(2) 3 return address fact(3) 3 ... TDDB57 DALG – Lecture 3: Lists, stacks, queues. Info x1 P Prev Next on exit from the call: pop and discard the arguments go to the return address Run-time stack immediately before calling fact(0) TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 17 J. Maluszynski, IDA, Linköpings Universitet, 2005. TDDB57 DALG – Lecture 3: Lists, stacks, queues. Tail Recursion Page 18 J. Maluszynski, IDA, Linköpings Universitet, 2005. Tail-recursive function A recursive call is tail-recursive iff the first instruction after returning from it is return. Consider binarySearch: tail-recursive functions can be rewritten using iteration The recursive call in fact is not tail-recursive: function binarySearch (table key T a b , key K) : integer if a b then return 1 middle a b 2 if K T middle then return middle else if K T middle then return binarySearch T a middle 1 K else K T middle return binarySearch T middle 1 b K function fact (integer n) : integer if n 0 then return 1 else f n f act n 1 ; return f stack not needed: everything on stack will be discarded The first instruction after returning from the recursive call is multiplication n must be kept on stack Both recursive calls are tail-recursive. TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 19 J. Maluszynski, IDA, Linköpings Universitet, 2005. TDDB57 DALG – Lecture 3: Lists, stacks, queues. Page 20 Tail Recursion Elimination Tail-recursive Factorial Function Both recursive calls can be eliminated: f act can be rewritten by introducing a help function: function fact (integer n) : integer return f act2 n 1 function fact2 (integer n, integer f ) : integer if n 0 then return f else return f act2 n 1 n f f act2 is tail-recursive. space consumption after recursion elimination will be O 1 function binarySearch (table key T a b , key K) : integer (1) if a b then return 1 middle a b 2 if K T middle then return middle else if K T middle then was: return binarySearch T a middle 1 K b middle 1 else K T middle was: return binarySearch T a middle 1 K a middle 1 goto (1) J. Maluszynski, IDA, Linköpings Universitet, 2005.