Ambiguity in Context-Free Grammars, Disambiguation Techniques, and Analysis of the Grammar SaS/Sa/aS \rightarrow aS/Sa/a

Ambiguity in Context-Free Grammars, Disambiguation Techniques, and Analysis of the Grammar SaS/Sa/aS \rightarrow aS/Sa/a

Verified Sources
Sep 11, 2026

Ambiguous Grammars & Removing Ambiguity (lecture-style)

A context-free grammar (CFG) is called ambiguous when there exists at least one terminal string that can be produced in two distinct ways resulting in two different parse trees (equivalently, two different leftmost/rightmost derivations).2 Ambiguity is a syntactic property of the grammar, not of the language alone: a language may admit both ambiguous and unambiguous grammars (or be inherently ambiguous).2

Ambiguity becomes a practical problem in parsing/compilers because a parser would not have a unique syntactic structure to attach to the same input string, undermining deterministic meaning assignment from syntax trees.

Key terms:

  • Ambiguous grammar
  • Parse tree
  • Leftmost derivation
  • Unambiguous grammar

Footnotes

  1. Parse Trees / Ambiguous Grammars (University of Rochester CSC 173 notes) - https://www.cs.rochester.edu/u/nelson/courses/csc_173/grammars/parsetrees.html - Defines ambiguous grammars via existence of two different parse trees for the same terminal string and uses this to prove ambiguity. 2 3

  2. Ambiguous Grammar (GeeksforGeeks overview) - https://www.geeksforgeeks.org/compiler-design/ambiguous-grammar - Defines ambiguity in terms of more than one parse tree/derivation for a string.

  3. Ambiguous grammar - Wikipedia - https://en.wikipedia.org/wiki/Ambiguous_grammar - Discusses ambiguity, recognition, and (inherently) ambiguous languages.

Ambiguity can often be reduced or eliminated by redesigning the grammar (grammar transformation) so that the intended structure is forced by the rules. Typical approaches include:

  1. Refactoring to enforce structure, e.g., left-factoring (common in LL parsers).
  2. Eliminating left/right recursion (improves parser construction but does not always solve ambiguity by itself).
  3. Encoding precedence and associativity in the grammar (crucial for arithmetic-expression ambiguity).
  4. Using parser-generator precedence/associativity declarations (e.g., in YACC) which effectively resolves some shift/reduce conflicts.2

However, there is a strong theoretical limitation: the computational task “given a CFG, decide whether it is ambiguous” is undecidable in general. Likewise, the task of algorithmically finding an equivalent unambiguous CFG (when possible) is not solvable in general.

Key terms:

  • Left factoring
  • Operator precedence
  • Associativity
  • Undecidable problem

Footnotes

  1. Ambiguous grammar - Wikipedia - https://en.wikipedia.org/wiki/Ambiguous_grammar - Discusses ambiguity, recognition, and (inherently) ambiguous languages.

  2. Context-Free Grammars lecture notes (UT Austin PDF) - https://www.cs.utexas.edu/~cline/ear/automata/CS341-Fall-2004-Packet/1-LectureNotes/ContextFree.pdf - Covers resolving ambiguity via precedence/associativity and grammar transformations.

  3. CS 373 lecture notes (Grainger/Illinois) on ambiguity decision/removal being undecidable - https://courses.grainger.illinois.edu/cs373/fa2010/lectures/lect20.pdf - States ambiguity decision is undecidable and discusses impossibility of general removal as an algorithmic task. 2

How to test (prove) a CFG is ambiguous

  1. 1
    Step 1

    Pick a terminal string that you suspect can be derived in multiple ways.

  2. 2
    Step 2

    Construct two different parse trees (or two distinct leftmost/rightmost derivations) for the same string.

  3. 3
    Step 3

    Ensure the parse trees differ structurally (not just by redundant rearrangements).

  4. 4
    Step 4

    If you find one string with two different parse trees, the grammar is ambiguous.

    Footnotes

    1. Parse Trees / Ambiguous Grammars (University of Rochester CSC 173 notes) - https://www.cs.rochester.edu/u/nelson/courses/csc_173/grammars/parsetrees.html - Defines ambiguous grammars via existence of two different parse trees for the same terminal string and uses this to prove ambiguity.

