CS308 Compiler Principles Syntax Analyzer Li Jiang

Similar documents
LALR Parsing. What Yacc and most compilers employ.

LR Parsing Techniques

Bottom up parsing. The sentential forms happen to be a right most derivation in the reverse order. S a A B e a A d e. a A d e a A B e S.

3. Syntax Analysis. Andrea Polini. Formal Languages and Compilers Master in Computer Science University of Camerino

Principles of Programming Languages

UNIT-III BOTTOM-UP PARSING

Section A. A grammar that produces more than one parse tree for some sentences is said to be ambiguous.

Syntax Analysis (Parsing)

LR Parsing Techniques


Table-Driven Parsing

Parsing. Handle, viable prefix, items, closures, goto s LR(k): SLR(1), LR(1), LALR(1)

Syn S t yn a t x a Ana x lysi y s si 1

PART 3 - SYNTAX ANALYSIS. F. Wotawa TU Graz) Compiler Construction Summer term / 309


Bottom-up parsing. Bottom-Up Parsing. Recall. Goal: For a grammar G, withstartsymbols, any string α such that S α is called a sentential form

A left-sentential form is a sentential form that occurs in the leftmost derivation of some sentence.

MODULE 14 SLR PARSER LR(0) ITEMS

Syntax Analysis. Martin Sulzmann. Martin Sulzmann Syntax Analysis 1 / 38

Parsing. Roadmap. > Context-free grammars > Derivations and precedence > Top-down parsing > Left-recursion > Look-ahead > Table-driven parsing

Acknowledgements. The slides for this lecture are a modified versions of the offering by Prof. Sanjeev K Aggarwal

Syntax Analysis. Amitabha Sanyal. ( as) Department of Computer Science and Engineering, Indian Institute of Technology, Bombay

Top down vs. bottom up parsing

8 Parsing. Parsing. Top Down Parsing Methods. Parsing complexity. Top down vs. bottom up parsing. Top down vs. bottom up parsing

Compilerconstructie. najaar Rudy van Vliet kamer 140 Snellius, tel rvvliet(at)liacs(dot)nl. college 3, vrijdag 22 september 2017

Formal Languages and Compilers Lecture VII Part 3: Syntactic A

Introduction to parsers

MIT Parse Table Construction. Martin Rinard Laboratory for Computer Science Massachusetts Institute of Technology

Bottom-Up Parsing. Parser Generation. LR Parsing. Constructing LR Parser

CSE P 501 Compilers. LR Parsing Hal Perkins Spring UW CSE P 501 Spring 2018 D-1

CA Compiler Construction

CMSC 330: Organization of Programming Languages

Compiler Construction 2016/2017 Syntax Analysis

Concepts Introduced in Chapter 4

CS 321 Programming Languages and Compilers. VI. Parsing

3. Parsing. Oscar Nierstrasz

Compiler Design 1. Bottom-UP Parsing. Goutam Biswas. Lect 6

SYED AMMAL ENGINEERING COLLEGE (An ISO 9001:2008 Certified Institution) Dr. E.M. Abdullah Campus, Ramanathapuram

Downloaded from Page 1. LR Parsing

Principles of Compiler Design Presented by, R.Venkadeshan,M.Tech-IT, Lecturer /CSE Dept, Chettinad College of Engineering &Technology

Parsing Wrapup. Roadmap (Where are we?) Last lecture Shift-reduce parser LR(1) parsing. This lecture LR(1) parsing

Context-free grammars

Note that for recursive descent to work, if A ::= B1 B2 is a grammar rule we need First k (B1) disjoint from First k (B2).

Wednesday, September 9, 15. Parsers

Parsers. What is a parser. Languages. Agenda. Terminology. Languages. A parser has two jobs:

UNIT III & IV. Bottom up parsing

Compiler Construction: Parsing

Principle of Compilers Lecture IV Part 4: Syntactic Analysis. Alessandro Artale

Let us construct the LR(1) items for the grammar given below to construct the LALR parsing table.

LR Parsers. Aditi Raste, CCOEW

Formal Languages and Compilers Lecture VII Part 4: Syntactic A

Where We Are. CMSC 330: Organization of Programming Languages. This Lecture. Programming Languages. Motivation for Grammars

Syntax Analysis Part I

CMSC 330: Organization of Programming Languages. Architecture of Compilers, Interpreters

VIVA QUESTIONS WITH ANSWERS

LR Parsing. Leftmost and Rightmost Derivations. Compiler Design CSE 504. Derivations for id + id: T id = id+id. 1 Shift-Reduce Parsing.

CSE 401 Compilers. LR Parsing Hal Perkins Autumn /10/ Hal Perkins & UW CSE D-1

Parsers. Xiaokang Qiu Purdue University. August 31, 2018 ECE 468

Parser Generation. Bottom-Up Parsing. Constructing LR Parser. LR Parsing. Construct parse tree bottom-up --- from leaves to the root

Monday, September 13, Parsers

Syntactic Analysis. Chapter 4. Compiler Construction Syntactic Analysis 1

Compiler Design. Spring Syntactic Analysis. Sample Exercises and Solutions. Prof. Pedro C. Diniz

CSC 4181 Compiler Construction. Parsing. Outline. Introduction

Architecture of Compilers, Interpreters. CMSC 330: Organization of Programming Languages. Front End Scanner and Parser. Implementing the Front End

Parsing. Rupesh Nasre. CS3300 Compiler Design IIT Madras July 2018

The analysis part breaks up the source program into constituent pieces and creates an intermediate representation of the source program.

General Overview of Compiler

S Y N T A X A N A L Y S I S LR

Syntax Analyzer --- Parser

Table-driven using an explicit stack (no recursion!). Stack can be viewed as containing both terminals and non-terminals.

Syntax Analysis: Context-free Grammars, Pushdown Automata and Parsing Part - 4. Y.N. Srikant

CMSC 330: Organization of Programming Languages. Context Free Grammars

QUESTIONS RELATED TO UNIT I, II And III

CMSC 330: Organization of Programming Languages. Context Free Grammars

CMSC 330: Organization of Programming Languages

CMSC 330: Organization of Programming Languages

LR Parsing, Part 2. Constructing Parse Tables. An NFA Recognizing Viable Prefixes. Computing the Closure. GOTO Function and DFA States

Wednesday, August 31, Parsers

shift-reduce parsing

