0% found this document useful (0 votes)
4 views

Compiler

Uploaded by

noob.gaming.hihi
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
4 views

Compiler

Uploaded by

noob.gaming.hihi
Copyright
© © All Rights Reserved
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 5

-

Q1. Explain the phases of a compiler. What role does each phase play in translating a high-level
program into machine code?

Answer:
A compiler translates high-level programming code into machine-readable code through several
phases:

1. Lexical Analysis:

The compiler scans the source code to identify tokens (basic language components like
keywords, identifiers, and operators).

Example: The code int a = 5; is broken into tokens: int, a, =, 5, and ;.

2. Syntax Analysis (Parsing):

Ensures the program's structure follows the grammar rules of the language.

Example: Constructs a parse tree to validate if (a > b) { x = 1; }.

3. Semantic Analysis:

Checks for semantic errors like type mismatches (e.g., adding a number and a string).

Example: Ensures int a = "hello"; throws an error.

4. Intermediate Code Generation:

Converts the source code into an intermediate representation (IR) for easier optimization and
portability.

Example: A line like x = a + b becomes t1 = a + b.

5. Code Optimization:
Improves the intermediate code to make it more efficient.

Example: Eliminates redundant instructions or simplifies loops.

6. Code Generation:

Produces the final machine code (assembly or binary) from the optimized intermediate code.

7. Code Linking and Loading:

Links external libraries and loads the executable into memory for execution.

---

Q2. What are Finite Automata and Regular Expressions? How are they used in lexical analysis?

Answer:

Finite Automata (FA):

A mathematical model used to recognize patterns in strings. It consists of states, transitions,


and final states.

Deterministic FA (DFA): Each state has one transition per input symbol.

Non-Deterministic FA (NFA): States may have multiple transitions for the same symbol.

Regular Expressions (RE):

Used to define patterns for lexical elements like keywords and operators in a programming
language.

Example: The RE a*b matches strings like b, ab, and aaab.


Use in Lexical Analysis:

1. Lexical analyzers use REs to describe tokens (e.g., int for integers).

2. Convert REs into NFAs or DFAs for efficient pattern recognition.

3. The automaton scans the source code, recognizing valid tokens based on transitions.

---

Q3. Compare top-down and bottom-up parsing techniques. How are they implemented in syntax
analysis?

Answer:

Top-Down Parsing:

Starts with the root of the parse tree and works downward to match the input.

Recursive Descent Parsing: Implements the grammar rules recursively.

LL Parsers (Left-to-right, Leftmost derivation): A common top-down approach.

Example: Parsing a rule like S → aSb for input aabb.

Bottom-Up Parsing:

Starts with the input tokens and works upward to construct the parse tree.

Shift-Reduce Parsing: A token is shifted onto the stack, and reductions are applied to match
grammar rules.

LR Parsers (Left-to-right, Rightmost derivation): Includes variants like SLR, CLR, and LALR.

Comparison:
1. Top-Down Parsing is simpler but struggles with left-recursive grammars.

2. Bottom-Up Parsing handles a wider range of grammars, making it suitable for complex
programming languages.

---

Q4. What is Syntax-Directed Translation (SDT)? How are syntax trees and intermediate code
generated?

Answer:

Syntax-Directed Translation (SDT):

Integrates semantic actions with grammar rules to guide translation during parsing.

Example: A rule like E → E1 + T { E.value = E1.value + T.value; } calculates values during


parsing.

Syntax Trees:

A hierarchical representation of the structure of a program.

Each node represents an operation or construct.

Example: For a + b * c, the syntax tree has + at the root, with a and * as children, and b and c
as leaves.

Intermediate Code Generation:

Converts the syntax tree into a linear representation (e.g., three-address code).

Example: For a + b * c, intermediate code could be:

t1 = b * c
t2 = a + t1
---

Q5. Explain code optimization in compilers. What are loop optimization and DAG
representation?

Answer:

Code Optimization:

Enhances the intermediate code to improve performance without altering its functionality.

Goals: Reduce execution time, minimize memory usage, and improve hardware utilization.

Loop Optimization:

Focuses on improving performance for repeated execution in loops.

1. Loop Unrolling: Reduces the overhead of loop control by executing multiple iterations in a
single iteration.

2. Invariant Code Motion: Moves calculations outside the loop if they don’t depend on loop
variables.

DAG Representation:

Directed Acyclic Graph (DAG) is used to represent expressions in intermediate code.

Purpose: Detects and eliminates redundant calculations.

Example: For t1 = a + b and t2 = a + b, the DAG stores a + b once, avoiding duplication.

You might also like