给出能在Dev中运行的自底向上的语法分析程序的C语言代码
时间: 2024-06-09 19:09:35 浏览: 18
以下是C语言实现的自底向上语法分析程序的示例代码:
```c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define MAX_SIZE 100
// 定义产生式结构体
struct Production {
char left; // 产生式左部
char right[MAX_SIZE]; // 产生式右部
};
// 定义项目结构体
struct Item {
char left; // 项目左部
char right[MAX_SIZE + 1]; // 项目右部
int dot_pos; // dot 位置
};
// 定义状态结构体
struct State {
struct Item items[MAX_SIZE]; // 项目集合
int size; // 项目数量
} states[MAX_SIZE]; // 状态集合
int num_states = 0; // 状态数量
// 定义文法产生式列表
struct Production productions[MAX_SIZE];
int num_productions = 0;
// 定义文法符号集合
char symbols[MAX_SIZE];
int num_symbols = 0;
// 定义预测分析表
int action[MAX_SIZE][MAX_SIZE]; // action 表
int goto_table[MAX_SIZE][MAX_SIZE]; // goto 表
// 定义栈结构体
struct Stack {
int data[MAX_SIZE]; // 栈数据
int size; // 栈大小
} stack;
// 将符号加入符号集合
void add_symbol(char symbol) {
if (strchr(symbols, symbol) == NULL) {
symbols[num_symbols++] = symbol;
}
}
// 将产生式加入产生式列表
void add_production(const char* line) {
char* p = strchr(line, '-');
if (p != NULL) {
productions[num_productions].left = *(p - 1);
strcpy(productions[num_productions].right, p + 2);
num_productions++;
}
}
// 将项目加入状态
void add_item(struct State* state, const struct Item* item) {
for (int i = 0; i < state->size; i++) {
if (strcmp(state->items[i].right, item->right) == 0 && state->items[i].dot_pos == item->dot_pos) {
return; // 项目已存在
}
}
state->items[state->size++] = *item;
}
// 将状态加入状态集合
int add_state(const struct State* state) {
for (int i = 0; i < num_states; i++) {
if (state->size == states[i].size && memcmp(state->items, states[i].items, state->size * sizeof(struct Item)) == 0) {
return i; // 状态已存在
}
}
states[num_states] = *state;
return num_states++;
}
// 获取项目的 closure
void closure(struct State* state) {
int size = state->size;
for (int i = 0; i < size; i++) {
if (state->items[i].dot_pos < strlen(state->items[i].right)) {
char symbol = state->items[i].right[state->items[i].dot_pos];
if (isupper(symbol)) {
for (int j = 0; j < num_productions; j++) {
if (productions[j].left == symbol) {
struct Item item = { symbol, productions[j].right, 0 };
add_item(state, &item);
}
}
}
}
}
if (state->size > size) {
closure(state); // 递归计算 closure
}
}
// 获取项目集合的 goto
void goto_state(const struct State* from, struct State* to, char symbol) {
to->size = 0;
for (int i = 0; i < from->size; i++) {
if (from->items[i].dot_pos < strlen(from->items[i].right) && from->items[i].right[from->items[i].dot_pos] == symbol) {
struct Item item = { from->items[i].left, from->items[i].right, from->items[i].dot_pos + 1 };
add_item(to, &item);
}
}
closure(to);
}
// 构造 LR(0) 项集族
void build_states() {
struct Item item = { productions[0].left, productions[0].right, 0 };
struct State state = { { item }, 1 };
closure(&state);
add_state(&state);
for (int i = 0; i < num_states; i++) {
for (int j = 0; j < num_symbols; j++) {
struct State next_state;
goto_state(&states[i], &next_state, symbols[j]);
if (next_state.size > 0) {
int index = add_state(&next_state);
if (isupper(symbols[j])) {
goto_table[i][j] = index;
} else {
action[i][j] = index;
}
}
}
for (int j = 0; j < num_productions; j++) {
for (int k = 0; k < states[i].size; k++) {
if (states[i].items[k].dot_pos == strlen(states[i].items[k].right)) {
if (states[i].items[k].left == productions[j].left) {
action[i][num_symbols + j] = j + 1; // 移进-归约冲突
}
}
}
}
}
}
// 初始化栈
void init_stack() {
stack.data[0] = 0;
stack.size = 1;
}
// 获取栈顶状态
int top_state() {
if (stack.size > 0) {
return stack.data[stack.size - 1];
} else {
return -1;
}
}
// 符号入栈
void push_symbol(char symbol) {
stack.data[stack.size++] = symbol;
}
// 符号出栈
void pop_symbol() {
stack.size--;
}
// 执行移进操作
void shift(int state) {
push_symbol(state);
push_symbol(input[++pos]);
}
// 执行归约操作
int reduce(int production) {
int len = strlen(productions[production].right);
for (int i = 0; i < 2 * len; i++) {
pop_symbol();
}
int state = top_state();
int symbol = productions[production].left;
push_symbol(symbol);
int next_state = goto_table[state][symbol - 'A'];
push_symbol(next_state);
return next_state;
}
// 解析输入
void parse_input() {
init_stack();
push_symbol(0);
while (stack.size > 0) {
int state = top_state();
int symbol = input[pos];
if (isupper(symbol)) {
int next_state = goto_table[state][symbol - 'A'];
if (next_state > 0) {
push_symbol(next_state);
push_symbol(symbol);
pos++;
} else {
printf("Error: Invalid input\n");
return;
}
} else {
int action_index = action[state][symbol - 'a'];
if (action_index > 0) {
if (action_index == num_productions + 1) {
printf("Accept\n");
return;
} else if (action_index > 0 && action_index <= num_productions) {
reduce(action_index - 1);
} else {
printf("Error: Invalid input\n");
return;
}
} else {
printf("Error: Invalid input\n");
return;
}
}
}
}
int main() {
char line[MAX_SIZE];
while (fgets(line, MAX_SIZE, stdin) != NULL) {
if (line[0] == '\n') {
break;
}
add_symbol(line[0]);
add_production(line);
}
add_symbol('$');
build_states();
char input[MAX_SIZE];
int pos = 0;
printf("Input: ");
fgets(input, MAX_SIZE, stdin);
input[strlen(input) - 1] = '$';
parse_input();
return 0;
}
```
此代码实现了一个简单的 LR(0) 自底向上语法分析器,包括文法产生式列表、文法符号集合、LR(0) 项集族、预测分析表、栈结构体等相关内容。可以通过输入文法产生式列表和待分析的语句,执行自底向上语法分析。
相关推荐
![zip](https://img-home.csdnimg.cn/images/20210720083736.png)
![rar](https://img-home.csdnimg.cn/images/20210720083606.png)
![rar](https://img-home.csdnimg.cn/images/20210720083606.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)
![](https://csdnimg.cn/download_wenku/file_type_ask_c1.png)