Data Structures and Algorithm Design Review Data Structures

  • Slides: 112
Download presentation
Data Structures and Algorithm Design (Review)

Data Structures and Algorithm Design (Review)

Data Structures and Algorithm Design: Java basics Object-oriented design Stacks, queues, and deques Vectors,

Data Structures and Algorithm Design: Java basics Object-oriented design Stacks, queues, and deques Vectors, lists and sequences Trees and binary trees … …

Java Basics Class Modifiers abstract, final, public Variable Modifiers public, protected, private, static, final

Java Basics Class Modifiers abstract, final, public Variable Modifiers public, protected, private, static, final Methods Method Modifiers public, protected, private, abstract, final, static Arrays int[] a = new int[ 10 ]; float[][] x = new float[ 8 ][ 10 ]; a[ i ] = 138; x[ i ][ i + 1 ] = 2. 189 + x[ i ];

Java Basics Recursion public class Recursion. Example { public static int function(int n) {

Java Basics Recursion public class Recursion. Example { public static int function(int n) { if (n==0) return 1; if (n==1) return 1; if (n==2) return 3; else return 3*function(n-3) + 4*function(n-2) + 5*function(n-1); } public static void main(String []args){ int num = Integer. parse. Int(args[0]); System. out. println(num); int b = function(num); System. out. println("f =" + " " + b); }}

Object-Oriented Design Inheritance Polymorphism method overriding method overloading Keyword: this Exception Interface, Abstract Classes

Object-Oriented Design Inheritance Polymorphism method overriding method overloading Keyword: this Exception Interface, Abstract Classes Type casting

import java. util. *; import java. lang. *; interface Can. Fight { void fight

import java. util. *; import java. lang. *; interface Can. Fight { void fight ( ); } interface Can. Swim { void swim ( ); } interface Can. Fly {void fly ( ); } class Action. Character { public void fight( ) { }} class Hero extends Action. Character implements Can. Fight, Can. Swim, Can. Fly { public void fight ( ) {System. out. println(“Can fight!”); } public void swim ( ) {System. out. println(“Can swim!”); } public void fly ( ) {System. out. println(“Can fly!”); } }

public class Adventure { static void t(Can. Fight x) { x. fight(); } static

public class Adventure { static void t(Can. Fight x) { x. fight(); } static void u(Can. Swim x) { x. swim(); } static void v(Can. Fly x) { x. fly(); } static void w(Action. Character x) { x. fight(); } public static void main (String[ ] args) { Hero h = new Hero( ); t(h); //Treat it as a Can. Fight u(h); //Treat it as a Can. Swim v(h); //Treat it as a Can. Fly w(h); //Treat it as an Action. Character } }

Action. Character Can. Fight subclass Can. Swim Can. Fly implementation Hero instantiation h static

Action. Character Can. Fight subclass Can. Swim Can. Fly implementation Hero instantiation h static void t(Can. Fight x) { x. fight(); } static void u(Can. Swim x) { x. swim(); } static void v(Can. Fly x) { x. fly(); } static void w(Action. Character x) { x. fight(); } Hero h = new Hero( ) t(h); //Treat it as a Can. Fight u(h); //Treat it as a Can. Swim v(h); //Treat it as a Can. Fly w(h); //Treat it as an Action. Character

Stacks, Queues, and Deques Stacks Queues Deques Singly linked lists Doubly linked lists Sample

Stacks, Queues, and Deques Stacks Queues Deques Singly linked lists Doubly linked lists Sample case study application

Stacks Definition: A stack is a container of objects that are inserted and removed

Stacks Definition: A stack is a container of objects that are inserted and removed according to the last-in first-out (LIFO) principle. A stack S is an abstract data type (ADT) that supports following two fundamental methods: push(o): Insert object o at the top of the stack Input: Object; Output: None. pop(): Remove from the stack and return the top object on the stack; an error occurs if the stack is empty. Input: None; Output: Object

public interface Stack { public void push( Object element ); public Object pop() throws

public interface Stack { public void push( Object element ); public Object pop() throws Stack. Empty. Exception; public int size(); public boolean is. Empty(); public Object top() throws Stack. Empty. Exception; }

public class Array. Stack implements Stack { public static final int CAPACITY = 1000;

public class Array. Stack implements Stack { public static final int CAPACITY = 1000; private in capacity; private Object [] S; private int top = -1; public Array. Statck() { this( CAPACITY ); } public Array. Stack( int cap ) { capacity = cap; S = new Object[ capacity ]; } public int size() { return ( top + 1 ); }

public boolean is. Empty() { return( top < 0 ); } public void push(

public boolean is. Empty() { return( top < 0 ); } public void push( Object obj ) throws Stack. Full. Exception { if( size() == capacity ) throw new Stack. Full. Exception( "Stack overflow" ); S[ ++top ] = obj; } public Object top() throws Stack. Empty. Exception { if( is. Empty() ) throw new Stack. Empty. Exception( "Stack is empty. " ); return S[ top ]; }

public Object pop() throws Stack. Empty. Exception { Object elem; if( is. Empty() )

public Object pop() throws Stack. Empty. Exception { Object elem; if( is. Empty() ) throw new Stack. Empty. Exception( "Stack is Empty. " ); elem = S[ top ]; S[ top-- ] = null; return elem; } }

Sample Case Study Application We want to write a program to calculate the span

Sample Case Study Application We want to write a program to calculate the span of the stock’s price on a given day. The span of the stock’s price on a given day: The maximum number of the consecutive days up to the current day such that the stock price on each of those days has been less than or equal to the price on the current day.

Java Implementation

Java Implementation

Main idea: The span si on a certain day i can be easily computed

Main idea: The span si on a certain day i can be easily computed if we know the closest day preceding day i, such that the price on that day is higher than the price on day i. If such a preceding day exists for a day i, let us denote it with h(i), and otherwise let us define h(i) = -1. Then, si = i – h(i).

si = i – h(i). h(0) h(1) h(2) h(3) h(4) h(5) h(6) -1 0

si = i – h(i). h(0) h(1) h(2) h(3) h(4) h(5) h(6) -1 0 1 1 3 1 0 s 1 1 s 2 1 s 3 2 s 4 1 s 5 4 s 6 6 s 0 1

The problem is how to compute h(i) efficiently? Step 1: p 0 = 48.

The problem is how to compute h(i) efficiently? Step 1: p 0 = 48. 97. h(0) = -1, s 0 = 0 - h(0) = 0 – (-1) = 1 0 Day 0. It is possible that h(1) = 0. Step 2: p 1 = 47. 54. Pop days with prices less than or equal to p 1. At this point of time, we have only one element in the stack. It is 0 and p 0 > p 1. So h(1) = 0, s 1 = 1 - h(1) = 1 – 0 = 1. 1 0 Day 1. It is possible that h(2) = 1.

Step 3: p 2 = 45. 83. Pop days with prices less than or

Step 3: p 2 = 45. 83. Pop days with prices less than or equal to p 2. At this point of time, we have two elements in the stack. The top one is 1 and p 1 > p 2. So h(2) = 1, s 2 = 2 - h(2) = 2 – 1 = 1. 2 1 Day 2. It is possible that h(3) = 2. 0 Step 4: p 3 = 46. 34. Pop days with prices less than or equal to p 3. The top one will be taken out since p 3 > p 2. The second one is 1 and p 1 > p 3. So h(3) = 1, s 3 = 3 - h(3) = 3 – 1 = 2. 3 1 0 Day 3. It is possible that h(4) = 3.

Step 5: p 4 = 45. 68. Pop days with prices less than or

Step 5: p 4 = 45. 68. Pop days with prices less than or equal to p 4. The top one is 3 and p 3 > p 4. So h(4) = 3, s 4 = 4 - h(3) = 4 – 3 = 1. 4 3 Day 4. It is possible that h(5) = 4. 1 0 Step 6: p 5 = 46. 95. Pop days with prices less than or equal to p 3. The top two will be taken out since p 5 > p 4 and p 5 > p 3. The third one is 1 and p 1 > p 5. So h(5) = 1, s 5 = 5 - h(5) = 5 – 1 = 4. 5 1 0 Day 5. It is possible that h(6) = 5.

Step 7: p 6 = 48. 17. Pop days with prices less than or

Step 7: p 6 = 48. 17. Pop days with prices less than or equal to p 3. The top two will be taken out since p 6 > p 5 and p 6 > p 1. The third one is 0 and p 0 > p 6. So h(6) = 0, s 5 = 6 - h(6) = 6 – 0 = 6. 6 0 Day 6. The price on day 6. The process stops.

How to calculate 1+2 -3+4 -5+6+7 -8+9? public class Expression. Alculation { public static

How to calculate 1+2 -3+4 -5+6+7 -8+9? public class Expression. Alculation { public static void main(String [] args){ String s = "1+2 -3+4 -5+6+7 -8+9"; char c = 0; int result = 0; Object temp; Stack my. Stack = new Array. Stack(); my. Stack. push(new Integer(1)); for (int i = 1; i < s. length(); i++){ if (s. char. At(i) == ‘+’ || s. char. At(i) == ‘-’) my. Stack. push(new Character(s. char. At(i))); else { temp = my. Stack. pop(); result = ((Integer)my. Stack. pop()). int. Value(); c = s. char. At(i); if (temp == ‘+’) result = result + (c-'0'); else result = result - (c-'0'); my. Stack. push(new Integer(result)); } } System. out. println("Total is " + result); } }

Queues Definition: A queue is a container of objects that are inserted and removed

Queues Definition: A queue is a container of objects that are inserted and removed according to the first-in first-out (FIFO) principle.

class Array. Queue implements Queue { private Object[] elem; private int front, rear; private

class Array. Queue implements Queue { private Object[] elem; private int front, rear; private static final int DEFAULT_LENGTH = 100; private int length; public Array. Queue() { this(DEFAULT_LENGTH); } public Array. Queue(int length) { elem = new Object[length]; front = rear = 0; this. length = length; }

public void enqueue(Object element) throws Queue. Full. Exception { if (size()==length-1) throw new Queue.

public void enqueue(Object element) throws Queue. Full. Exception { if (size()==length-1) throw new Queue. Full. Exception(); else { elem[rear] = element; rear = (rear+1)%length; } }

public Object dequeue() throws Queue. Empty. Exception { if (is. Empty()) throw new Queue.

public Object dequeue() throws Queue. Empty. Exception { if (is. Empty()) throw new Queue. Empty. Exception(); else { Object temp = elem[front]; elem[front] = null; front = (front+1)%length; return temp; } } private boolean is. Full() { return (rear-front)==(length-1); }

public int size() { return (length-front+rear)%length; } public boolean is. Empty() { return front==rear;

public int size() { return (length-front+rear)%length; } public boolean is. Empty() { return front==rear; } public Object front() throws Queue. Empty. Exception { if (is. Empty()) throw new Queue. Empty. Exception(); else return elem[front]; } }

Queues Application: Search a tree in the breadth-first-manner enqueue(root); while (the queue is not

Queues Application: Search a tree in the breadth-first-manner enqueue(root); while (the queue is not empty) do {x : = dequeue; print(x); let x 1, x 2, …, xk be the children of x; for (i = k to 1) do {enqueue(xi); } }

Queues Sample trace: step 1: 1 step 5: step 2: step 4: step 3:

Queues Sample trace: step 1: 1 step 5: step 2: step 4: step 3: 2 3 3 4 5 6 7 visit(1) visit(2) visit(3) step 6: 5 6 7 8 9 10 11 visit(4) visit(5) … …

Singly Linked Lists

Singly Linked Lists

Class Node

Class Node

Node x = new Node(); x. set. Element(new String(“Baltimore”));

Node x = new Node(); x. set. Element(new String(“Baltimore”));

x. set. Next(head); head = x;

x. set. Next(head); head = x;

head = head. get. Next();

head = head. get. Next();

How to generate a singly linked list? public class Head_and_Tail { Node head; Node

How to generate a singly linked list? public class Head_and_Tail { Node head; Node tail; Head_and_Tail(Node x, Node y) { head = x; tail = y; } }

public class Generating. List { Node head = null; Node tail = null; Public

public class Generating. List { Node head = null; Node tail = null; Public Head_and_Tail linked_list () { Node x = null; for (int i = 0; i < 10; i++) {x = new Node(); x. set. Element(new Integer(i)); if (i == 0 ) {x. set. Next(null); tail = x; } else x. set. Next(head); head = x; } return new Head_and_Tail(head, tail); } }

Doubly Linked List Difference from singly linked lists: - each node contains two links.

Doubly Linked List Difference from singly linked lists: - each node contains two links. - two extra nodes: header and trailer, which contain no elements.

Class DLNode

Class DLNode

Have a new node: header trailer Baltimore Rome Seattle Toronto DLNode x = new

Have a new node: header trailer Baltimore Rome Seattle Toronto DLNode x = new DLNode(); x. set. Element(new String(“Toronto”)); (x. element new String(“Toronto”))

Update the links: trailer header Baltimore Rome Seattle Toronto x. set. Prev(header); x. set.

Update the links: trailer header Baltimore Rome Seattle Toronto x. set. Prev(header); x. set. Next(header. get. Next()); (header. get. Next()). set. Prev(x); header. set. Next(x); x. prev header; x. next header. next; header. next. prev x; header. next x;

Update the links: trailer header Toronto Baltimore Rome Seattle ((trailer. get. Prev()). get. Prev).

Update the links: trailer header Toronto Baltimore Rome Seattle ((trailer. get. Prev()). get. Prev). set. Next(trailer); trailer. set. Prev((trailer. get. Prev()); trailer. prev. next trailer; trailer. prev;

Deques Definition: A double-ended queue is a queue that supports insertion and deletion at

Deques Definition: A double-ended queue is a queue that supports insertion and deletion at both the front and the rear of the queue. A deque D is an abstract data type that supports the following four fundamental methods:

public interface Deque { void insert. First(Object e); void insert. Last(Object e); Object remove.

public interface Deque { void insert. First(Object e); void insert. Last(Object e); Object remove. First(); Object remove. Last(); Object first(); Object last(); int size(); boolean is. Empty(); }

Class My. Deque

Class My. Deque

Implementing Stacks and Queues with Deques

Implementing Stacks and Queues with Deques

Class Deque. Stack

Class Deque. Stack

Vectors, Lists, and Sequences Vectors Lists Sequences Iterators

Vectors, Lists, and Sequences Vectors Lists Sequences Iterators

Vector (interface) extends impl. Array. Vector (class) extends List (interface) extends Sequence (interface) impl.

Vector (interface) extends impl. Array. Vector (class) extends List (interface) extends Sequence (interface) impl. Array. Sequence (class) Node. List (class) extends Node. Sequence (class)

Vectors public interface Vector { public int size(); public boolean is. Empty(); public Object

Vectors public interface Vector { public int size(); public boolean is. Empty(); public Object elem. At. Rank(int r); public Object replace. At. Rank(int r, Object e); public void insert. At. Rank(int r, Object e); public Object remove. At. Rank(int r); }

public class Array. Vector implements Vector { private Object[] A; // array storing the

public class Array. Vector implements Vector { private Object[] A; // array storing the elements of the vector private int capacity = 16; // initial length of array A private int size = 0; // number of elements stored in the vector /** Creates the vector with initial capacity 16. */ public Array. Vector() { A = new Object[capacity]; }

public Object elem. At. Rank(int r) {return a[r]; } public int size() {return size;

public Object elem. At. Rank(int r) {return a[r]; } public int size() {return size; } public boolean is. Empty {return size()==0; } public Object replace. At. Rank (int r, Object e) { Object temp=a[r]; a[r]=e; return temp; }

 /** Inserts an element at the given rank. */ public void insert. At.

/** Inserts an element at the given rank. */ public void insert. At. Rank(int r, Object e) throws Boundary. Violation. Exception { check. Rank(r, size() + 1); if (size == capacity) { // an overflow capacity *= 2; Object[] B = new Object[capacity]; for (int i=0; i<size; i++) B[i] = A[i]; A = B; } for (int i=size-1; i>=r; i--) // shift elements up A[i+1] = A[i]; A[r] = e; size++; }

/** Removes the element stored at the given rank. */ public Object remove. At.

/** Removes the element stored at the given rank. */ public Object remove. At. Rank(int r) throws Boundary. Violation. Exception { check. Rank(r, size()); Object temp = A[r]; for (int i=r; i<size-1; i++) // shift elements down A[i] = A[i+1]; size--; return temp; } public int size( ) {return size; }

Lists public interface Position { Object element(); }

Lists public interface Position { Object element(); }

Position element(); impl. Dnode element(){…}; get. Next(){…}; get. Prev(){…}; set. Next(){…}; set. Prev(){…}; set.

Position element(); impl. Dnode element(){…}; get. Next(){…}; get. Prev(){…}; set. Next(){…}; set. Prev(){…}; set. Element(){…};

public interface List { /** Returns the number of elements in this list. */

public interface List { /** Returns the number of elements in this list. */ public int size(); /** Returns whether the list is empty. */ public boolean is. Empty(); /** Returns the first node in the list. */ public Position first(); /** Returns the last node in the list. */ public Position last(); /** Returns the node after a given node in the list. */ public Position next(Position p) throws Invalid. Position. Exception, Boundary. Violation. Exception; /** Returns the node before a given node in the list. */ public Position prev(Position p) throws Invalid. Position. Exception, Boundary. Violation. Exception;

/** Inserts an element at the front of the list. */ public Position insert.

/** Inserts an element at the front of the list. */ public Position insert. First(Object e); /** Inserts and element at the back of the list. */ public Position insert. Last(Object e); /** Inserts an element after the given node in the list. */ public Position insert. After(Position p, Object e) throws Invalid. Position. Exception; /** Inserts an element before the given node in the list. */ public Position insert. Before(Position p, Object e) throws Invalid. Position. Exception; /** Removes a node from the list. */ public Object remove(Position p) throws Invalid. Position. Exception; /** Replaces the element stored at the given node. */ public Object replace(Position p, Object e) throws Invalid. Position. Exception; }

Class Node. List

Class Node. List

List first(); last(); is. First(); is. Last(); before(); after(); replace. Element(); swap. Element(); insert.

List first(); last(); is. First(); is. Last(); before(); after(); replace. Element(); swap. Element(); insert. First(); insert. Last(); impl. Node. List … ….

Sequence

Sequence

Implementation of a sequence with a doubly linked list: Sequence ADT Position rank Doubly

Implementation of a sequence with a doubly linked list: Sequence ADT Position rank Doubly linked list Node at. Rank(r) rank. Of(p)

/** Implementation of a sequence by means of a doubly linked list. */ public

/** Implementation of a sequence by means of a doubly linked list. */ public class Node. Sequence extends Node. List implements Sequence { /** Checks whether the given rank is in the range [0, n - 1] */ protected void check. Rank(int r, int n) throws Boundary. Violation. Exception { if (r < 0 || r >= n) throw new Boundary. Violation. Exception("Illegal rank: " + r); }

 /** Returns the position containing the element at the given rank; * O(n)

/** Returns the position containing the element at the given rank; * O(n) time. */ public Position at. Rank (int rank) { DNode node; check. Rank(rank, size()); if (rank <= size()/2) { // scan forward from the head node = header. get. Next(); for (int i=0; i < rank; i++) node = node. get. Next(); } else { // scan backward from the tail node = trailer. get. Prev(); for (int i=1; i < size()-rank; i++) node = node. get. Prev(); } return node; }

 /** Gets an element at the given rank. */ public Object elem. At.

/** Gets an element at the given rank. */ public Object elem. At. Rank(int r) { return at. Rank(r). element(); } /** Returns the rank of a given position. */ public int rank. Of(Position p) { DNode node; node = header. get. Next(); for (int i=1; i < size(); i++) { if (p == node) return i; else node = node. get. Next(); } } }

 /** Inserts an element at the given rank; O(n) time. */ public void

/** Inserts an element at the given rank; O(n) time. */ public void insert. At. Rank (int rank, Object element) throws Boundary. Violation. Exception { check. Rank(rank, size() + 1); if (rank == size()) insert. Last(element); else { insert. Before(at. Rank(rank), element); } }

 /** Removes the element stored at the given rank; O(n) time. */ public

/** Removes the element stored at the given rank; O(n) time. */ public Object remove. At. Rank (int rank) throws Boundary. Violation. Exception { check. Rank(rank, size()); return remove(at. Rank(rank)); } public Object replace. At. Rank (int rank, object element) throws Boundadry. Violation. Exception { check. Rank(rank); return replace. Element(at. Rank(rank), element); } }

Implementing a Sequence with an Array

Implementing a Sequence with an Array

Iterator

Iterator

An implementation of the Iterator is always related to container, i. e. , a

An implementation of the Iterator is always related to container, i. e. , a vector, a list, or a sequence. The following is an exemplary implementation of the List Iterator. public class Position. Iterator implements Iterator { protected List list; // the underlying list protected Position cur; // the current (next) position public Position. Iterator() { } // default constructor public Position. Iterator(List L) { // preferred constructor list = L; if (list. is. Empty()) cur = null; // list is empty else cur = list. first(); // start with the first position }

public boolean has. Next() { return (cur != null); } public Object next() throws

public boolean has. Next() { return (cur != null); } public Object next() throws No. Such. Element. Exception { if (!has. Next()) throw new No. Such. Element. Exception("No next position"); Position to. Return = cur; if (cur == list. last()) cur = null; // no positions left else cur = list. next(cur); // move cursor to the next position return to. Return; } } class No. Such. Element. Exception extends Exception { public No. Such. Element. Exception() {super(); } public No. Such. Element. Exception(String s) { super(s); } }

In a similar way, we can establish an Element. Iterator as follows. public class

In a similar way, we can establish an Element. Iterator as follows. public class Element. Iterator implements Iterator { protected List list; // the underlying list protected Position cur; // the current (next) position protected Object element. Cur; // the current (next) element public Element. Iterator() { } // default constructor public Element. Iterator(List L) { // preferred constructor list = L; if (list. is. Empty()) cur = null; // list is empty else cur = list. first(); // start with the first position }

public boolean has. Next() { return (cur != null); } public Object next() throws

public boolean has. Next() { return (cur != null); } public Object next() throws No. Such. Element. Exception { if (!has. Next()) throw new No. Such. Element. Exception("No next position"); element. Cur = cur. element(); if (cur == list. last()) cur = null; // no positions left else cur = list. next(cur); // move cursor to the next position return element. Cur; } }

Trees What is a tree? Tree ADT Basic algorithms on trees Tree traversal

Trees What is a tree? Tree ADT Basic algorithms on trees Tree traversal

What is a tree?

What is a tree?

Tree Interface – Tree ADT public interface Tree { public int size(); public Boolean

Tree Interface – Tree ADT public interface Tree { public int size(); public Boolean is. Empty(); public Element. Iterator elements(); public Position. Iterator positions(); public void swap. Elements( Position v, Position w ); public Object replace. Element( Position v, Object e ); public Position root(); public Position parent( Position v ); public Position. Iterator children( Position v ); public boolean is. Internal( Position v ); public boolean is. External( Position v ); public boolean is. Root( Position v ); }

Ispectable. Container size is. Elements Ispectable. Position. Container positions Inspectable. Tree root parent children

Ispectable. Container size is. Elements Ispectable. Position. Container positions Inspectable. Tree root parent children is. Root is. Internal is. External Position. Container swap. Element replace. Element Tree

A Binary Tree Interface in Java

A Binary Tree Interface in Java

Class BTNode

Class BTNode

Interface Hierarchy for Positions Position element(); DNode element(){…}; get. Next(){…}; get. Prev(){…}; set. Next(){…};

Interface Hierarchy for Positions Position element(); DNode element(){…}; get. Next(){…}; get. Prev(){…}; set. Next(){…}; set. Prev(){…}; set. Element(){…}; BTNnode element(){…}; get. Left(){…}; get. Right(){…}; set. Left(){…}; set. Right(){…}; get. Parent(){…} set. Element(){…};

Also see the complete program for “Linked. Binary. Tree” posted on the home page

Also see the complete program for “Linked. Binary. Tree” posted on the home page of Dr. Yangjun Chen.

Ispectable. Container size is. Elements Ispectable. Position. Container positions Position. Container swap. Element replace.

Ispectable. Container size is. Elements Ispectable. Position. Container positions Position. Container swap. Element replace. Element Tree Inspectable. Tree root, parent, children, is. Root is. Internal, is. External Inspectable. Binary. Tree left. Child, right. Child, sibling Binary. Tree imple. Linked. Binary. Tree … …, replace. Element, swap. Element, expand. External, remove. Above. External

Basic Algorithms on Trees

Basic Algorithms on Trees

Inorder tree traversal

Inorder tree traversal

inorder(T, r) inorder(T, u) inorder(T, w) if … inorder(T, u) “visit” r 6 inorder(T,

inorder(T, r) inorder(T, u) inorder(T, w) if … inorder(T, u) “visit” r 6 inorder(T, w) “visit” u 2 “visit” w If … if … inorder (T, a) inorder (T, v) 1

inorder(T, v) inorder(T, x) if … inorder(T, x) “visit” v 4 If … inorder

inorder(T, v) inorder(T, x) if … inorder(T, x) “visit” v 4 If … inorder (T, y) “visit” x if … 3

inorder(T, y) if … “visit” y 5 if … inorder(T, a) inorder(T, b) “visit”

inorder(T, y) if … “visit” y 5 if … inorder(T, a) inorder(T, b) “visit” a 8 If … inorder (T, c) 7 9

Inorder traversal based on Stack data structure Algorithm Stack-control-inorder(T, v) establish stack S; S.

Inorder traversal based on Stack data structure Algorithm Stack-control-inorder(T, v) establish stack S; S. push(v); while (S is not empty) do {u : = S. pop(); if u is leaf or u is marked, visit u; else {let v 1 and v 2 be the left and right child node of v, respectively; S. push(v 2); mark u; S. push(u*); S. push(v 1); } }

r x v* y r* a print(r) a u r* a w u* v

r x v* y r* a print(r) a u r* a w u* v r* a v* y print(x) r* a b a* c u* v print(w) r* a y print(v) r* a a* c v print(u) r* a print(b) print(y) print(a) c print(c)