Compilers. Yannis Smaragdakis, U. Athens (original slides by Sam

CS2210: Compiler Construction Syntax Analysis Syntax Analysis

COP4020 Programming Languages. Syntax Prof. Robert van Engelen

Syntactic Analysis. Top-Down Parsing

LR Parsing - The Items

Gujarat Technological University Sankalchand Patel College of Engineering, Visnagar B.E. Semester VII (CE) July-Nov Compiler Design (170701)

Top-Down Parsing and Intro to Bottom-Up Parsing. Lecture 7

DEPARTMENT OF INFORMATION TECHNOLOGY / COMPUTER SCIENCE AND ENGINEERING UNIT -1-INTRODUCTION TO COMPILERS 2 MARK QUESTIONS

EDAN65: Compilers, Lecture 06 A LR parsing. Görel Hedin Revised:

VALLIAMMAI ENGNIEERING COLLEGE SRM Nagar, Kattankulathur

Chapter 3. Parsing #1

DEPARTMENT OF COMPUTER SCIENCE & ENGINEERING Subject Name: CS2352 Principles of Compiler Design Year/Sem : III/VI

Bottom-Up Parsing. Lecture 11-12

Part 3. Syntax analysis. Syntax analysis 96

Outline. 1 Introduction. 2 Context-free Grammars and Languages. 3 Top-down Deterministic Parsing. 4 Bottom-up Deterministic Parsing

Question Bank. 10CS63:Compiler Design

Syntax Analysis. Prof. James L. Frankel Harvard University. Version of 6:43 PM 6-Feb-2018 Copyright 2018, 2015 James L. Frankel. All rights reserved.

CS415 Compilers. Syntax Analysis. These slides are based on slides copyrighted by Keith Cooper, Ken Kennedy & Linda Torczon at Rice University

Top-Down Parsing and Intro to Bottom-Up Parsing. Lecture 7

Compiler Design 1. Top-Down Parsing. Goutam Biswas. Lect 5

Introduction to Syntax Analysis

Transcription:

CS308 Syntax Analyzer Li Jiang Department of Computer Science and Engineering Shanghai Jiao Tong University

Syntax Analyzer Syntax Analyzer creates the syntactic structure of the given source program. This syntactic structure is mostly a parse tree. Syntax Analyzer is also known as parser. The syntax of a program is described by a context-free grammar (CFG). We will use BNF (Backus-Naur Form) notation in the description of CFGs. The syntax analyzer (parser) checks whether a given source program satisfies the rules implied by a context-free grammar or not. If it satisfies, the parser creates the parse tree of that program. Otherwise the parser gives the error messages. A context-free grammar gives a precise syntactic specification of a programming language. the design of the grammar is an initial phase of the design of a compiler. a grammar can be directly converted into a parser by some tools. 2

Parser / Syntax Analyzer Parser works on a stream of tokens. The smallest item is a token. source program Lexical Analyzer token get next token Parser parse tree The parser obtains a string of tokens from the lexical analyzer, and verifies that the string of token names can be generated by the grammar for the source language. 3

Parsers Cont d We categorize the parsers into two groups: 1. Top-Down Parser the parse tree is created top to bottom, starting from the root. 2. Bottom-Up Parser the parse is created bottom to top; starting from the leaves Both scan the input from left to right (one symbol at a time). Efficient top-down and bottom-up parsers can be implemented only for sub-classes of context-free grammars. LL for top-down parsing LR for bottom-up parsing 4

Outline Context Free Grammar Parse Tree Top-down Parser Bottom-up Parser 5

Context-Free Grammars Recursive structures of a programming language are defined by a context-free grammar. A context-free grammar consists of: A finite set of terminals (in our case, these will be the set of tokens) A finite set of non-terminals (syntactic-variables) A finite set of production rules in the following form A where A is a non-terminal and is a string of terminals and non-terminals (including the empty string) A start symbol (one of the non-terminal symbol) Example: E E + E E E E * E E / E - E E ( E ) E id 6

Derivations E E+E E derives E+E (E+E derives from E) we can replace E by E+E we have to have a production rule E E+E in our grammar. E E+E id+e id+id A sequence of replacements of non-terminal symbols is called a derivation of id+id from E. In general a derivation step is A if there is a production rule A in our grammar where and are arbitrary strings of terminal and non-terminal symbols 1 2... n ( n derives from 1 or 1 derives n ) * + : derives in one step : derives in zero or more steps : derives in one or more steps 7

CFG - Terminology L(G) is the language of grammar G (the language generated by G). It is a set of sentences. A sentence of L(G) is a string of terminal symbols of G. If S is the start symbol of G then is a sentence of L(G) iff S *, where is a string of terminals of G. If G is a context-free grammar, L(G) is a context-free language. Two grammars are equivalent if they produce the same language. * S - If contains non-terminals, it is called as a sentential form of G. - If does not contain non-terminals, it is called as a sentence of G. 8

Derivation Example E -E -(E) -(E+E) -(id+e) -(id+id) OR E -E -(E) -(E+E) -(E+id) -(id+id) At each derivation step, we can choose any of the non-terminal in the sentential form of G for the replacement. If we always choose the left-most non-terminal in each derivation step, this derivation is called as left-most derivation. If we always choose the right-most non-terminal in each derivation step, this derivation is called as right-most derivation. 9

Left-Most and Right-Most Derivations Left-Most Derivation E -E -(E) -(E+E) -(id+e) -(id+id) lm Right-Most Derivation E -E -(E) -(E+E) -(E+id) -(id+id) rm lm rm lm rm The top-down parsers try to find the left-most derivation of the given source program. The bottom-up parsers try to find the right-most derivation of the given source program in the reverse order. lm rm lm rm 10

Quiz The set of all strings of 0s and 1s that are palindrome; that is, the string reads the same backward as forward. The set of all strings of 0s and 1s with an equal number of 0s and 1s. 11

Outline Context Free Grammar Parse Tree Top-down Parser Bottom-up Parser 12

Parse Tree A parse tree is a graphical representation of a derivation. Inner nodes of a parse tree are non-terminal symbols. The leaves of a parse tree are terminal symbols. E E E -E -(E) - E - E -(E+E) ( E ) E E - E - E -(id+e) -(id+id) ( E ) ( E ) E + E E + E id id id - E ( E E ) E + E 13

Ambiguity A grammar produces more than one parse tree for a sentence is an ambiguous grammar. E E+E id+e id+e*e id+id*e id+id*id E E + id E id E * E id E E*E E+E*E id+e*e id+id*e id+id*id E E + id E * E E id id 14

Ambiguity Cont d For the most parsers, the grammar must be unambiguous. unambiguous grammar unique selection of the parse tree for a sentence We should eliminate the ambiguity in the grammar during the design phase of the compiler. An ambiguous grammar should be rewritten to eliminate the ambiguity. How? We have to prefer one of the parse trees of a sentence (generated by an ambiguous grammar) to disambiguate that grammar to restrict to this choice. 15

Ambiguity Elimination Cont d Ambiguous grammars (because of ambiguous operators) can be disambiguated according to the precedence and associativity rules. E E+E E*E E^E id (E) disambiguate the grammar precedence: E E+T T T T*F F F G^F G G id (E) ^ (right to left) * (left to right) + (left to right) 16

Ambiguity Cont d stmt if expr then stmt if expr then stmt else stmt otherstmts if E 1 then if E 2 then S 1 else S 2 stmt if expr then stmt else stmt if expr stmt then stmt E 1 if expr then stmt S 2 E 1 if expr then stmt else stmt E 2 S 1 E 2 S 1 S 2 1 2 17

Ambiguity Elimination Cont d We prefer the parse tree, in which else matches with the closest if. So, we can disambiguate our grammar to reflect this choice. The unambiguous grammar will be: stmt matchedstmt unmatchedstmt matchedstmt if expr then matchedstmt else matchedstmt otherstmts unmatchedstmt if expr then stmt if expr then matchedstmt else unmatchedstmt Try again! if E 1 then if E 2 then S 1 else S 2 18

Left Recursion A grammar is left recursive if it has a nonterminal A such that there is a derivation. + A A for some string Top-down parsing techniques cannot handle leftrecursive grammars. So, we have to convert our left-recursive grammar into an equivalent grammar which is not leftrecursive. The left-recursion may appear in a single step of the derivation (immediate left-recursion), or may appear in more than one step of the derivation. 19

Immediate Left-Recursion Elimination A A where does not start with A eliminate immediate left recursion A A A A an equivalent grammar In general: A A 1... A m 1... n where 1... n do not start with A eliminate immediate left recursion A 1 A... n A A 1 A... m A an equivalent grammar 20

Immediate Left-Recursion Elimination Example E E+T T T T*F F F id (E) eliminate immediate left recursion E T E E +T E T F T T *F T F id (E) 21

Non-Immediate Left-Recursion Just eliminating the immediate left-recursion is not enough to get a left-recursion free grammar. S Aa b A Sc d This grammar is still left-recursive. S Aa Sca A Sc Aac or causes to a left-recursion We have to eliminate all left-recursions from our grammar The Left-recursion is hidden! 22

Algorithm for Eliminating Left-Recursion - Arrange non-terminals in some order: A 1... A n - for i from 1 to n do { - for j from 1 to i-1 do { } replace each production A i A j by A i 1... k where A j 1... k Expose the hidden leftrecursion! } - eliminate immediate left-recursions among A i productions * 23

Example for Eliminating Left-Recursion S Aa b A Ac Sd f - Order of non-terminals: S, A for S: - we do not enter the inner loop. - there is no immediate left recursion in S. for A: - Replace A Sd with A Aad bd So, we will have A Ac Aad bd f - Eliminate the immediate left-recursion in A A bda fa A ca ada What about another order? So, the resulting equivalent grammar which is not left-recursive is: S Aa b A bda fa A ca ada 24

Example for Eliminating Left-Recursion Cont d S Aa b A Ac Sd f - Order of non-terminals: A, S for A: - Eliminate the immediate left-recursion in A A SdA fa A ca for S: - Replace S Aa with S SdA a fa a So, we will have S SdA a fa a b - Eliminate the immediate left-recursion in S S fa as bs S da as So, the resulting equivalent grammar which is not left-recursive is: S fa as bs S da as A SdA fa A ca See the difference? 25

Left-Factoring A predictive parser (a top-down parser without backtracking) needs the grammar to be leftfactored. grammar a new equivalent grammar suitable for predictive parsing stmt if expr then stmt else stmt if expr then stmt when we see if, we cannot know which production rule to choose to re-write stmt in the derivation. 26

In general, Left-Factoring Cont d A 1 2 where is non-empty and the first symbols of 1 and 2 (if they have one) are different. when processing we cannot know whether expand A to 1 or A to 2 But, if we re-write the grammar as follows A A A 1 2 so, we can immediately expand A to A 27

Algorithm for Left-Factoring For each non-terminal A with two or more alternatives (production rules) with a common non-empty prefix, say A 1... n 1... m where is the longest prefix convert it into A A 1... m A 1... n 28

Left-Factoring Example1 A abb ab cdg cdeb cdfb A aa cdg cdeb cdfb A bb B A aa cda A bb B A g eb fb 29

Left-Factoring Example2 A ad a ab abc b A aa b A d b bc A aa b A d ba A c 30

CFG vs. Regular Expression Grammar is a more powerful notation than regular expressions. Every language described by a regular expression can be described by a grammar. For each state i of the FA, create a nonterminal A i. If state i has a transition to state j on input a (include ε), add the production A i aa j. If i is an accepting state, add A i ε. If i is the start state, make A i be the start symbol of the grammar. A 0 ba 0 aa 1 A 1 aa 1 ba 2 (a b) * a b A 2 aa 1 ba 0 A 2 ε 31

CFG Vs. Regular Expression Cont d A language described by a grammar may not be described by a regular expression. Because regular expression/finite automata cannot count. Example: Language L = {a n b n n >= 1} Can be written as grammar S asb ab But cannot be expressed by a regular expression 32

Quiz Given the following grammar, a) left factor it; b) see whether suitable for top-down parsing? c) Eliminate left recursion from the original grammar; d) Is the resulting grammar suitable for top-down parsing S -> 0S1 01 S -> SS+ SS* a S -> S(S)S e S -> (L) a, L -> L, S S 33

