C语言之实现简单的表达式计算器
这篇博文是对上一篇博文代码的重构!并在此基础上加了一个eval_express函数,实现表达式的交互计算,初步达到REPL,即读表达式、算表达式、输出结果,这样一个循环。
定义表达式数据类型和输出函数
- Express结构体,用来保存表达式的节点数据,运算符或数字
- out_value函数,输出表达式节点的值
- out_info函数,输出表达式节点的详细信息
- 以上两个函数做用是在编码过程中输出信息,主要是起到调试做用,注意:必不可少!!!
- 代码如下:
/* define express datatype */
typedef enum _ExpressDataType ExprDT;
enum _ExpressDataType {
DT_OPERATOR,
DT_INTEGER,
};
/* define express struct */
typedef struct _Express Expr;
struct _Express {
ExprDT dt;
union {
char oval; //operator
long ival; //integer
} V;
};
/* output express value */
void
out_value (Expr expr)
{
switch (expr.dt)
{
case DT_OPERATOR: printf (" %c", expr.V.oval); break;
case DT_INTEGER : printf (" %ld", expr.V.ival); break;
}
}
/* output express info */
void
out_info (Expr expr)
{
switch (expr.dt)
{
case DT_OPERATOR: printf (" op : %c\n", expr.V.oval); break;
case DT_INTEGER : printf ("int : %ld\n", expr.V.ival); break;
}
}
将表达式字符串解析成各个节点,并保存到数组中
- parse_string函数,参数estr是表达式字符串,参数expr是表达式节点数组,参数ensize是数组的长度
- 测试函数test_pstring,调用parse_string函数,观察输出结果
- 代码如下:
/* parse express string to Expr struct array */
int
parse_string (char *estr, Expr *expr, int ensize)
{
char buf[32] = {0};
int idx = 0, jdx = 1, ep = 0;
char c;
buf[0] = '+';
c = estr[idx];
while (c != 0)
{
switch (c)
{
case '0'...'9': //number
{
char n = estr[idx+1];
buf[jdx] = c; jdx++;
if (n == ' ' || n == ')' || n == '\0'|| //number end
n == '+' || n == '-' || n == '*' || n == '/') //operator
{
long lt = strtol (buf, NULL, 10);
expr[ep].dt = DT_INTEGER;
expr[ep].V.ival = lt; ep++;
memset (buf, 0, 32); buf[0] = '+'; jdx = 1;
}
}
break;
case '+': case '-': case '*': case '/': case '(': case ')': //operator
{
if (c == '-') //negative number
{
char p, n;
if ((idx-1) < 0)
p = ' ';
else
p = estr[idx-1]; //prev char
n = estr[idx+1]; //next char
if (p >= '0' && p <= '9')
{ } //c is a operator, do nothing
else
{
if (n >= '0' && n <= '9')
{ buf[0] = '-'; }
break; //negative sign
}
}
expr[ep].dt = DT_OPERATOR;
expr[ep].V.oval = c; ep++;
}
break;
case ' ': //space do nothing
break;
default:
printf ("Syntax error!\n");
}
idx++; c = estr[idx]; //next char
}
return ep;
}
/* test parse_string function */
void
test_pstring (void)
{
int len = 0;
Expr expr[128];
char *es = "-100+200*300+-400";
//char *es = "(100+200)*(300+400)";
printf ("Express: %s\n", es);
printf ("--------------------\n");
len = parse_string (es, expr, 128);
for (int i = 0; i < len; i++)
out_info (expr[i]);
printf ("--------------------\n");
printf ("Express:");
for (int i = 0; i < len; i++)
out_value (expr[i]);
printf ("\n");
printf ("Express nodes : %d\n", len);
printf ("--------------------\n");
}
/**/
int
main (int argc, char *argv[])
{
test_pstring ();
return 0;
}
/******(X(X)X)******/
编译运行,达到预期,结果如下:
gwsong@ubuntu:/tmp/boo$ gcc pe.c -o pe
gwsong@ubuntu:/tmp/boo$ ./pe
Express: -100+200*300+-400
--------------------
int : -100
op : +
int : 200
op : *
int : 300
op : +
int : -400
--------------------
Express: -100 + 200 * 300 + -400
Express nodes : 7
--------------------
gwsong@ubuntu:/tmp/boo$
将中缀表达式数组转换为后缀表达式数组
- mid_torpn函数,参数expr是中缀表达式数组,即上面解析得的数组,参数rpn是目标后缀表达式数组,参数elen是中缀表达式数组的长度!
- 代码如下:
/* get priority level */
char
get_plv (char x)
{
if (x == '+') return 1;
if (x == '-') return 1;
if (x == '*') return 2;
if (x == '/') return 2;
return 0;
}
/* middle expr to rpn expr */
int
mid_torpn (Expr *expr, Expr *rpn, int elen)
{
Expr st[8];
int idx = 0, ip = 0;
for (int j = 0; j < 8; j++)
{ st[j].dt = 0; st[j].V.oval = 0; }
for (int i = 0; i < elen; i++)
{
Expr et = expr[i];
switch (et.dt)
{
case DT_INTEGER: //number
rpn[idx].dt = DT_INTEGER;
rpn[idx].V.ival = et.V.ival; idx++;
break;
case DT_OPERATOR: //operator
{
switch (et.V.oval)
{
case '+': case '-': case '*': case '/': //operator
{
char lv, lx;
if (ip == 0) //stack empty
{
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
break;
}
if (st[ip-1].dt == DT_OPERATOR && st[ip-1].V.oval == '(')
{
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
break;
}
lv = get_plv (et.V.oval);
lx = get_plv (st[ip-1].V.oval);
if (lv > lx)
{
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
break;
}
else
{
rpn[idx].dt = DT_OPERATOR;
rpn[idx].V.oval = st[ip-1].V.oval; idx++; //out
st[ip-1].dt = 0; st[ip-1].V.oval = 0; ip--; //pop
while (ip > 0)
{
char lt = get_plv (st[ip-1].V.oval);
if (lv > lt)
{
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
}
else
{
rpn[idx].dt = DT_OPERATOR;
rpn[idx].V.oval = st[ip-1].V.oval; idx++; //out
st[ip-1].dt = 0; st[ip-1].V.oval = 0; ip--; //pop
}
}
if (ip == 0)
{
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
}
}
}
break;
case '(':
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
break;
case ')':
{
while (ip > 0)
{
char ot = st[ip-1].V.oval;
if (ot == '(')
{
st[ip-1].dt = 0; st[ip-1].V.oval = 0; ip--; //pop
}
else
{
rpn[idx].dt = DT_OPERATOR;
rpn[idx].V.oval = st[ip-1].V.oval; idx++; //out
st[ip-1].dt = 0; st[ip-1].V.oval = 0; ip--; //pop
}
}
}
break;
}
}
break;
}
}
//pop until stack empty
while (ip > 0)
{
rpn[idx].dt = DT_OPERATOR;
rpn[idx].V.oval = st[ip-1].V.oval; idx++; //out
st[ip-1].dt = 0; st[ip-1].V.oval = 0; ip--; //pop
}
return idx;
}
/* test mdi_torpn function */
void
test_midtorpn (void)
{
int len = 0, rlen = 0;
Expr expr[128], rpn[128];
//char *es = "100+200*300+400";
//char *es = "(100+200)*(300+400)";
char *es = "100*(300-200)/400";
len = parse_string (es, expr, 128);
rlen = mid_torpn (expr, rpn, len);
printf ("Express : %s\n", es);
printf ("--------------------\n");
for (int i = 0; i < rlen; i++)
out_info (rpn[i]);
printf ("--------------------\n");
printf ("RPN expr:");
for (int i = 0; i < rlen; i++)
out_value (rpn[i]);
printf ("\n");
}
/**/
int
main (int argc, char *argv[])
{
//test_pstring ();
test_midtorpn ();
return 0;
}
/******(X(X)X)******/
编译运行,达到预期,效果如下:
gwsong@ubuntu:/tmp/boo$ gcc pe.c -o pe
gwsong@ubuntu:/tmp/boo$ ./pe
Express : 100*(300-200)/400
--------------------
int : 100
int : 300
int : 200
op : -
op : *
int : 400
op : /
--------------------
RPN expr: 100 300 200 - * 400 /
gwsong@ubuntu:/tmp/boo$
计算后缀表达式,输出计算结果
- 上面的结果显示输出了正确的后缀表达式
- compute_rpn_express函数,用数组模拟栈来计算后缀表达式输出计算结果
- 代码如下:
/* compute rpn express */
Expr
compute_rpn_express (Expr *expr, int rlen)
{
Expr st[16], rs;
int ip = 0;
for (int j = 0; j < 16; j++)
{ st[j].dt = 0; st[j].V.oval = 0;}
for (int i = 0; i < rlen; i++)
{
Expr et = expr[i];
if (et.dt == DT_INTEGER)
{
st[ip].dt = DT_INTEGER; st[ip].V.ival = et.V.ival; ip++;
printf ("push %ld\n", et.V.ival);
}
else if (et.dt == DT_OPERATOR)
{
switch (et.V.oval)
{
case '+':
{
printf ("operate : %ld + %ld = ", st[ip-2].V.ival, st[ip-1].V.ival);
st[ip-2].V.ival = st[ip-2].V.ival + st[ip-1].V.ival;
printf ("%ld\n", st[ip-2].V.ival);
st[ip-1].V.oval = 0; ip--;
}
break;
case '-':
{
printf ("operate : %ld - %ld = ", st[ip-2].V.ival, st[ip-1].V.ival);
st[ip-2].V.ival = st[ip-2].V.ival - st[ip-1].V.ival;
printf ("%ld\n", st[ip-2].V.ival);
st[ip-1].V.ival = 0; ip--;
}
break;
case '*':
{
printf ("operate : %ld * %ld = ", st[ip-2].V.ival, st[ip-1].V.ival);
st[ip-2].V.ival = st[ip-2].V.ival * st[ip-1].V.ival;
printf ("%ld\n", st[ip-2].V.ival);
st[ip-1].V.ival = 0; ip--;
}
break;
case '/':
{
printf ("operate : %ld / %ld = ", st[ip-2].V.ival, st[ip-1].V.ival);
st[ip-2].V.ival = st[ip-2].V.ival / st[ip-1].V.ival;
printf ("%ld\n", st[ip-2].V.ival);
st[ip-1].V.ival = 0; ip--;
}
break;
}
}
}
rs.dt = DT_INTEGER;
rs.V.ival = st[0].V.ival;
return rs;
}
/* test compute_rpn_express function */
void
test_compute_rpn_express (void)
{
int len = 0, rlen = 0;
Expr expr[128], rpn[128], rs;
//char *es = "100+200*300+400";
//char *es = "(100+200)*(300+400)";
char *es = "100*(300-200)/400";
len = parse_string (es, expr, 128);
rlen = mid_torpn (expr, rpn, len);
printf ("Express : %s\n", es);
printf ("--------------------\n");
for (int i = 0; i < rlen; i++)
out_info (rpn[i]);
printf ("--------------------\n");
printf ("RPN expr:");
for (int i = 0; i < rlen; i++)
out_value (rpn[i]);
printf ("\n");
printf ("--------------------\n");
rs = compute_rpn_express (rpn, rlen);
printf ("--------------------\n");
printf (" Result : %ld\n", rs.V.ival);
}
/**/
int
main (int argc, char *argv[])
{
//test_pstring ();
//test_midtorpn ();
test_compute_rpn_express ();
return 0;
}
/******(X(X)X)******/
编译运行,结果如下:
gwsong@ubuntu:/tmp/boo$ gcc pe.c -o pe
gwsong@ubuntu:/tmp/boo$ ./pe
Express : 100*(300-200)/400
--------------------
int : 100
int : 300
int : 200
op : -
op : *
int : 400
op : /
--------------------
RPN expr: 100 300 200 - * 400 /
--------------------
push 100
push 300
push 200
operate : 300 - 200 = 100
operate : 100 * 100 = 10000
push 400
operate : 10000 / 400 = 25
--------------------
Result : 25
gwsong@ubuntu:/tmp/boo$
做一个交互的计算器,输入表达式,输出计算结果
- 以上计算结果是正确的,做一个命令行交互的计算器就很容易了!!!
- REPL, read - evalute - print - loop
- 读取表达式,计算表达式,输出计算结果,如此循环就可以了!!!
- 定义buf[1024]来将读取的字符串保存存起来,当输入换行符时,计算buf并输出结果!
- 退出循环用CTRL-D键,这一点LINUX老手好像都知道!
- 代码如下:
/* evalute express */
void
eval_express (void)
{
Expr expr[128], rpn[128], rs;
char es[1024] = {0};
int idx = 0, len = 0, rlen = 0;
char c;
printf ("REPL:> ");
c = fgetc (stdin);
while (c != EOF)
{
if (c == '\n')
{
len = parse_string (es, expr, 128);
rlen = mid_torpn (expr, rpn, len);
printf ("------------------------------\n");
rs = compute_rpn_express (rpn, rlen);
printf ("------------------------------\n");
printf (" Result : %ld\n", rs.V.ival);
memset (es, 0, 1024);
len = 0; rlen = 0; idx = 0;
printf ("REPL:> ");
c = fgetc (stdin);
}
else
{
es[idx] = c;
idx++; c = fgetc (stdin);
}
}
}
/**/
int
main (int argc, char *argv[])
{
//test_pstring ();
//test_midtorpn ();
//test_compute_rpn_express ();
eval_express ();
return 0;
}
/******(X(X)X)******/
编译运行,效果如下:
gwsong@ubuntu:/tmp/boo$ gcc pe.c -o pe
gwsong@ubuntu:/tmp/boo$ ./pe
REPL:> (100+200)/(90-80)
------------------------------
push 100
push 200
operate : 100 + 200 = 300
push 90
push 80
operate : 90 - 80 = 10
operate : 300 / 10 = 30
------------------------------
Result : 30
REPL:>
- 可以多输入几个表达式测试一下!!!
完整代码如下:
/* filename: pe.c */
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
/* compile : gcc pe.c -o pe */
/* run : ./pe */
/* define express datatype */
typedef enum _ExpressDataType ExprDT;
enum _ExpressDataType {
DT_OPERATOR,
DT_INTEGER,
};
/* define express struct */
typedef struct _Express Expr;
struct _Express {
ExprDT dt;
union {
char oval; //operator
long ival; //integer
} V;
};
/* output express value */
void
out_value (Expr expr)
{
switch (expr.dt)
{
case DT_OPERATOR: printf (" %c", expr.V.oval); break;
case DT_INTEGER : printf (" %ld", expr.V.ival); break;
}
}
/* output express info */
void
out_info (Expr expr)
{
switch (expr.dt)
{
case DT_OPERATOR: printf (" op : %c\n", expr.V.oval); break;
case DT_INTEGER : printf ("int : %ld\n", expr.V.ival); break;
}
}
/* parse express string to Expr struct array */
int
parse_string (char *estr, Expr *expr, int ensize)
{
char buf[32] = {0};
int idx = 0, jdx = 1, ep = 0;
char c;
buf[0] = '+';
c = estr[idx];
while (c != 0)
{
switch (c)
{
case '0'...'9': //number
{
char n = estr[idx+1];
buf[jdx] = c; jdx++;
if (n == ' ' || n == ')' || n == '\0'|| //number end
n == '+' || n == '-' || n == '*' || n == '/') //operator
{
long lt = strtol (buf, NULL, 10);
expr[ep].dt = DT_INTEGER;
expr[ep].V.ival = lt; ep++;
memset (buf, 0, 32); buf[0] = '+'; jdx = 1;
}
}
break;
case '+': case '-': case '*': case '/': case '(': case ')': //operator
{
if (c == '-') //negative number
{
char p, n;
if ((idx-1) < 0)
p = ' ';
else
p = estr[idx-1]; //prev char
n = estr[idx+1]; //next char
if (p >= '0' && p <= '9')
{ } //c is a operator, do nothing
else
{
if (n >= '0' && n <= '9')
{ buf[0] = '-'; }
break; //negative sign
}
}
expr[ep].dt = DT_OPERATOR;
expr[ep].V.oval = c; ep++;
}
break;
case ' ': //space do nothing
break;
default:
printf ("Syntax error!\n");
}
idx++; c = estr[idx]; //next char
}
return ep;
}
/* test parse_string function */
void
test_pstring (void)
{
int len = 0;
Expr expr[128];
char *es = "-100+200*300+-400";
//char *es = "(100+200)*(300+400)";
printf ("Express: %s\n", es);
printf ("--------------------\n");
len = parse_string (es, expr, 128);
for (int i = 0; i < len; i++)
out_info (expr[i]);
printf ("--------------------\n");
printf ("Express:");
for (int i = 0; i < len; i++)
out_value (expr[i]);
printf ("\n");
printf ("Express nodes : %d\n", len);
printf ("--------------------\n");
}
/* get priority level */
char
get_plv (char x)
{
if (x == '+') return 1;
if (x == '-') return 1;
if (x == '*') return 2;
if (x == '/') return 2;
return 0;
}
/* middle expr to rpn expr */
int
mid_torpn (Expr *expr, Expr *rpn, int elen)
{
Expr st[8];
int idx = 0, ip = 0;
for (int j = 0; j < 8; j++)
{ st[j].dt = 0; st[j].V.oval = 0; }
for (int i = 0; i < elen; i++)
{
Expr et = expr[i];
switch (et.dt)
{
case DT_INTEGER: //number
rpn[idx].dt = DT_INTEGER;
rpn[idx].V.ival = et.V.ival; idx++;
break;
case DT_OPERATOR: //operator
{
switch (et.V.oval)
{
case '+': case '-': case '*': case '/': //operator
{
char lv, lx;
if (ip == 0) //stack empty
{
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
break;
}
if (st[ip-1].dt == DT_OPERATOR && st[ip-1].V.oval == '(')
{
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
break;
}
lv = get_plv (et.V.oval);
lx = get_plv (st[ip-1].V.oval);
if (lv > lx)
{
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
break;
}
else
{
rpn[idx].dt = DT_OPERATOR;
rpn[idx].V.oval = st[ip-1].V.oval; idx++; //out
st[ip-1].dt = 0; st[ip-1].V.oval = 0; ip--; //pop
while (ip > 0)
{
char lt = get_plv (st[ip-1].V.oval);
if (lv > lt)
{
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
}
else
{
rpn[idx].dt = DT_OPERATOR;
rpn[idx].V.oval = st[ip-1].V.oval; idx++; //out
st[ip-1].dt = 0; st[ip-1].V.oval = 0; ip--; //pop
}
}
if (ip == 0)
{
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
}
}
}
break;
case '(':
st[ip].dt = DT_OPERATOR;
st[ip].V.oval = et.V.oval; ip++; //push
break;
case ')':
{
while (ip > 0)
{
char ot = st[ip-1].V.oval;
if (ot == '(')
{
st[ip-1].dt = 0; st[ip-1].V.oval = 0; ip--; //pop
}
else
{
rpn[idx].dt = DT_OPERATOR;
rpn[idx].V.oval = st[ip-1].V.oval; idx++; //out
st[ip-1].dt = 0; st[ip-1].V.oval = 0; ip--; //pop
}
}
}
break;
}
}
break;
}
}
//pop until stack empty
while (ip > 0)
{
rpn[idx].dt = DT_OPERATOR;
rpn[idx].V.oval = st[ip-1].V.oval; idx++; //out
st[ip-1].dt = 0; st[ip-1].V.oval = 0; ip--; //pop
}
return idx;
}
/* test mdi_torpn function */
void
test_midtorpn (void)
{
int len = 0, rlen = 0;
Expr expr[128], rpn[128];
//char *es = "100+200*300+400";
//char *es = "(100+200)*(300+400)";
char *es = "100*(300-200)/400";
len = parse_string (es, expr, 128);
rlen = mid_torpn (expr, rpn, len);
printf ("Express : %s\n", es);
printf ("--------------------\n");
for (int i = 0; i < rlen; i++)
out_info (rpn[i]);
printf ("--------------------\n");
printf ("RPN expr:");
for (int i = 0; i < rlen; i++)
out_value (rpn[i]);
printf ("\n");
}
/* compute rpn express */
Expr
compute_rpn_express (Expr *expr, int rlen)
{
Expr st[16], rs;
int ip = 0;
for (int j = 0; j < 16; j++)
{ st[j].dt = 0; st[j].V.oval = 0;}
for (int i = 0; i < rlen; i++)
{
Expr et = expr[i];
if (et.dt == DT_INTEGER)
{
st[ip].dt = DT_INTEGER; st[ip].V.ival = et.V.ival; ip++;
printf ("push %ld\n", et.V.ival);
}
else if (et.dt == DT_OPERATOR)
{
switch (et.V.oval)
{
case '+':
{
printf ("operate : %ld + %ld = ", st[ip-2].V.ival, st[ip-1].V.ival);
st[ip-2].V.ival = st[ip-2].V.ival + st[ip-1].V.ival;
printf ("%ld\n", st[ip-2].V.ival);
st[ip-1].V.oval = 0; ip--;
}
break;
case '-':
{
printf ("operate : %ld - %ld = ", st[ip-2].V.ival, st[ip-1].V.ival);
st[ip-2].V.ival = st[ip-2].V.ival - st[ip-1].V.ival;
printf ("%ld\n", st[ip-2].V.ival);
st[ip-1].V.ival = 0; ip--;
}
break;
case '*':
{
printf ("operate : %ld * %ld = ", st[ip-2].V.ival, st[ip-1].V.ival);
st[ip-2].V.ival = st[ip-2].V.ival * st[ip-1].V.ival;
printf ("%ld\n", st[ip-2].V.ival);
st[ip-1].V.ival = 0; ip--;
}
break;
case '/':
{
printf ("operate : %ld / %ld = ", st[ip-2].V.ival, st[ip-1].V.ival);
st[ip-2].V.ival = st[ip-2].V.ival / st[ip-1].V.ival;
printf ("%ld\n", st[ip-2].V.ival);
st[ip-1].V.ival = 0; ip--;
}
break;
}
}
}
rs.dt = DT_INTEGER;
rs.V.ival = st[0].V.ival;
return rs;
}
/* test compute_rpn_express function */
void
test_compute_rpn_express (void)
{
int len = 0, rlen = 0;
Expr expr[128], rpn[128], rs;
//char *es = "100+200*300+400";
//char *es = "(100+200)*(300+400)";
char *es = "100*(300-200)/400";
len = parse_string (es, expr, 128);
rlen = mid_torpn (expr, rpn, len);
printf ("Express : %s\n", es);
printf ("--------------------\n");
for (int i = 0; i < rlen; i++)
out_info (rpn[i]);
printf ("--------------------\n");
printf ("RPN expr:");
for (int i = 0; i < rlen; i++)
out_value (rpn[i]);
printf ("\n");
printf ("--------------------\n");
rs = compute_rpn_express (rpn, rlen);
printf ("--------------------\n");
printf (" Result : %ld\n", rs.V.ival);
}
/* evalute express */
void
eval_express (void)
{
Expr expr[128], rpn[128], rs;
char es[1024] = {0};
int idx = 0, len = 0, rlen = 0;
char c;
printf ("REPL:> ");
c = fgetc (stdin);
while (c != EOF)
{
if (c == '\n')
{
len = parse_string (es, expr, 128);
rlen = mid_torpn (expr, rpn, len);
printf ("------------------------------\n");
rs = compute_rpn_express (rpn, rlen);
printf ("------------------------------\n");
printf (" Result : %ld\n", rs.V.ival);
memset (es, 0, 1024);
len = 0; rlen = 0; idx = 0;
printf ("REPL:> ");
c = fgetc (stdin);
}
else
{
es[idx] = c;
idx++; c = fgetc (stdin);
}
}
}
/**/
int
main (int argc, char *argv[])
{
//test_pstring ();
//test_midtorpn ();
//test_compute_rpn_express ();
eval_express ();
return 0;
}
/******(X(X)X)******/
- 下一步继续研究数据结构和算法!!!