接着前一篇博文,再将后缀表达式转为由二叉树保存数据,并分别采用先序、中序、后序遍历该二叉树。
#include <ctype.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define MAX_EXPRESSION_LENGTH 100
enum flag_kind {
Operand = 1, Operator
};
typedef enum flag_kind Op_Kind;
struct expression_binary_tree_node {
Op_Kind kind;
int value;
struct expression_binary_tree_node *left;
struct expression_binary_tree_node *right;
};
typedef struct expression_binary_tree_node Expression_Node;
typedef struct expression_binary_tree_node *Expression_Tree;
Expression_Tree mk_single_digit_exp_node(const char *);
Expression_Tree mk_operator_exp_node(Expression_Tree, Expression_Tree, const char *);
struct stack_node_4_expression {
Expression_Tree tree;
struct stack_node_4_expression *next;
};
typedef struct stack_node_4_expression Expression_Stack_Node;
typedef struct stack_node_4_expression *P_Expression_Stack_Node;
typedef struct stack_node_4_expression *Stack_4_Expression;
typedef struct stack_node_4_expression **P_Stack_4_Expression;
void push_expression_stack(P_Stack_4_Expression, Expression_Tree);
void pop_expression_stack(P_Stack_4_Expression);
struct stack_node {
char c;
struct stack_node *next;
};
typedef struct stack_node Stack_Node;
typedef struct stack_node *P_Stack_Node;
typedef struct stack_node *Stack;
typedef struct stack_node **P_Stack;
void push_stack(P_Stack, char);
void pop_stack(P_Stack);
P_Stack_Node stack_top(P_Stack);
char *infix_2_suffix(const char *);
Expression_Tree suffix_2_expression_tree(const char *);
void pre_order_traversal_expression(const struct expression_binary_tree_node *);
void in_order_traversal_expression(const struct expression_binary_tree_node *);
void post_order_traversal_expression(const struct expression_binary_tree_node *);
int main() {
#if 0
Stack stack = NULL;
P_Stack p_stack = &stack;
push_stack(p_stack, 'a');
push_stack(p_stack, 'b');
push_stack(p_stack, 'c');
P_Stack_Node tmp;
for (tmp = stack; tmp != NULL; tmp = tmp->next) {
printf("%c\n", tmp->c);
}
#endif
char *input = malloc(sizeof(char) * MAX_EXPRESSION_LENGTH);
char *i;
for (i = input; i < input + MAX_EXPRESSION_LENGTH; ++i) {
*i = '\0';
}
char *res = NULL;
Expression_Tree suf_tree = NULL;
while (scanf("%s", input) == 1) {
#if 0
printf("%s\n", input);
#endif
res = infix_2_suffix(input);
printf("%s\n", res);
suf_tree = suffix_2_expression_tree(res);
pre_order_traversal_expression(suf_tree);
printf("\n");
in_order_traversal_expression(suf_tree);
printf("\n");
post_order_traversal_expression(suf_tree);
printf("\n");
free(res);
res = NULL;
}
free(input);
return 0;
}
void push_stack(P_Stack p_stack, char c) {
P_Stack_Node p = malloc(sizeof(Stack_Node));
p->c = c;
p->next = NULL;
if (*p_stack != NULL) p->next = *p_stack;
*p_stack = p;
}
void pop_stack(P_Stack p_stack) {
if (*p_stack == NULL) return;
P_Stack_Node p = *p_stack;
*p_stack = p->next;
free(p);
p = NULL;
}
P_Stack_Node stack_top(P_Stack p_stack) {
return *p_stack;
}
char *infix_2_suffix(const char *infix) {
size_t infix_length = strlen(infix);
char *suffix = malloc(sizeof(char) * (infix_length + 1));
char *i;
for (i = suffix; i < suffix + infix_length + 1; ++i) *i = '\0';
Stack op = NULL;
P_Stack p_stack = &op;
const char *j;
i = suffix;
for (j = infix; *j != '\0'; ++j) {
if (isdigit(*j)) *i++ = *j;
else {
switch (*j) {
case '(':
push_stack(p_stack, '(');
break;
case ')': {
char c;
while ((c = stack_top(p_stack)->c) != '(') {
*i++ = c;
pop_stack(p_stack);
}
pop_stack(p_stack);
break;
}
case '+':
if (op == NULL) push_stack(p_stack, '+');
else {
while (1) {
if (op == NULL) break;
switch (stack_top(p_stack)->c) {
case '(':
push_stack(p_stack, '+');
goto label_break;
case '+':
*i++ = '+';
pop_stack(p_stack);
push_stack(p_stack, '+');
goto label_break;
case '*':
*i++ = '*';
pop_stack(p_stack);
break;
default:
break;
}
}
}
label_break:
break;
case '*':
if (op == NULL) push_stack(p_stack, '*');
else {
while (1) {
if (op == NULL) break;
switch (stack_top(p_stack)->c) {
case '(':
case '+':
push_stack(p_stack, '*');
goto label_break_1;
case '*':
*i++ = '*';
pop_stack(p_stack);
push_stack(p_stack, '*');
goto label_break_1;
default:
break;
}
}
}
label_break_1:
break;
default:
break;
}
}
}
while (op != NULL) {
*i++ = stack_top(p_stack)->c;
pop_stack(p_stack);
}
return suffix;
}
void push_expression_stack(P_Stack_4_Expression p_stack, Expression_Tree tree) {
P_Expression_Stack_Node p = malloc(sizeof(Expression_Stack_Node));
p->tree = tree;
p->next = *p_stack != NULL ? *p_stack : NULL;
*p_stack = p;
}
void pop_expression_stack(P_Stack_4_Expression p_stack) {
if (*p_stack == NULL) return;
P_Expression_Stack_Node p = *p_stack;
*p_stack = p->next;
free(p);
p = NULL;
}
Expression_Tree suffix_2_expression_tree(const char *suffix_expression) {
Stack_4_Expression exp_stack = NULL;
P_Stack_4_Expression p_exp_stack = &exp_stack;
const char *c = NULL;
for (c = suffix_expression; *c != '\0'; ++c) {
if (isdigit(*c)) {
push_expression_stack(p_exp_stack, mk_single_digit_exp_node(c));
} else {
Expression_Tree t2 = exp_stack->tree;
pop_expression_stack(p_exp_stack);
Expression_Tree t1 = exp_stack->tree;
pop_expression_stack(p_exp_stack);
push_expression_stack(p_exp_stack, mk_operator_exp_node(t1, t2, c));
}
}
Expression_Tree res = exp_stack->tree;
pop_expression_stack(p_exp_stack);
return res;
}
Expression_Tree mk_single_digit_exp_node(const char *p_digit) {
Expression_Tree t = malloc(sizeof(Expression_Node));
t->left = NULL;
t->right = NULL;
t->value = *p_digit - '0';
t->kind = Operand;
return t;
}
Expression_Tree mk_operator_exp_node(Expression_Tree first_operand, Expression_Tree second_operand, const char *pc) {
Expression_Tree t = malloc(sizeof(Expression_Node));
t->left = first_operand;
t->right = second_operand;
t->value = *pc;
t->kind = Operator;
return t;
}
void pre_order_traversal_expression(const struct expression_binary_tree_node *tree) {
if (tree == NULL) return;
switch (tree->kind) {
case Operand:
printf("%d", tree->value);
break;
case Operator:
printf("%c", (char) (tree->value));
break;
default:
break;
}
pre_order_traversal_expression(tree->left);
pre_order_traversal_expression(tree->right);
}
void in_order_traversal_expression(const struct expression_binary_tree_node *tree) {
if (tree == NULL) return;
in_order_traversal_expression(tree->left);
switch (tree->kind) {
case Operand:
printf("%d", tree->value);
break;
case Operator:
printf("%c", (char) (tree->value));
break;
default:
break;
}
in_order_traversal_expression(tree->right);
}
void post_order_traversal_expression(const struct expression_binary_tree_node *tree) {
if (tree == NULL) return;
post_order_traversal_expression(tree->left);
post_order_traversal_expression(tree->right);
switch (tree->kind) {
case Operand:
printf("%d", tree->value);
break;
case Operator:
printf("%c", (char) (tree->value));
break;
default:
break;
}
}
运行结果
1+2*3
123*+
+1*23
1+2*3
123*+
1+2*3+4*5+(6+7)*8*9
123*+45*+67+8*9*+
+++1*23*45**+6789
1+2*3+4*5+6+7*8*9
123*+45*+67+8*9*+
缺陷
同博文