S -> SS+ SS* a 1. Left factor 2. No. Left recursion 3. Eliminate left recursion 4. Yes 35

CS308 Top-Down Parsing

Top-Down Parsing The parse tree is created top to bottom. Top-down parser Recursive-Descent Parsing Backtracking is needed (If a choice of a production rule does not work, we backtrack to try other alternatives.) It is a general parsing technique, but not widely used. Not efficient Predictive Parsing No backtracking Efficient Recursive Predictive Parsing is a special form of Recursive Descent parsing without backtracking. Non-Recursive (Table Driven) Predictive Parser is also known as LL(1) parser. 40

Recursive-Descent Parsing A recursive-descent parsing program consists of a set of procedures, one for each nonterminal. Backtracking is needed (need repeated scans over the input). It tries to find the left-most derivation. S abc B bc b input: abc S Main(){ } Execution begins with the procedure for the start symbol, which halts and announces success if its procedure body scans the entire input string. a B c a B c fails, backtrack S b c b 41

Procedure for stmt compares its argument with the lookahead symbol advances to the next input terminal if they match, and changes the value of lookahead, each terminal is matched with each nonterminal leads to a call of its procedure A left-recursive grammar can cause a recursivedescent parser to go into an infinite loop. How can we get this procedure? Let s continue 42