Now consider the grammar (as written):

SaS  /  Sa  /  aS \rightarrow aS \;/\; Sa \;/\; a

Interpreting “//” as alternative productions, the CFG is:

SaSSaaS \rightarrow aS \quad\mid\quad Sa \quad\mid\quad a

We will decide whether it is ambiguous by checking whether some string has more than one parse tree.

Key insight: every production adds exactly one terminal symbol aa either on the left (aSaS) or on the right (SaSa), and the base case produces exactly one aa (SaS\rightarrow a).

Key terms:

  • Base case
  • Sentential form
  • Derivation length

Claim: The grammar is unambiguous

Let the target string be ana^n (i.e., nn copies of aa). We show that it has a unique parse tree.

Structure forced by the first step

  • If the derivation starts with SaSS \Rightarrow aS, then one aa is fixed as the leftmost symbol of the final yield; the rest must come from deriving the remaining n1n-1 symbols via SS.
  • If instead SSaS \Rightarrow Sa, then one aa is fixed as the rightmost symbol.
  • Only SaS \Rightarrow a can produce a string of length 11.

Uniqueness argument (for ana^n): Consider the derivation tree’s root label SS. The tree has exactly one internal node labeled SS at each derivation depth until reaching the leaf created by SaS \rightarrow a.

For the yield to be exactly ana^n, at each internal SS node, you must choose whether that node contributes the next aa on the left or on the right. But because the entire string is homogeneous (aa everywhere), different “left vs right” choices could appear to lead to the same terminal string.

We resolve this by observing that different sequences of left/right choices change the branching structure in the parse tree: the grammar’s productions are not symmetric through a single local rewrite—each internal node corresponds to a specific production occurrence (aSaS or SaSa). Those occurrences induce different tree shapes.

Concretely:

  • For n=2n=2, the grammar can only derive aaaa by either:
    • SaSaaS \Rightarrow aS \Rightarrow a a
    • or SSaaaS \Rightarrow Sa \Rightarrow a a These terminal strings are identical, so we check whether these produce different parse trees:
  • First derivation tree: root uses SaSS\rightarrow aS; the SS child then uses SaS\rightarrow a.
  • Second derivation tree: root uses SSaS\rightarrow Sa; the SS child then uses SaS\rightarrow a.

These two parse trees are structurally different because the root production differs (aSaS vs SaSa), even though the final yield is the same terminal string aaaa.

Therefore, the grammar is ambiguous.

This directly matches the definition: if there exists a string with two different parse trees, the grammar is ambiguous.

Key terms:

  • Ambiguity witness
  • Production choice

Footnotes

  1. Parse Trees / Ambiguous Grammars (University of Rochester CSC 173 notes) - https://www.cs.rochester.edu/u/nelson/courses/csc_173/grammars/parsetrees.html - Defines ambiguous grammars via existence of two different parse trees for the same terminal string and uses this to prove ambiguity.

Explicit ambiguity witness for this grammar

We exhibit two different parse trees (equivalently, two distinct derivations) for the same string aaaa.

Derivation 1 (using SaSS\rightarrow aS at the root):

SaSaaS \Rightarrow aS \Rightarrow aa

Derivation 2 (using SSaS\rightarrow Sa at the root):

SSaaaS \Rightarrow Sa \Rightarrow aa

These correspond to different parse-tree structures at the root because the root production differs (aSaS vs SaSa). Hence the grammar is ambiguous.

Footnotes

  1. Parse Trees / Ambiguous Grammars (University of Rochester CSC 173 notes) - https://www.cs.rochester.edu/u/nelson/courses/csc_173/grammars/parsetrees.html - Defines ambiguous grammars via existence of two different parse trees for the same terminal string and uses this to prove ambiguity.

Pro Tip

To prove ambiguity, it’s enough to find one string (an ambiguity witness) with two different parse trees/derivations. You do not need to prove ambiguity for all strings.

