CD Notes
Real-world parser implementation guide with AST construction, symbol tables, and code generation
Learning parser generation through practical projects accelerates understanding. Here are realistic project ideas with implementation guidance.
Project Ideas by Difficulty
Beginner: Simple Calculator
Features:
- Basic arithmetic: +, -, *, /
- Parentheses for grouping
- Error handling
Lexer:
Parser:
expr : NUMBER { $$ = $1; }
| expr '+' expr { $$ = $1 + $3; }
| expr '*' expr { $$ = $1 * $3; }
| '(' expr ')' { $$ = $2; }
;Intermediate: Variable Assignment
Features:
- Variable declaration:
int x = 5; - Variable usage:
y = x + 3; - Symbol table
Grammar Additions:
statement : TYPE IDENTIFIER '=' expr ';' { declare($2, $1, $4); }
| IDENTIFIER '=' expr ';' { assign($1, $3); }
;Advanced: Small Programming Language
Features:
- Functions:
int add(int a, int b) { return a + b; } - Control flow: if/else, while, for
- Arrays
- Type system
- Scope management
Complexity:
- Symbol table with scoping
- Type checking
- AST generation
- Code generation or interpretation
Building AST (Abstract Syntax Tree)
Instead of evaluating directly, build a tree:
struct ASTNode {
char *type; // "binop", "number", "var", etc
char *op; // for binop: "+", "-", etc
int value; // for number
char *name; // for identifier
struct ASTNode *left;
struct ASTNode *right;
};
typedef struct ASTNode* ASTPtr;
ASTPtr makeNode(char *type) {
ASTPtr node = malloc(sizeof(struct ASTNode));
node->type = strdup(type);
return node;
}
ASTPtr makeBinOp(ASTPtr left, char *op, ASTPtr right) {
ASTPtr node = makeNode("binop");
node->left = left;
node->op = strdup(op);
node->right = right;
return node;
}Bison Usage:
%union {
int intval;
struct ASTNode *node;
}
%type <node> expr
%type <intval> NUMBER
expr : expr PLUS expr { $$ = makeBinOp($1, "+", $3); }
| NUMBER { ASTPtr n = makeNode("number");
n->value = $1; $$ = n; }
;Symbol Table Implementation
Track variables and their properties:
Type Checking
Validate type compatibility:
Code Generation
Output intermediate or machine code:
Testing Your Parser
Interview Q&A
Q: How do you build an AST with Bison? A: Define a union with AST node pointers, use %type directives, create nodes in semantic actions with pointers, build tree by setting left/right pointers.
Q: How do you manage symbol tables? A: Use an array or hash table, store name/type/scope. Handle scoping by tracking function depth. Implement lookup to search most recent scope first.
Q: What's the difference between code generation and interpretation? A: Code generation produces intermediate or machine code. Interpretation directly executes AST or bytecode. Generation is faster for repeated execution.
Q: How do you handle variable scopes? A: Track scope depth (global=0, function=1, nested block=2, etc.). When looking up variables, find most recent declaration in current or outer scopes.
Q: What errors should parser projects detect? A: Syntax errors (invalid tokens), semantic errors (type mismatches, undefined variables), scope errors (variable not declared), and runtime errors (division by zero).
Exam Focus
Revise definitions, diagrams, examples, and short-answer points for Practical Parser Projects.
Interview Use
Prepare one clear explanation, one practical example, and one common mistake for this Compiler Design topic.
Search Terms
compiler-design, compiler design, compiler, design, parser, generators, practical, projects
Related Compiler Design Topics