Predictive Parser a grammar a grammar suitable for predictive eliminating left parsing (a LL(1) grammar) left recursion factoring not 100% guaranteed When rewriting a non-terminal in a derivation step, a predictive parser can uniquely choose a production rule by just looking the current symbol in the input string. A 1... n input:... a... current token 43

Predictive Parser Example stmt if... while... begin... for... When we are trying to rewrite the nonterminal stmt, we can uniquely choose the production rule by just looking the current token. if the current token is if we have to choose first production rule. 44

Recursive Predictive Parsing Each non-terminal corresponds to a procedure. Example: A abb (Only production rule for A) proc A { - match the current token with a, and move to the next token; - call proc B; - match the current token with b, and move to the next token; } 45

Recursive Predictive Parsing Cont d A abb bab proc A { case of the current token { a : - match the current token with a, and move to the next token; - call B; - match the current token with b, and move to the next token; b : - match the current token with b, and move to the next token; - call A; - call B; } } 46

Recursive Predictive Parsing Cont d When to apply -productions. A aa bb If all other productions fail, we should apply an -production. For example, if the current token is not a or b, we may apply the -production. Most correct choice: We should apply an -production for a nonterminal A when the current token is in the follow set of A (which terminals can follow A in the sentential forms). 47

Recursive Predictive Parsing Example A abe cbd C B bb C f proc A { proc C { match the current token with f, case of the current token { and move to the next token; } a: - match the current token with a, and move to the next token; proc B { - call B; case of the current token { - match the current token with e, b: - match the current token with b, and move to the next token; and move to the next token; c: - match the current token with c, - call B and move to the next token; d, e: do nothing - call B; } - match the current token with d, } and move to the next token; follow set of B f: - call C } } first set of C 48

Compute FIRST & FOLLOW X > FIRST FIRST & FOLLOW set for tokens! 49

Non-Recursive Predictive Parsing Non-Recursive predictive parsing is a table-driven parsing method. It is a top-down parser. It is also known as LL(1) Parser. LL(1) one input symbol used as a look-ahead symbol to determine parser action left most derivation input scanned from left to right input buffer stack Non-recursive Predictive Parser output Parsing Table We need an algorithm to implement the aforementioned procedures. What is a proper data structure? 50

LL(1) Parser input buffer string of tokens to be parsed, followed by endmarker $. output a production rule representing a step of the derivation sequence (left-most derivation) of the string in the input buffer. stack contains the grammar symbols at the bottom of the stack, there is a special endmarker $. initially the stack contains only the symbol $ and the starting symbol S. $S when the stack is emptied (i.e., only $ left in the stack), the parsing is completed. parsing table a two-dimensional array M[A,a] each row is a non-terminal symbol each column is a terminal symbol or the special symbol $ each entry holds a production rule. 51

LL(1) Parser Parser Actions The symbol at the top of the stack (say X) and the current symbol in the input string (say a) determine the parser action. There are four possible parser actions. 1. If X and a are $ parser halts (successful completion) 2. If X and a are the same terminal symbol (different from $) parser pops X from the stack, and moves to the next symbol in the input buffer. 3. If X is a non-terminal parser looks at the parsing table entry M[X,a]. If M[X,a] holds a production rule X Y 1 Y 2...Y k, it pops X from the stack and pushes Y k,y k-1,...,y 1 into the stack. 4. none of the above error all empty entries in the parsing table are errors. If X is a terminal symbol different from a, this is also an error case. 52

LL(1) Parser Example1 E TE E +TE T FT T *FT F (E) id id + * ( ) $ E E TE E TE E E +TE E E T T FT T FT T T T *FT T T F F id F (E) 53

LL(1) Parser Example1 Cont d stack input output $E id+id$ E TE $E T id+id$ T FT $E T F id+id$ F id $ E T id id+id$ $ E T +id$ T $ E +id$ E +TE $ E T+ +id$ $ E T id$ T FT $ E T F id$ F id $ E T id id$ $ E T $ T $ E $ E $ $ accept 54

LL(1) Parser Example2 S aba B bb S LL(1) Parsing Table S aba a b $ B B B bb stack input output $S abba$ S aba $aba abba$ $ab bba$ B bb $abb bba$ $ab ba$ B bb $abb ba$ $ab a$ B $a a$ $ $ accept, successful completion 55

LL(1) Parser Example2 Cont d Outputs: S aba B bb B bb B Derivation(left-most): S aba abba abbba abba Parse tree S a B a Remaining question? b B How derive parsing table? b B 56

Constructing LL(1) Parsing Tables Two functions are used in the construction of LL(1) parsing tables. FIRST( ) is a set of the terminal symbols which occur as first symbols in strings derived from is any string of grammar symbols. if derives to, then is also in FIRST( ). FOLLOW(A) is the set of the terminals which occur immediately after (follow) the non-terminal A in the strings derived from the starting symbol. a terminal a is in FOLLOW(A) if S * Aa endmarker $ is in FOLLOW(A) if S * A 57

Computing FIRST(X) If X is a terminal symbol FIRST(X)={X} If X is a non-terminal symbol and X is a production rule is in FIRST(X) If X is a non-terminal symbol and X Y 1 Y 2..Y n is a production rule if terminal a in FIRST(Y i ) and is in all FIRST(Y j ) for j=1,...,i-1, then a is in FIRST(X). if is in all FIRST(Y j ) for j=1,...,n, then is in FIRST(X). If X is FIRST(X)={ } We apply these rules until nothing more can be added to any FIRST set. 58

