1 / 15

# CS 201 Computer Systems Programming Chapter 7 “ Printing Binary Trees ” - PowerPoint PPT Presentation

Herbert G. Mayer, PSU CS Status 7/9/2014. CS 201 Computer Systems Programming Chapter 7 “ Printing Binary Trees ”. Syllabus. Arithmetic Expressions and Trees Infix Without Parentheses Infix With Parentheses Postfix Without Parentheses Prefix Without Parentheses Interesting Examples

I am the owner, or an agent authorized to act on behalf of the owner, of the copyrighted work described.

## PowerPoint Slideshow about ' CS 201 Computer Systems Programming Chapter 7 “ Printing Binary Trees ”' - edan

Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author.While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server.

- - - - - - - - - - - - - - - - - - - - - - - - - - E N D - - - - - - - - - - - - - - - - - - - - - - - - - -
Presentation Transcript

Status 7/9/2014

CS 201Computer Systems ProgrammingChapter 7“Printing Binary Trees”

• Arithmetic Expressions and Trees

• Infix Without Parentheses

• Infix With Parentheses

• Postfix Without Parentheses

• Prefix Without Parentheses

• Interesting Examples

• Use of Postfix

• Three typical notations for dyadic operations:

• Infix notation: write as the first the left operand, reading left-to-right, then list the dyadic operator, finally list the right operand

• For CPU: Order will not work for code emission, as the CPU needs both operands for processing the operator

• For humans: requires parentheses for proper operator precedence

• Note exception: programming language APL

• Postfix notation: write left operand first, then list the right operand, finally the operator

• This order will work for code emission, as operator has both operands available at processing time

• Needs no parentheses, and still obeys operator precedence

• Postfix notation AKA Polish Postfix, after Jan Łukasiewicz, 1920

• Prefix notation: First list the operator, next the first (left) operand, finally the second (right) operand

Infix: ( a + ( x ^ c ) )

Postfix: a x c ^ +

Prefix: + a ^ x c

• a + x ^ c

+

a

^

x

c

^ stands for exponentiation operator, with highest precedence: higher than * or /

which in turn have higher priority than + or -

Infix: ( ( x – a ) / b )

Postfix: x a – b /

Prefix: / – x a b

• ( x – a ) / b

/

-

b

x

a

/ stands for division operator, with higher precedence than, say, –

Infix: ( ( a ^ ( b – c ) ) / d )

Postfix: a b c - ^ d /

Prefix: / ^ a – b c d

Wrong: a ^ ( ( b – c ) / d )

• a ^ ( b – c ) / d

/

^

d

a

-

b

c

Data Structure to Print Trees

• Express tree and printing it via a C program

• To do so, define a NodeType data structure

• Thus a node needs to haver operand operator classification, and 2 possible subtrees

• For practical purposes, distinguish literals from variable (i.e. symbolic names)

• Represent the arithmetic expression as tree of such nodes

• And define functions that traverse the tree and print operands and operators in the right order

Data Structure to Print Trees

• // node has class: literal, identifier, or operator.

• // Parenthesized expressions have been reduced: no ( )

• typedef enum { Literal, Identifier, Operator } NodeClass;

• typedef struct NodeType * NodePtr; // forward

• // actual node structure; using the forward pointers

• typedef struct NodeType

• {

• NodeClass Class; // 3 classes. Not C++ ‘class’

• char Symbol; // stores ident or small literal

• int LitVal; // if Class == Literal: its value

• NodePtr Left; // left subtree

• NodePtr Right; // right subtree

• } s_node_tp;

• // Print in infix notation without parentheses ( )

• void Print_No_Paren( NodePtr Root )

• { // Print_No_Paren

• if ( Root ) {

• Print_No_Paren ( Root->Left );

• if ( Root->Class == Literal ) {

• printf( "%d", Root->LitVal );

• }else{

• printf( "%c", Root->Symbol );

• } //end if

• Print_No_Paren ( Root->Right );

• } //end if

• } //end Print_No_Paren

Input: ( a + x ) / b prints as: a + x / b misleading

• // Print in infix notation with parentheses ( and )

• // though prints too many ( ) pairs

• void Print_Infix( NodePtr Root )

• { // Print_Infix

• if ( Root ) {

• if ( Root->Class == Operator ) {

• printf( "(" );

• } //end if

• Print_Infix( Root->Left );

• if ( Root->Class == Literal ) {

• printf( "%d", Root->LitVal );

• }else{

• printf( "%c", Root->Symbol );

• } //end if

• Print_Infix( Root->Right );

• if ( Root->Class == Operator ) {

• printf( ")" );

• } //end if

• } //end if

• } //end Print_Infix

Input: ( a + x ) / b prints as: ( ( a + x ) / b ) -- OK

// Print in Polish Postfix notation, no parentheses

void Print_Postfix( NodePtr Root )

{ // Print_Postfix

if ( Root ) {

Print_Postfix( Root->Left );

Print_Postfix( Root->Right );

if ( Root->Class == Literal ) {

printf( "%d", Root->LitVal );

}else{

printf( "%c", Root->Symbol );

} //end if

} //end if

} //end Print_Postfix

Input: a ^ ( b – c ) / d prints as: a b c - ^ d / -- OK

// Prefix: operator executes when 2 operands found

void Print_Prefix( NodePtr Root )

{ // Print_Prefix

if ( Root ) {

if ( Root->Class == Literal ) {

printf( "%d", Root->LitVal );

}else{

printf( "%c", Root->Symbol );

} //end if

Print_Prefix( Root->Left );

Print_Prefix( Root->Right );

} //end if

} //end Print_Prefix

Input: ( a + x ) / b prints as: / + a x b -- OK

• Input 1: a + b * c ^ ( x – 2 * d ) / ( e – f )

Infix: ( a + ( ( b * ( c ^ ( x – ( 2 * d ) ) ) ) / ( e – f ) ) )

Postfix: a b c x 2 d * - ^ * e f - / +

Prefix: + a / * b ^ c – x * 2 d – e f

Input 2: 4 / x ^ ( k – l / m ) * 8 * x - & 9 + n

Infix: ( ( ( ( ( 4 / ( x ^ ( k - ( l / m ) ) ) ) * 8 ) * x ) - ( & 9 ) ) + n )

Postfix: 4 x k l m / - ^ / 8 * x * 9 & - n +

Prefix: + - * * / 4 ^ x – k / l m 8 x & 9 n

• Postfix, AKA Polish Postfix notation is a natural for code generation, not just for stack machines

• Operands are needed first: Two for dyadic, or one for monadic operations

• Once generated and available on stack, stack machine can execute the next operation

• Easy for compiler writer, natural for stack machine

• Stack poor for execution, as all references are through memory: top of stack

• Even a GPR architecture needs both operands available somewhere (in regs) to execute operator

• Łukasiewicz: http://www.calculator.org/Lukasiewicz.aspx

• http://cslibrary.stanford.edu/110/BinaryTrees.html