Untitled
unknown
plain_text
a year ago
7.6 kB
3
Indexable
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <stdlib.h>
#define MAX_SYMBOLS 100
#define MAX_INPUT_LENGTH 100
#define MAX_STACK_SIZE 100
// Define Symbol structure
struct Symbol {
int index;
char name[50];
char dataType[20];
char scope[50];
};
// Define Token Types
typedef enum {
KEYWORD,
IDENTIFIER,
CONSTANT,
OPERATOR,
DELIMITER,
UNKNOWN
} TokenType;
// List of sample keywords (you can expand this list)
const char *keywords[] = {"int", "float", "char", "void", "return", "if", "else", "while", "for"};
const int keyword_count = 9;
// Stack for operators in expression evaluation
typedef struct {
char items[MAX_STACK_SIZE];
int top;
} Stack;
void initStack(Stack* s) {
s->top = -1;
}
int isEmpty(Stack* s) {
return s->top == -1;
}
void push(Stack* s, char item) {
if (s->top < MAX_STACK_SIZE - 1) {
s->items[++s->top] = item;
}
}
char pop(Stack* s) {
if (isEmpty(s)) {
return -1;
}
return s->items[s->top--];
}
char peek(Stack* s) {
if (isEmpty(s)) {
return -1;
}
return s->items[s->top];
}
// Function to display the symbol table
void displayTable(struct Symbol symbols[], int count) {
printf("\n============================= SYMBOL TABLE =============================\n");
printf("| %-5s | %-20s | %-10s | %-15s |\n", "Index", "Name", "DataType", "Scope");
printf("==========================================================================\n");
for (int i = 0; i < count; i++) {
printf("| %-5d | %-20s | %-10s | %-15s |\n", symbols[i].index, symbols[i].name, symbols[i].dataType, symbols[i].scope);
}
printf("==========================================================================\n");
}
// Function to insert a new symbol into the symbol table
void insertSymbol(struct Symbol symbols[], int *count) {
if (*count >= MAX_SYMBOLS) {
printf("\nError: Symbol table is full!\n");
return;
}
struct Symbol newSymbol;
newSymbol.index = *count + 1;
printf("Enter identifier name: ");
scanf("%s", newSymbol.name);
printf("Enter data type: ");
scanf("%s", newSymbol.dataType);
printf("Enter scope: ");
scanf("%s", newSymbol.scope);
symbols[*count] = newSymbol;
(*count)++;
printf("\nSymbol inserted successfully!\n");
}
// Function to check if a character is an operator
int isOperator(char c) {
return (c == '+' || c == '-' || c == '*' || c == '/' || c == '%');
}
// Function to check precedence of operators
int precedence(char op) {
if (op == '+' || op == '-') return 1;
if (op == '*' || op == '/') return 2;
return 0;
}
// Convert infix expression to postfix
void infixToPostfix(char* infix, char* postfix) {
Stack s;
initStack(&s);
int j = 0;
for (int i = 0; i < strlen(infix); i++) {
char current = infix[i];
if (isalnum(current)) {
postfix[j++] = current; // Add operand (variable or constant)
}
else if (current == '(') {
push(&s, current); // Push '(' to stack
}
else if (current == ')') {
while (!isEmpty(&s) && peek(&s) != '(') {
postfix[j++] = pop(&s); // Pop until '('
}
pop(&s); // Discard '('
}
else if (isOperator(current)) {
while (!isEmpty(&s) && precedence(peek(&s)) >= precedence(current)) {
postfix[j++] = pop(&s); // Pop operators based on precedence
}
push(&s, current); // Push current operator
}
}
// Pop remaining operators from the stack
while (!isEmpty(&s)) {
postfix[j++] = pop(&s);
}
postfix[j] = '\0'; // Null-terminate the postfix expression
}
// Generate Three Address Code (TAC)
void generateTAC(char* infix) {
char postfix[MAX_INPUT_LENGTH];
infixToPostfix(infix, postfix);
printf("\n==================== THREE ADDRESS CODE ====================\n");
int tempCounter = 1;
Stack s;
initStack(&s);
for (int i = 0; i < strlen(postfix); i++) {
char current = postfix[i];
if (isalnum(current)) {
push(&s, current); // Push operands (variables/constants)
}
else if (isOperator(current)) {
char operand2 = pop(&s); // Pop second operand
char operand1 = pop(&s); // Pop first operand
printf("t%d = %c %c %c\n", tempCounter++, operand1, current, operand2); // Print TAC
push(&s, 't' + (tempCounter - 1)); // Push the temporary variable
}
}
printf("==============================================================\n");
}
// Main function with menu options
int main() {
struct Symbol symbols[MAX_SYMBOLS];
int symbolCount = 0;
int choice;
while (1) {
printf("\n======================= MENU =======================\n");
printf("1. Insert symbol\n");
printf("2. Display symbol table\n");
printf("3. Lexical analysis (tokenize code)\n");
printf("4. Convert expression to postfix and generate TAC\n");
printf("5. Exit\n");
printf("Enter your choice: ");
scanf("%d", &choice);
switch (choice) {
case 1:
insertSymbol(symbols, &symbolCount);
break;
case 2:
displayTable(symbols, symbolCount);
break;
case 3: {
char code[MAX_INPUT_LENGTH];
printf("Enter code to tokenize (e.g., int x = 10;): ");
getchar(); // To consume the newline character from previous input
fgets(code, MAX_INPUT_LENGTH, stdin);
printf("\n========================= TOKENS ==========================\n");
for (int i = 0; i < strlen(code); i++) {
if (isspace(code[i])) continue; // Skip spaces
if (isalpha(code[i])) {
printf("%c - IDENTIFIER\n", code[i]);
}
else if (isdigit(code[i])) {
printf("%c - CONSTANT\n", code[i]);
}
else if (isOperator(code[i])) {
printf("%c - OPERATOR\n", code[i]);
}
else {
printf("%c - DELIMITER\n", code[i]);
}
}
break;
}
case 4: {
char expression[MAX_INPUT_LENGTH];
printf("Enter an expression: ");
getchar(); // To consume the newline character from previous input
fgets(expression, MAX_INPUT_LENGTH, stdin);
printf("\n======================= POSTFIX =======================\n");
char postfix[MAX_INPUT_LENGTH];
infixToPostfix(expression, postfix);
printf("Postfix Expression: %s\n", postfix);
generateTAC(expression);
break;
}
case 5:
printf("Exiting...\n");
return 0;
default:
printf("Invalid choice. Please try again.\n");
}
}
return 0;
}
Editor is loading...
Leave a Comment