FIRST Example * E TE E +TE T FT T *FT F (E) id FIRST(F) = { (, id } FIRST(TE ) = { (, id } FIRST(T ) = { *, } FIRST(+TE ) = {+} FIRST(T) = { (, id } FIRST( ) = { } FIRST(E ) = { +, } FIRST(FT ) = { (, id } FIRST(E) = { (, id } FIRST(*FT ) = {*} FIRST( ) = { } FIRST((E)) = {(} FIRST(id) = {id} 59

Computing FOLLOW(X) If S is the start symbol $ is in FOLLOW(S) if A B is a production rule everything in FIRST( ) is in FOLLOW(B) except If ( A B is a production rule ) or ( A B is a production rule and is in FIRST( ) ) everything in FOLLOW(A) is in FOLLOW(B). We apply these rules until nothing more can be added to any FOLLOW set. 60

FOLLOW Example * E TE E +TE T FT T *FT F (E) id FOLLOW(E) = { $, ) } FOLLOW(E ) = { $, ) } FOLLOW(T) = { +, ), $ } FIRST(E ) = {+, } FOLLOW(T ) = { +, ), $ } FOLLOW(F) = { +, *, ), $ } FIRST(T ) = {*, } 61

Constructing LL(1) Parsing Table For each production A of grammar G for each terminal a in FIRST( ) add A to M[A,a] If in FIRST( ) for each terminal a in FOLLOW(A), add A to M[A,a] If in FIRST( ) and $ in FOLLOW(A) add A to M[A,$] All other undefined entries of the parsing table are error entries. 62

Constructing LL(1) Parsing Table Example E TE FIRST(TE )={(,id} E TE into M[E,(] and M[E,id] E +TE FIRST(+TE )={+} E +TE into M[E,+] E FIRST( )={ } none but since in FIRST( ) and FOLLOW(E )={$,)} E into M[E,$] and M[E,)] T FT FIRST(FT )={(,id} T FT into M[T,(] and M[T,id] T *FT FIRST(*FT )={*} T *FT into M[T,*] T FIRST( )={ } none but since in FIRST( ) and FOLLOW(T )={$,),+} T into M[T,$], M[T,)] and M[T,+] F (E) FIRST((E))={(} F (E) into M[F,(] F id FIRST(id)={id} F id into M[F,id] 63

LL(1) Grammars A grammar whose parsing table has no multiply defined entries is said to be LL(1) grammar. An entry in the parsing table of a grammar may contain more than one production rule. In this case, we say that it is not a LL(1) grammar. a grammar a LL(1) grammar (no 100% guarantee) eliminating left recursion left factoring 64

A Grammar which is not LL(1) S i C t S E a FOLLOW(S) = { $,e } E e S FOLLOW(E) = { $,e } C b FOLLOW(C) = { t } FIRST(iCtSE) = {i} FIRST(a) = {a} FIRST(eS) = {e} FIRST( ) = { } FIRST(b) = {b} S S a E a b e i t $ E e S E S ictse E Problem: ambiguity C C b two production rules for M[E,e] 65

A Grammar which is not LL(1) Cont d What can we do if the resulting parsing table contains multiply defined entries? eliminate the left recursion. left factor the grammar. If the parsing table still contains multiply defined entries, that grammar is ambiguous or it is inherently not a LL(1) grammar. A left recursive grammar cannot be a LL(1) grammar. A A any terminal that appears in FIRST( ) also appears FIRST(A ) because A. If is, any terminal that appears in FIRST( ) also appears in FIRST(A ) and FOLLOW(A). A not left factored grammar cannot be a LL(1) grammar A 1 2 any terminal that appears in FIRST( 1 ) also appears in FIRST( 2 ). An ambiguous grammar cannot be a LL(1) grammar. 66

Properties of LL(1) Grammars A grammar G is LL(1) if and only if the following conditions hold for any two distinctive production rules A and A 1. and do not derive any string starting with the same terminals. 2. At most one of and can derive. 3. If can derive, then cannot derive to any string starting with a terminal in FOLLOW(A). 67

Quiz For grammar: S -> S+S SS (S) S* a, devise predictive parsers and show the parsing tables. You may left-factor and/or eliminate left-recursion from your gramars. 68

S -> S+S SS (S) S* a Left-factoring Eliminate left-recursion 69

S -> S+S SS (S) S* a Revised production FIRST && FOLLOW 70

S -> S+S SS (S) S* a Parsing table 71

CS308 Bottom-Up Parsing

Bottom-Up Parsing A bottom-up parser creates the parse tree of the given input starting from leaves towards the root. A bottom-up parser tries to find the right-most derivation of the given input in the reverse order. S... Bottom-up parsing is also known as shift-reduce parsing because its two main actions are shift and reduce. At each shift action, the current symbol in the input string is pushed into a stack. At each reduction step, the symbols at the top of the stack (this symbol sequence is the right side of a production) will be replaced by the non-terminal at the left side of that production. 79

Shift-Reduce Parsing A shift-reduce parser tries to reduce the given input string into the starting symbol. a string the starting symbol reduced to At each reduction step, a substring of the input matching to the right side of a production rule is replaced by the non-terminal at the left side of that production rule. If the substring is chosen correctly, the right most derivation of that string is created in the reverse order. Rightmost Derivation: Shift-Reduce Parser finds: S * rm S... rm rm 80

Shift-Reduce Parsing -- Example S aabb input string: aaabb A aa a aaabb B bb b aabb reduction aabb S S aabb aabb aaabb aaabb rm rm rm rm Right Sentential Forms How do we know which substring to be replaced at each reduction step? 81

Handle In the following reduction, a handle of is the body of production A in the position following. S * A rm ( is a string of terminals) A handle is a substring that matches the right side of a production rule. But not every substring matches the right side of a production rule is a handle Only that can move the reduction forward towards the start symbol in the reverse of a rightmost derivation. If the grammar is unambiguous, then every rightsentential form of the grammar has exactly one handle. rm 82

S ab ba A a as baa B abb bs b Handle Example What is the handle of aabbab? S ab aabb aabb aabsb aabbab Handle is ba 83

Handle Pruning A right-most derivation in reverse can be obtained by handle-pruning. S= 0 1 2... n-1 n = rm string rm rm rm rm input From n, find a handle A n n in n, and replace n by A n to get n-1. Then find a handle A n-1 n-1 in n-1, and replace n-1 by A n-1 to get n-2. Repeat this, until we reach S. 84

Handle Pruning Example E E+T T T T*F F F (E) id Right-Most Derivation of id+id*id E E+T E+T*F E+T*id E+F*id E+id*id T+id*id F+id*id id+id*id Right Sentential Form id+id*id F+id*id T+id*id E+id*id E+F*id E+T*id E+T*F E+T E Reducing Production F id T F E T F id T F F id T T*F E E+T Handles are red and underlined in the right-sentential forms. 85

Shift-Reduce Parsing Initial stack just contains only the end-marker $. The end of the input string is marked by the end-marker $. There are four possible actions in a shift-reduce parser: Shift: The next input symbol is shifted into the top of the stack. Reduce: Replace the handle on the top of the stack by the non-terminal. Accept: Successful completion of parsing. Error: Parser discovers a syntax error, and calls an error recovery routine. 86

Shift-Reduce Parsing Example Stack Input Action E E+T T $ id+id*id$ shift T T*F F $id +id*id$ reduce by F id F (E) id $F +id*id$ reduce by T F $T +id*id$ reduce by E T E 8 $E +id*id$ shift $E+ id*id$ shift E 3 + T 7 $E+id *id$ reduce by F id $E+F *id$ reduce by T F T 2 T 5 * F6 $E+T *id$ shift $E+T* id$ shift F 1 F 4 id $E+T*id $ reduce by F id $E+T*F $ reduce by T T*F id id $E+T $ reduce by E E+T Parse Tree $E $ accept 87

Try it by your own Grammar: S -> SS+ SS* a Right-sentential forms: aaa*a++ Give bottom-up parses 88

Conflicts During Shift-Reduce Parsing There are context-free grammars for which shift-reduce parsers cannot be used. Stack contents and the next input symbol may not decide action: shift/reduce conflict: Whether make a shift operation or a reduction. reduce/reduce conflict: The parser cannot decide which of several reductions to make. If a shift-reduce parser cannot be used for a grammar, that grammar is called as non- LR(k) grammar. An ambiguous grammar can never be a LR grammar. 89

Shift-Reduce Parsers There are two main categories of shift-reduce parsers 1. Operator-Precedence Parser simple, but only a small class of grammars. CFG LR LALR SLR 2. LR-Parsers covers wide range of grammars. SLR simple LR parser LR most general LR parser LALR intermediate LR parser (lookahead LR parser) SLR, LR and LALR work same, only their parsing tables are different. 90

LR Parsers The most powerful shift-reduce parsing (yet efficient) is: LR(k) parsing. left to right right-most k lookahead scanning derivation (k is omitted it is 1) LR parsing s advantages: LR parsing is the most general non-backtracking shift-reduce parsing, yet it is still efficient. The class of grammars that can be parsed using LR methods is a proper superset of the class of grammars that can be parsed with predictive parsers. LL(1)-Grammars LR(1)-Grammars An LR-parser can detect a syntactic error in a left-to-right scan of the input. 91

Model of LR Parser * state symbol stack S m X m S m-1 input a 1... a i... a n $ LR Parsing Algorithm output X m-1.. Action Table Goto Table S 1 X 1 S 0 s t a t e s terminals and $ four different actions s t a t e s non-terminal each item is a state number 92

A Configuration of LR Parsing Algorithm A configuration of a LR parsing is: ( S o X 1 S 1... X m S m, a i a i+1... a n $ ) Stack Rest of Input S m and a i decides the parser action by consulting the parsing action table. (Initial Stack contains just S o ) A configuration of a LR parsing represents the right sentential form: X 1... X m a i a i+1... a n $ 93

Actions of A LR-Parser 1. shift s -- shifts the next input symbol and the state s into the stack ( S o X 1 S 1... X m S m, a i a i+1... a n $ ) ( S o X 1 S 1... X m S m a i s, a i+1... a n $ ) 2. reduce A pop 2 (r= ) items from the stack; then push A and s, where s=goto[s m-r, A] ( S o X 1 S 1... X m S m, a i a i+1... a n $ ) ( S o X 1 S 1... X m-r S m-r A s, a i... a n $ ) Output is the reducing production A 3. Accept Parsing successfully completed 4. Error -- Parser detected an error (an empty entry in the action table) 94

Reduce Action Pop 2 (r= ) items from the stack; Assume that = Y 1 Y 2...Y r Push A and s where s=goto[s m-r, A] ( S o X 1 S 1... X m-r S m-r Y 1 S m-r+1...y r S m, a i a i+1... a n $ ) ( S o X 1 S 1... X m-r S m-r A s, a i... a n $ ) In fact, Y 1 Y 2...Y r is a handle. X 1... X m-r A a i... a n $ X 1... X m Y 1...Y r a i a i+1... a n $ 95

(SLR) Parsing Table 1) E E+T 2) E T 3) T T*F 4) T F 5) F (E) 6) F id Action Table Goto Table state id + * ( ) $ E T F 0 s5 s4 1 2 3 1 s6 acc 2 r2 s7 r2 r2 3 r4 r4 r4 r4 4 s5 s4 8 2 3 5 r6 r6 r6 r6 6 s5 s4 9 3 7 s5 s4 10 8 s6 s11 9 r1 s7 r1 r1 10 r3 r3 r3 r3 11 r5 r5 r5 r5 96

