What is the difference between LR0 and SLR parsing?
Master System Design with Codemia
Enhance your system design skills with over 120 practice problems, detailed solutions, and hands-on exercises.
Introduction
LR parsing methods all work bottom-up, but they differ in how much context they use when deciding whether to shift or reduce. The difference between LR(0) and SLR is exactly that extra context: LR(0) uses only the current parser state, while SLR adds FOLLOW-set lookahead to reduce actions.
What LR(0) Means
An LR(0) parser builds states from LR items, where each item is a production with a dot showing how much of the right-hand side has been seen. A state might contain items like:
- '
A -> a . B' - '
B -> . c' - '
B -> . d'
The parser uses these states to decide:
- shift, if the dot is before a terminal
- goto, if the dot is before a nonterminal
- reduce, if the dot is at the end
The important limitation is that an LR(0) parser does not look at the next input symbol before reducing. If a state contains a completed item such as A -> b ., LR(0) wants to reduce on every possible lookahead symbol. That makes LR(0) very strict: only simple grammars avoid conflicts.
What SLR Adds
SLR stands for Simple LR. It still uses the same LR(0) item automaton, so the states themselves do not get more detailed. The improvement happens when building the action table.
For a completed item A -> alpha ., SLR does not reduce on every terminal. It reduces only on terminals in FOLLOW(A). That single rule often removes conflicts that LR(0) cannot resolve.
So the key distinction is:
- LR(0): reduce everywhere
- SLR: reduce only where the grammar says
Acan legally be followed
This makes SLR strictly more powerful than LR(0), though still weaker than canonical LR(1) and LALR.
A Small Example
Consider this grammar:
After reading b, one parser state contains these completed items:
In LR(0), both items ask for a reduction on every lookahead symbol. That creates a reduce/reduce conflict because the parser cannot choose between:
- reduce
S -> b - reduce
A -> b
SLR resolves it by using FOLLOW sets:
- '
FOLLOW(S)contains only end-of-input' - '
FOLLOW(A)contains onlya'
So the SLR action table becomes:
- on
a, reduceA -> b - on end-of-input, reduce
S -> b
No conflict remains.
Runnable Illustration
This Python snippet demonstrates the exact difference in table generation:
Output summary:
- LR(0) places both reductions on every terminal
- SLR places each reduction only where the nonterminal may legally appear next
That is the practical meaning of SLR's extra power.
How the Parsing Tables Differ
The construction pipeline is almost the same for both methods:
- augment the grammar
- build closure and goto sets from LR(0) items
- create parser states
- fill the action and goto tables
The only real difference is step 4.
For LR(0):
- a completed item inserts a reduce action for all terminals
For SLR:
- a completed item inserts a reduce action only for
FOLLOW(lhs)
Because the automaton is identical, SLR is easy to explain as "LR(0) plus FOLLOW sets."
When LR(0) Fails but SLR Works
LR(0) fails whenever a completed item shares a state with a possible shift or another completed item and the parser needs lookahead to know which action is legal. SLR can fix some of those cases because FOLLOW sets filter out impossible reductions.
However, SLR is still approximate. FOLLOW sets are global properties of a nonterminal, not state-specific lookaheads. That means SLR can still report conflicts for grammars that canonical LR(1) can parse.
So the usual power relationship is:
- LR(0) is the weakest
- SLR is better
- LALR and LR(1) are stronger
Common Pitfalls
The most common mistake is thinking SLR changes the item sets. It does not. SLR keeps LR(0) states and only changes where reduce actions are placed in the parsing table.
Another mistake is assuming FOLLOW sets always solve conflicts. They solve some conflicts, not all. If a grammar needs state-specific lookahead, SLR is not enough.
It is also easy to confuse "lookahead count" with implementation complexity. SLR uses one-symbol lookahead indirectly, but it does not store full LR(1) lookahead sets in each item.
Finally, students often memorize the definitions without looking at an actual conflict state. The difference becomes much clearer when you compare one LR(0) state and see how FOLLOW sets restrict the legal reductions.
Summary
- LR(0) decides reductions without lookahead and therefore reduces on every terminal in a completed state.
- SLR uses the same LR(0) states but limits reductions to terminals in the left-hand side FOLLOW set.
- Because of that filtering, SLR handles more grammars than LR(0).
- SLR is still weaker than LR(1) because FOLLOW sets are global, not state-specific.
- The simplest mental model is: SLR equals LR(0) automaton plus FOLLOW-based reduce placement.