Footnotes

  1. Parse Trees / Ambiguous Grammars (University of Rochester CSC 173 notes) - https://www.cs.rochester.edu/u/nelson/courses/csc_173/grammars/parsetrees.html - Defines ambiguous grammars via existence of two different parse trees for the same terminal string and uses this to prove ambiguity.

Warning: ambiguity vs. multiple derivations

Having two different derivations/parse trees for some string implies ambiguity, but “existence of derivations” alone isn’t enough—your derivations must be structurally distinct parse trees for the same terminal yield.2

Footnotes

  1. Parse Trees / Ambiguous Grammars (University of Rochester CSC 173 notes) - https://www.cs.rochester.edu/u/nelson/courses/csc_173/grammars/parsetrees.html - Defines ambiguous grammars via existence of two different parse trees for the same terminal string and uses this to prove ambiguity.

  2. Ambiguous Grammar (GeeksforGeeks overview) - https://www.geeksforgeeks.org/compiler-design/ambiguous-grammar - Defines ambiguity in terms of more than one parse tree/derivation for a string.

From definitions to a grammar decision

Definition

Step A

Ambiguous iff some string has two different parse trees."

Footnotes

  1. Parse Trees / Ambiguous Grammars (University of Rochester CSC 173 notes) - https://www.cs.rochester.edu/u/nelson/courses/csc_173/grammars/parsetrees.html - Defines ambiguous grammars via existence of two different parse trees for the same terminal string and uses this to prove ambiguity.

Search for a witness

Step B

Try short strings first (e.g., a2a^2) to find conflicting root productions."

Compare parse trees

Step C

If the root production differs and yields the same string, ambiguity holds."

Conclude

Step D

If witness exists, grammar is ambiguous; general ambiguity decision is undecidable."

Footnotes

  1. CS 373 lecture notes (Grainger/Illinois) on ambiguity decision/removal being undecidable - https://courses.grainger.illinois.edu/cs373/fa2010/lectures/lect20.pdf - States ambiguity decision is undecidable and discusses impossibility of general removal as an algorithmic task.

Ambiguity evidence for the grammar

For input aaaa, the grammar yields multiple distinct parse structures.

Disambiguation: can ambiguity always be removed?

Knowledge Check

Question 1 of 4
Q1Single choice

A CFG is ambiguous if

Explore Related Topics

1

Functional-Dependency Analysis and Normalization of R(A, B, C, D, E, F)

2

Ambiguity in the Grammar \(S \rightarrow ABA,\; A \rightarrow aA \mid \epsilon,\; B \rightarrow bB \mid \epsilon\)

The grammar (S\rightarrow ABA,;A\rightarrow aA\mid\epsilon,;B\rightarrow bB\mid\epsilon) is ambiguous because the two (A) nonterminals can distribute the same (a)-string in multiple ways, especially when (B) derives (\epsilon).

  • It generates the language (L(S)={a^i b^j a^k\mid i,j,k\ge0}=a^*b^a^).
  • The shortest string (a) has two distinct left‑most derivations (or parse trees), proving ambiguity.
  • Every string (a^n) with (n\ge1) can be split between the two (A) symbols in (n+1) ways, yielding multiple parse trees.
  • The ambiguity stems from both (A) producing (a^*) and (B) being able to vanish via (\epsilon).
  • An equivalent unambiguous grammar can be constructed, showing the ambiguity is a property of this grammar, not necessarily of the language.
3

Lexical Analysis and the Main Structure Used: Finite Automata

Lexical analysis relies on finite automata—typically deterministic finite automata (DFA)—to recognize token patterns defined by regular expressions.

  • Regular expressions for identifiers, numbers, etc., are converted to NFAs then to a DFA for fast scanning.
  • The DFA processes the source character by character, tracking a single current state and emitting a token at each accepting state.
  • Queues, stacks, and trees support other compiler phases (parsing, AST construction) but are not the primary model for token recognition.
  • Lexers output a stream of tokens that the parser consumes for syntax analysis.