Moves of A LR-Parser Example stack input action output 0 id*id+id$ shift 5 0id5 *id+id$ reduce by F id F id 0F3 *id+id$ reduce by T F T F 0T2 *id+id$ shift 7 0T2*7 id+id$ shift 5 0T2*7id5 +id$ reduce by F id F id 0T2*7F10 +id$ reduce by T T*F T T*F 0T2 +id$ reduce by E T E T 0E1 +id$ shift 6 0E1+6 id$ shift 5 0E1+6id5 $ reduce by F id F id 0E1+6F3 $ reduce by T F T F 0E1+6T9 $ reduce by E E+T E E+T 0E1 $ accept 97

Constructing SLR Parsing Tables LR(0) Item An LR(0) item of a grammar G is a production of G with a dot at some position of the body. Ex: A abb Possible LR(0) Items: A.aBb (four different possibilities) A a.bb Reduction: Moving doc to the right end A ab.b A abb. A collection of sets of LR(0) items (the canonical LR(0) collection) is the basis for constructing SLR parsers. (LR(0) automation) The collection of sets of LR(0) items will be the states. Augmented Grammar: G is G with a new production rule S S where S is the new starting symbol. CLOSURE and GOTO function * 98

The Closure Operation If I is a set of LR(0) items for a grammar G, then closure(i) is the set of LR(0) items constructed from I by the two rules: 1. Initially, every LR(0) item in I is added to closure(i). 2. If A.B is in closure(i) and B is a production rule of G, then B. will be in the closure(i). Apply this rule until no more new LR(0) items can be added to closure(i). * 99

The Closure Operation -- Example E E closure({e.e}) = E E+T { E.E kernel item * E T T T*F T F F (E) F id E.E+T E.T T.T*F T.F F.(E) F.id } Kernel items : the initial item, S.S, and all items whose dots are not at the left end. Nonkernel items : all items with their dots at the left end, except for S'.S. 100

Goto Operation If I is a set of LR(0) items and X is a grammar symbol (terminal or non-terminal), then goto(i,x) is defined as follows: If A.X in I, then every item in closure({a X. }) will be in goto(i,x). Example: I ={ E.E, E.E+T, E.T, T.T*F, T.F, F.(E), F.id } goto(i,e) = { E E., E E.+T } goto(i,t) = { E T., T T.*F } goto(i,f) = {T F. } goto(i,() = { F (.E), E.E+T, E.T, T.T*F, T.F, F.(E), F.id } goto(i,id) = { F id. } 101

Construction of The Canonical LR(0) Collections To create the SLR parsing tables for a grammar G, we will create the canonical LR(0) collection of the grammar G. Algorithm: C is { closure({s.s}) } repeat the followings until no more set of LR(0) items can be added to C. for each I in C and each grammar symbol X if goto(i,x) is not empty and not in C add goto(i,x) to C goto function is a DFA on the sets in C. 102

The Canonical LR(0) Collection Example I 0 : E.E I 1 : E E. I 6 : E E+.T I 9 : E E+T. E.E+T E E.+T T.T*F T T.*F E.T T.F T.T*F I 2 : E T. F.(E) I 10 : T T*F. T.F T T.*F F.id F.(E) F.id I 3 : T F. I 7 : T T*.F I 11 : F (E). F.(E) I 4 : F (.E) F.id E.E+T E.T I 8 : F (E.) T.T*F E E.+T T.F F.(E) F.id I 5 : F id. 103

Transition Diagram (DFA) of Goto Function E I 0 I 1 T + I 6 T F ( id I 9 to I 3 to I 4 * to I 7 F ( id I 2 I 3 I 4 id I 5 * E T F ( I 7 I 8 to I 2 to I 3 to I 4 F ( id ) + to I 5 I 10 to I 4 to I 5 I 11 to I 6 104

Constructing SLR Parsing Table 1. Construct the canonical collection of sets of LR(0) items for G. C {I 0,...,I n } 2. Create the parsing action table as follows If a is a terminal, A.a in I i and goto(i i,a)=i j then action[i,a] is shift j. If A. is in I i, then action[i,a] is reduce A for all a in FOLLOW(A) where A S. If S S. is in I i, then action[i,$] is accept. If any conflicting actions generated by these rules, the grammar is not SLR. 3. Create the parsing goto table for all non-terminals A, if goto(i i,a)=i j then goto[i,a]=j 4. All entries not defined by (2) and (3) are errors. 5. Initial state of the parser contains S.S 105

Parsing Tables of Expression Grammar 1) E E+T 2) E T 3) T T*F 4) T F 5) F (E) 6) F id Action Table Goto Table state id + * ( ) $ E T F 0 s5 s4 1 2 3 1 s6 acc 2 r2 s7 r2 r2 3 r4 r4 r4 r4 4 s5 s4 8 2 3 5 r6 r6 r6 r6 6 s5 s4 9 3 7 s5 s4 10 8 s6 s11 9 r1 s7 r1 r1 10 r3 r3 r3 r3 11 r5 r5 r5 r5 106

SLR(1) Grammar An LR parser using SLR(1) parsing tables for a grammar G is called a SLR(1) parser for G. If a grammar G has an SLR(1) parsing table, it is called SLR(1) grammar (SLR grammar for short). Every SLR grammar is unambiguous, but not every unambiguous grammar is a SLR grammar. 107

Shift/Reduce and Reduce/Reduce Conflicts If a state does not know whether it will make a shift operation or reduction for a terminal, we say that there is a shift/reduce conflict. If a state does not know whether it will make a reduction operation using the production rule i or j for a terminal, we say that there is a reduce/reduce conflict. If the SLR parsing table of a grammar G has a conflict, we say that the grammar is not a SLR grammar. 108

Conflict Example 1 S L=R I 0 : S.S I 1 : S S. I 6 : S L=.R I 9 : S L=R. S R S.L=R R.L L *R S.R I 2 : S L.=R L.*R L id L.*R R L. L.id R L L.id R.L I 3 : S R. I 4 : L *.R I 7 : L *R. Problem R.L FOLLOW(R) = {=,$} L.*R I 8 : R L. = shift 6 L.id reduce by R L shift/reduce conflict I 5 : L id. 109

Conflict Example 2 S AaAb I 0 :S.S S BbBa S.AaAb A S.BbBa B A. B. Problem FOLLOW(A)={a,b} FOLLOW(B)={a,b} a reduce by A b reduce by A reduce by B reduce by B reduce/reduce conflict reduce/reduce conflict 110

Constructing Canonical LR(1) Items In SLR method, the state i makes a reduction by A when the current token is a: if the A. in the I i and a is in FOLLOW(A) In some situations, A cannot be followed by the terminal a in a right-sentential form when and the state i are on the top stack. This means that making reduction in this case is not correct. Consider previous example 1 111

LR(1) Item To avoid some of invalid reductions, the states need to carry more information. Extra information is put into a state by including a terminal symbol as a second component in an item. A LR(1) item is: A.,a where a is the look-ahead of the LR(1) item a is a terminal or end-marker. 112

LR(1) Item Cont d When ( in the LR(1) item A.,a ) is not empty, the lookahead does not have any effect. When is empty (A.,a ), we do the reduction by A only if the next input symbol is a (not for any terminal in FOLLOW(A)). A state will contain A.,a 1... A.,a n where {a 1,...,a n } FOLLOW(A) 113

A Short Notation A set of LR(1) items containing the following items A.,a 1... A.,a n can be written as A.,a 1 /a 2 /.../a n 114

Canonical Collection of Sets of LR(1) Items The construction of the canonical collection of the sets of LR(1) items are similar to that of the sets of LR(0) items, except that closure and goto operations work a little bit different. closure(i) is: ( where I is a set of LR(1) items) every LR(1) item in I is in closure(i) if A.B,a in closure(i) and B is a production rule of G; then B.,b will be in the closure(i) for each terminal b in FIRST( a). 115

goto operation If I is a set of LR(1) items and X is a grammar symbol (terminal or non-terminal), then goto(i,x) is defined as follows: If A.X,a in I then every item in closure({a X.,a}) will be in goto(i,x). 116

Construction of The Canonical LR(1) Collection Algorithm: C is { closure({s.s,$}) } repeat the followings until no more set of LR(1) items can be added to C. for each I in C and each grammar symbol X if goto(i,x) is not empty and not in C add goto(i,x) to C goto function is a DFA on the sets in C. 117

Canonical LR(1) Collection Example 1 S S 1) S L=R 2) S R 3) L *R 4) L id 5) R L I 0 :S.S,$ S.L=R,$ S.R,$ L.*R,$/= L.id,$/= R.L,$ S I 1 :S S.,$ * LI 2 :S L.=R,$ R L.,$ R I 3 :S R.,$ = to I 6 I 4 :L *.R,$/= R.L,$/= L.*R,$/= L.id,$/= id I 5 :L id.,$/= R L * id to I 7 to I 8 to I 4 to I 5 I 6 :S L=.R,$ R.L,$ L.*R,$ L.id,$ I 7 :L *R.,$/= I 8 : R L.,$/= R L * id to I 9 to I 10 to I 11 to I 12 I 9 :S L=R.,$ I 10 :R L.,$ I 11 :L *.R,$ R.L,$ L.*R,$ L.id,$ I 12 :L id.,$ R L * id to I 13 to I 10 to I 11 to I 12 I 13 :L *R.,$ I 4 and I 11 I 5 and I 12 I 7 and I 13 I 8 and I 10 118

Canonical LR(1) Collection Example 2 S AaAb I 0 : S.S,$ S I 1 : S S.,$ S BbBa S.AaAb,$ A A S.BbBa,$ B A.,a B I 2 : S A.aAb,$ B.,b I 3 : S B.bBa,$ I 4 : S Aa.Ab,$ A I 6 : S AaA.b,$ b I 8 : S AaAb.,$ A.,b I 5 : S Bb.Ba,$ B I 7 : S BbB.a,$ a I 9 : S BbBa.,$ B.,a a b to I 4 to I 5 119

Construction of LR(1) Parsing Tables 1. Construct the canonical collection of sets of LR(1) items for G. C {I 0,...,I n } 2. Create the parsing action table as follows If a is a terminal, A.a,b in I i and goto(i i,a)=i j then action[i,a] is shift j. If A.,a is in I i, then action[i,a] is reduce A where A S. If S S.,$ is in I i, then action[i,$] is accept. If any conflicting actions generated by these rules, the grammar is not LR(1). 3. Create the parsing goto table for all non-terminals A, if goto(i i,a)=i j then goto[i,a]=j 4. All entries not defined by (2) and (3) are errors. 5. Initial state of the parser contains S.S,$ 120

LR(1) Parsing Tables for Example 1 id * = $ S L R 0 s5 s4 1 2 3 1 acc 2 s6 r5 3 r2 4 s5 s4 8 7 5 r4 r4 6 s12 s11 10 9 7 r3 r3 8 r5 r5 9 r1 10 r5 11 s12 s11 10 13 12 r4 13 r3 no shift/reduce or no reduce/reduce conflict so, it is a LR(1) grammar 121

LALR Parsing Tables LALR stands for LookAhead LR. LALR parsers are often used in practice because LALR parsing tables are smaller than LR(1) parsing tables. The number of states in SLR and LALR parsing tables for a grammar G are equal. But LALR parsers recognize more grammars than SLR parsers. A state of LALR parser will be a set of LR(1) items with modifications. Yacc creates a LALR parser for the given grammar. 122

The Core of A Set of LR(1) Items The core of a set of LR(1) items is the set of its first component. S L.=R,$ S L.=R Core R L.,$ R L. Find the states (sets of LR(1) items) in a canonical LR(1) parser with the same core, and merge them into a single state. I 1 :L id.,= A new state: I 12 : L id.,=/$ I 2 :L id.,$ Do this for all states of a canonical LR(1) parser to get the states of the LALR parser. 123

Creating LALR Parsing Tables Canonical LR(1) Parser LALR Parser shrink # of states This shrink process may introduce a reduce/reduce conflict in the resulting LALR parser (so the grammar is NOT LALR) But, this shrink process does not produce a shift/reduce conflict. 124

Shift/Reduce Conflict We cannot introduce a shift/reduce conflict during the shrinking process for the creation of the states of a LALR parser. Assume that we can introduce a shift/reduce conflict. In this case, a state of LALR parser must have: A.,a and B.a,b This means that a state of the canonical LR(1) parser must have: A.,a and B.a,c But, this state has also a shift/reduce conflict. i.e. The original canonical LR(1) parser has a conflict. Contradiction! 125

Reduce/Reduce Conflict But, we may introduce a reduce/reduce conflict during the shrink process for the creation of the states of a LALR parser. I 1 : A.,a I 2 : A.,b B.,b B.,c I 12 : A.,a/b reduce/reduce conflict B.,b/c 126

Creation of LALR Parsing Tables Create the canonical LR(1) collection of the sets of LR(1) items for the given grammar. For each core, find all sets having it, and replace those sets into a single set. C={I 0,...,I n } C ={J 0,...,J m } where m n Create the parsing table (action and goto tables) the same way as that of LR(1) parser. Note: If J=I 1... I k, since I 1,...,I k have the same core cores of goto(i 1,X),...,goto(I k,x) must be same. So, goto(j,x)=k where K is the union of all sets of items having the same core as goto(i 1,X). If no conflict is introduced, the grammar is LALR(1) grammar. 127

Canonical LR(1) Collection Example 1 S S 1) S L=R 2) S R 3) L *R 4) L id 5) R L I 0 :S.S,$ S.L=R,$ S.R,$ L.*R,$/= L.id,$/= R.L,$ I 1 :S S.,$ S * LI 2 :S L.=R,$ R L.,$ R I 3 :S R.,$ to I 6 I 4 :L *.R,$/= R.L,$/= L.*R,$/= L.id,$/= id I 5 :L id.,$/= R L * id to I 7 to I 8 to I 4 to I 5 I 6 :S L=.R,$ R.L,$ L.*R,$ L.id,$ I 7 :L *R.,$/= I 8 : R L.,$/= R L * id to I 9 to I 10 to I 11 to I 12 I 9 :S L=R.,$ I 10 :R L.,$ I 11 :L *.R,$ R.L,$ L.*R,$ L.id,$ I 12 :L id.,$ R L * id I 13 :L *R.,$ Merging? I 4 and I 11 to I 13 I to I 5 and I 12 10 to I I 11 7 and I 13 to I 12 I 8 and I 10 128

Canonical LALR(1) Collection Example 1 S S 1) S L=R 2) S R 3) L *R 4) L id 5) R L I 0 :S.S,$ S.L=R,$ S.R,$ L.*R,$/= L.id,$/= R.L,$ I 1 :S S.,$ S * LI 2 :S L.=R,$ R L.,$ R I 3 :S R.,$ id I 411 :L *.R,$/= R.L,$/= to I 6 L.*R,$/= L.id,$/= I 512 :L id.,$/= R L * id to I 713 to I 810 to I 411 to I 512 I 6 :S L=.R,$ R.L,$ L.*R,$ L.id,$ I 713 :L *R.,$/= R L * id to I 9 to I 810 to I 411 to I 512 I 9 :S L=R.,$ Same Cores I 4 and I 11 I 5 and I 12 I 7 and I 13 I 810 : R L.,$/= Let s construct the parsing table! I 8 and I 10 129

LALR(1) Parsing Tables for Example2 id * = $ S L R 0 s5 s4 1 2 3 1 acc 2 s6 r5 3 r2 4 s5 s4 8 7 5 r4 r4 6 s12 s11 10 9 7 r3 r3 8 r5 r5 9 r1 no shift/reduce or no reduce/reduce conflict so, it is a LALR(1) grammar 130

Homework Exercise 4.2.1 Exercise 4.4.1(e), 4.4.12 Exercise 4.6.5 Exercise 4.7.1 Due date: Oct. 31, 2015 139

Summary Parsers, Context-free grammar, Derivations, Parse Trees, Ambiguity, Top- Down and Bottom-up Parsing, Design of Grammars, Recursive-Decent Parsers LL(1) parsers, Shift-reduce parsing, Viable prefixes, Valid Items, 140