|
  
- UID
- 133
- 帖子
- 51
- 精华
- 1
- 积分
- 186
- 金币
- 55
- 威望
- 2
- 贡献
- 0

|
C语言表达式计算器
为了方便了解流程,在程序中把计算过程也输出了.而且栈操作的实现部分也是自己实现的.* W- K i' \+ P& c
程序用两个栈,optr寄存运算符,opnd寄存操作数和运算结果.输入的表达式以等号结束,例如:2*(1+2)=- O* ]% T, K& f
/**************表达式计算器************/) d, |: p2 V& d% D4 l2 i6 V4 @& ~ d/ n
#include <stdio.h>! m7 e+ t$ q- H. E! k5 g; m
#include <stdlib.h>; o: [7 S; p3 ?: h: |
#include <string.h>* C! k: p' z) `
#include <conio.h>
+ x2 Y- J& z4 { y ]9 a#include <malloc.h>
! M/ Y& ^( J/ ~$ F- ^( e+ x1 N$ M3 q3 u
#define STACK_SIZE 1000 r7 W; S" k+ K. K
#define APPEND_SIZE 10) k/ B p7 q w+ s
& B m$ m [* N7 ostruct SNode{
h+ R7 m/ g# Q float data; /*存放操作数或者计算结果*/
* D/ W. w) F1 V; t' Q, O- Y2 s4 b char ch; /*存放运算符*/
- ?0 c3 e$ I0 n8 N! [. {+ ~* P& I};- F# v2 d; a; y, x8 N
7 Z- a& a- s! N. s
struct Stack{! T) l5 R9 s* V7 g
SNode *top;
7 @+ @+ u5 `& o SNode *base;
2 y j* C, ]8 f# Q3 R+ x! o int size;
$ ~6 Z" p. J5 u, h* K P# S- ]};, x" [8 o' k2 x+ f' _# e( l# o- T
1 p! K* {# L. y' S* I C/*栈操作函数*/
5 o, E) R6 E9 Z9 Iint InitStack(Stack &S); /*创建栈*/
+ U% e' |& O( R* d& t1 `' Hint DestroyStack(Stack &S); /*销毁栈*// v/ O! W, v( C7 \+ f
int ClearStack(Stack &S); /*清空栈*/
& I6 ]2 j4 z- d4 S& U8 R% [int GetTop(Stack S, SNode &e); /*取出栈顶结点并返回节点值*/
5 |! f Q& n3 ~, K% w1 pint Push(Stack &S,SNode e); /*将结点e压入栈*/4 @; a. Q, S: |4 c7 V
int Pop(Stack &S,SNode &e); /*删除栈顶结点并返回其节点值*/ O9 c0 c4 f/ L7 E
[$ o; ~" S* s6 }/ z; A4 u7 F0 W/*表达式计算器相关函数*/
# s. I( E) R7 ychar get_precede(char s,char c); /*判断运算符s和c的优先级*/
) ^$ }! ~# W& q4 C4 uint isOpr(char c); /*判断输入的字符是不是运算符,是则返回0,否返回1*/
- y& ?9 F9 c$ E# ~# k+ P/ Nfloat operate(float x, char opr, float y); /*计算x和y经过运算符opr计算后的结果*/, l& V( E; m& p$ Q
float compute(); /*表达式结算器主函数*/
, p3 F5 y( O$ V f7 P) x" Uchar *killzero(float result); /*去掉结果后面的0*/
( G+ a) m1 x$ V; w1 \* x. j- g& ]( f- y3 W% @0 _4 Z
int InitStack(Stack &S)
- \& j" K. `# [{* {. p3 q6 ~; d0 }% X. s
S.base=(SNode *)malloc(STACK_SIZE * sizeof(struct SNode));+ f- p: }8 X" g$ U! g
if(S.base==NULL)9 n* q4 S) F' J5 A8 |
{ q7 h" T+ q$ O) H/ M
printf("动态分配内存失败!");; b |$ l7 h+ j( X2 ?
return -1;) j- H6 C& Y) P; K9 i+ ^
}
; s- L9 A8 V$ y; w S.top=S.base;
( ^ q- f* T; K' J6 `: C+ i) O+ \( j S.size=STACK_SIZE;* x$ w+ A" W, y4 ^2 j3 k! l
return 0;. o- z& o/ ?4 C; w
}: }) M3 W, P6 @) T/ v8 E9 G
6 h0 \! q/ n5 b) D- M$ F8 ?# y* x6 _int DestroyStack(Stack &S)5 J% u4 N' n: W0 b
{, V* d+ X1 w" W$ H/ `$ G( o4 n
free(S.base);
" |, g+ a' g' a$ H4 n5 h return 0;
& X. t0 O% l" V D1 L6 u9 P4 B}
% A4 q$ R$ W3 L; N# A6 L' T0 \1 M; \% H7 q
int ClearStack(Stack &S)
7 S0 J0 f, L- _{
# ]. f. V/ C2 u' K6 F4 w( ^" f S.top=S.base;
& b1 C! w. i# Z/ e1 d return 0;
( l4 D( A2 F" n2 n! k. H3 t}
0 d: J$ @% w6 i: T( X# N4 D& a7 \
int GetTop(Stack S,SNode &e)
+ C# @" C3 ~+ l. B* |: I7 D{: U4 H! p4 \ j
if(S.top==S.base); Q( M$ u: X; p4 H
{9 {# s! n$ ^. j6 r% e- L+ p7 z2 |
printf("栈以为空!");
( @: P/ S6 h2 Q return -1;
' Q) h+ u1 C) Y }
! m. t. z+ @5 B+ Q& l; D2 u' u# V e=*(S.top-1);
( [* L5 }' F' o8 u% D/ [& B$ M return 0;; A. P1 \* v+ O5 p% v: O
}
: E9 Q3 U! z; ~ c* @; I6 y- L$ ]( \2 Z/ Z
/ H4 C; u" \3 c& T! r8 qint Push(Stack &S,SNode e). K; A6 d; q& d- Y5 m
{
' X' j% k t' O; D if(S.top-S.base>=S.size)
- x) m- b, W6 n" j0 H6 N- X; R9 x {
" y6 w1 o# t- W" |! A; q$ k( @% u S.base=(SNode *)realloc(S.base,(S.size+APPEND_SIZE)*sizeof(struct SNode)); C% o; c9 n# o4 p
if(S.base==NULL)
/ K0 M+ Q! ~1 P1 K; v, G( T {. V( \9 x( h) x2 f( s8 [/ {
printf("动态分配内存失败!");
7 y$ |9 v8 d2 A9 }$ e8 V% t return -1;* {7 r! O u8 ?' U
}9 D4 x- R+ b; T' w. `
S.top=S.base+S.size;/ R# ?" N! R2 q, S" r
S.size+=APPEND_SIZE;# ~' b! Y8 f- M
}
( N4 }0 B" ~4 a- J- X6 I& Y$ {* R *S.top=e;/ k! v; t0 L7 x2 m/ H
S.top++;
/ A& Q2 s' N0 K7 ^ return 0;, d o0 a* Z' U5 h) I
}
! P4 z8 K8 d( T7 u3 w+ m w2 U2 G: m; K# y0 V" U
int Pop(Stack &S,SNode &e)
$ b. w) x- y) ?5 X{8 y P3 A9 M" _2 }, w$ F
if(S.top==S.base)3 |. N ?9 h" z4 A2 b. |
{# ?# g# b+ U( G0 r L5 Q$ W
printf("栈为空!");8 x I; q5 i- D0 N8 x2 O& Y) U
return -1;; Q" Y4 u) k. C5 t2 k3 ?" D
}
; W, Z: x9 A1 p0 Y2 W4 R2 u5 O" x8 u e=*(S.top-1);
" \ b+ G& k1 V. m- J S.top--;
$ m- G; v# |% A( r8 j- ]) z( ? return 0;
+ O8 Z. n; c0 ` m+ m' U0 `}
: t6 F7 j2 H9 A9 M0 M: w; m
H3 n. U: w- z9 Ichar get_precede(char s,char c)7 k/ A2 X# T9 D3 S) E; b
{* j: _$ |9 O' h- B3 P9 x
switch(s)
$ H' X0 |' t# X' q {" R2 w$ ^7 v) H9 v' c1 k/ K% z" i; D @
case '+': 4 W# n. X7 q" z8 b6 z/ d% K' B
case '-':
% w, `% E0 U9 a9 F: c if(c=='+'||c=='-')' P' q# M, Q. E" K& T( @
return '>';9 U- [0 @' T" G
else if(c=='*'||c=='/')" v, Y- Y1 i. g7 Q
return '<';; s( b2 D$ E: \& r' Z0 A0 q
else if(c=='(')6 u) m' `0 d* [9 q3 H) O
return '<';# J, M* r- ?" r
else if(c==')')
4 J, o& h# f" W: T return '>';
5 Q3 S4 o6 a/ {8 d4 y2 G( i" j else 1 _7 V* h1 `, h, _9 V
return '>';1 G; v, [1 w" a/ @, z! }- F
case '*':& d9 t% l9 }& S, ~5 z
case '/':
9 d3 L5 R$ r+ L/ V if(c=='+'||c=='-')
: o' K, [* X+ A- @2 Y return '>';
9 M M) o- K, e! b) C else if(c=='*'||c=='/')5 i! x, ^1 X8 ]
return '>';3 i$ X$ r* j, w4 u
else if(c=='(')- _& N$ A; y1 e
return '<';2 j9 v) m* h% ?, p7 ^; o
else if(c==')')
4 J9 z& M4 Y6 n; X b: m return '>';. P3 y+ I8 R5 k1 ?) p' g( ~% t. d
else
; p: l' C4 c: G0 X2 c return '>';8 E5 c6 ~6 t1 ]; m2 ?5 R# c
case '(':
( f5 p) w$ `( B9 T4 U' W4 \, n if(c=='+'||c=='-')+ t: G' k* i/ ^8 [( _- s
return '<';0 M1 L0 i: Y* c+ Z8 S! v
else if(c=='*'||c=='/')0 p2 ^9 i/ G/ l7 q; R: Z6 I8 r
return '<';+ e4 s1 @! H6 ~ m. o7 e! V
else if(c=='(')
/ t9 ?* e- L7 H/ B3 `4 m) ] return '<';" Y) ^6 H5 |3 M* T. L
else if(c==')')# q$ v- [% \: ]+ K" e# Q
return '=';
& ~2 P: |) K( d( y4 p$ S$ ?* t else, _+ b' \- R2 d$ d
return 'E';
- S5 N, K% S2 R) d* L' ]) q. m$ l case ')':
; B: l' f% k: s if(c=='+'||c=='-')
, p! ]$ `8 A* P: V+ {, L" g return '>';
+ G8 {8 B! S$ o else if(c=='*'||c=='/')9 c" B A* R& r& o+ Y5 V
return '>';4 P/ w5 ^' J/ W+ y, L# {
else if(c=='(')8 m, P, q3 [, @% O
return 'E';7 c* O% D4 _ o0 b( ]
else if(c==')')3 t0 X$ Y- A" b3 H9 v
return '>';7 O6 K O9 ?) Y" T7 o: l; a
else
! x" F u) G. G9 S* L# F- L return '>';
6 \( ~* T6 g+ m) I7 z. m case '#':
5 j, e* t( _, ^; n5 g& X7 S9 U if(c=='+'||c=='-')
1 _/ R9 n6 L, N return '<';
, q, N: u0 I2 C" V0 V, F" X else if(c=='*'||c=='/')
6 I6 e2 A* A2 E% j* L ]. D! Z* x return '<';
6 P& S3 J3 a' \7 w: K else if(c=='(')( I9 a$ a& [/ l# U, U1 X4 _+ z' v
return '<';
& q2 b' S. ]4 q else if(c==')')
3 R- _0 Y/ s T x return 'E';
4 [+ b6 z6 I6 a4 F6 ]$ u, X9 h) C else8 g! L0 Z# j( L# a% t# d
return '=';
2 w2 y) s7 ^7 E' l& ? default:
2 ]7 h( m+ S; V4 T% Q% `* @' V* e9 ~$ A break;2 ?9 M* u2 X) E( Q) U3 L( x
}
* u+ V4 _' P$ |6 ?4 K( a# v. D return 0; ! K9 f# |0 k1 n
}. C# m& Q1 f! V' c* j
8 u2 l- G8 |$ V/ V- p8 O' w* xint isOpr(char c)
5 \1 t' @1 a. T5 k6 [* f. `{
* X6 Y5 R7 @; D if(c=='+'||c=='-'||c=='*'||c=='/'||c=='('||c==')'||c=='=') B% m1 \ r# F" p" f A
return 0;6 x: a7 |4 ]% R& n4 K8 d: Y9 \ {
else 3 B8 o9 y3 ~( t, A; U' ]) i& i; q
return 1;
6 w8 p+ _3 b8 k+ i2 ]% p}: |$ d9 k, v4 m
$ p/ q. V) t. [$ {6 T/ p0 }% U' @
float operate(float x, char opr, float y)
. S, w8 [% b% R# ^{
8 ?" {9 Y: e" M! S* Z5 h" E float result;
6 k0 `9 P- w/ Z6 B2 B5 x, Q switch (opr)2 h; @! [0 l; Y! M! G
{
9 |0 \0 e0 g+ m: k0 u case '+': 2 J7 z) h' C# t
result = x + y;7 I, R& K0 B6 m+ m3 G" \: w+ ]! J
break;, H' y+ X _, |6 @5 X
case '-': , c* H6 V" E: @3 j
result = x - y;
1 S6 q$ i% c v' G- [- g7 g break;0 t% @. l$ g3 j& i
case '*':
4 Q- k: n+ K e2 z result = x * y;
$ P3 j0 P; f; X8 N6 _4 @! U break;
4 e N* y9 e: I0 I& k, s2 w) x case '/':
" E. \. V- l# K. Y4 G+ E) | if (y == 0)2 Y- \. G; V Y" Q& m1 p0 l
{
; z: V! z& A7 o$ F1 j! e0 n printf("Divided by zero!\n");
3 U% v0 ^2 U: y return 0;: q1 N: T3 b* \3 h6 T/ H6 j
}
2 Z: m+ ^) f: m9 i, M0 U. ` else( H' v+ y- q) e3 I- P' ~
{5 ]; C3 H+ q& y* \0 @, w
result = x / y;
3 f2 @+ g# h/ ^9 `; ?+ V break;
* ^4 a4 A1 Q; M! E: ]! Y }
6 b- E C1 P1 k* e6 a+ Y0 ~' [8 E default:
4 J2 |2 f0 P% r: [2 [2 z2 J& f3 H# P9 M printf("Bad Input.\n"); 5 ^$ x! u2 O+ k2 p. ~% U8 }5 P
return 0;6 @* h/ {3 X8 T; y
}% {. M3 x9 n6 q: ^
return result;
4 J8 @. q g( h7 q( ]} 4 |2 U7 {- k6 F+ @: u; o
0 f+ L2 K; R4 g- Jfloat compute() /*计算的时候运算符栈顶结点的优先级始终最低*/6 V- {7 L9 @" W. m
{3 y0 n' g+ j( \2 l# I0 v1 w
Stack optr,opnd;' t( Q! I) b/ z# ?
struct SNode opr_in,opn_in,opr_top,opn_tmp,e,a,b,opr_t;% {, Y2 I ^! O& n+ d3 x+ B
char c;1 T# M' I' }! n G, K3 b5 ^7 B, d
char buf[16];; p7 U g& p h! c& a; W
int i=0;+ l. f, {; A) p+ L4 T0 b
' e0 l1 W" X% P- s: N$ _/ ?2 I6 m InitStack(optr); /*用于寄存运算符*/
& a1 L/ ^$ m. ] p InitStack(opnd); /*用于寄存操作数和计算结果*/
) ^& t! F$ [4 x2 B2 b. n4 @ memset(buf,0,sizeof(buf));
/ s3 _/ N, u4 f2 c2 F, l ! [( F' @" ^7 t' t
printf("Enter your expression:");! S: R8 t$ e6 F9 C! T$ f" x2 m
& R) z) }% B% v5 b0 I
opr_in.ch='#';
7 E! W+ }. V9 `" b0 z% Q Push(optr,opr_in); /*'#'入栈*/# Z& B# m6 o6 y7 ?+ _; D
GetTop(optr,opr_top);) L% d+ r; W* k" j) Y7 P6 g9 q3 [
c=getchar();5 a; b v+ a2 v6 x; k9 s! Z
while(c!='='||opr_top.ch!='#')
5 Q. t: x9 A; i+ ]- _ q5 ?$ V* k {- Q, X5 K1 e1 n# O- U
if(isOpr(c)!=0) /*不是运算符则保存到buf中,以便得到操作数*/0 I9 `, ^& E! a: S/ z: u
{: }" G" {4 R' q; l8 ~* ~. o
buf=c;4 `9 `. ?% Q( X; @8 U J
i++;
7 Q& @% I$ M+ s9 s7 ^1 \2 [ c=getchar();
1 V" v0 @5 u; I; Z% [! L/ r }
( f1 U* [9 D+ s else /*是运算符*/
" e2 |* m5 }5 ?% U0 h {) H6 r7 {' r6 z, M, A6 G
buf='\0';' I3 ~5 N! Y( v) U" f T
if(i) /*判断buf是否为空,不为空则取出值,压入操作数寄存器,并将buf置为空*/9 d# @+ D+ w1 q6 q8 ~
{
, {& ^) U2 H7 r1 g opn_in.data=(float)atof(buf);
/ h6 F _+ r" E- X& ~ Push(opnd,opn_in);
0 F( H8 j9 @3 x* W1 C Y0 C6 { printf("opnd入栈:[%f]\n",opn_in.data);7 a; B V# J3 V1 @
i=0;
) M! Q4 a. J' A6 y% W1 p8 J4 g memset(buf,0,sizeof(buf));
{" j# M3 ^3 ]" b+ f4 F2 P% S }' H; a. H- a+ y7 B9 L
opr_in.ch=c;
# g, g. m' d# S& N& T! x switch(get_precede(opr_top.ch,c)) /*根据运算符优先级做相应操作*/9 x8 N( f4 M- w* r C% c3 L6 M% |9 U
{
2 X# j0 D& l& S case '<': /*优先级小于栈顶结点,则运算符入栈*/) d+ n A2 j4 [3 z# V* O
Push(optr,opr_in);
* o" U5 a5 W1 w3 M/ c, { printf("optr入栈:[%c]\n",opr_in.ch);: C! m$ ]0 a0 l- Y7 l7 @3 O8 L
c=getchar();" o8 @+ \ _% N: m
break;
7 D5 G3 c8 t2 U6 X: v9 v2 U+ d case '=': /*优先级等于栈顶结点,即是括号,去掉括号*/2 W/ S3 U. V, s4 X+ G/ U1 f
Pop(optr,e);
% E1 l. t4 ~, x: e) ^# A; X: _ printf("optr出栈:去掉括号\n");+ r8 C* i# ]" S' s# [
c=getchar();6 Z w/ V2 w; X4 B" H
break;& q; `5 ~4 D, ^; \
case '>': /*优先级大于栈顶结点,取操作数和运算符计算*/
; e; J1 _) Q" m, q Pop(optr,opr_t);
8 h! d" F+ ~ ~7 V printf("optr出栈:[%c]\n",opr_t.ch);6 ?7 W2 y! Z# L. ?
if(Pop(opnd,b)<0)
& T: T* d* t$ T* e3 ?; D {' P& s9 q1 e, Z/ P
printf("Bad Input!\n");' O. a: P& x" K
fflush(stdin);
G! H) a G1 v: ? return -1;4 K3 ]0 S) o0 R. h* z
}
7 U; A- m2 f3 N F1 h printf("opnd出栈:[%f]\n",b.data);' y' [8 {! s$ S8 J# i3 G* H
if(Pop(opnd,a)<0)3 f g1 W* k3 H" B C
{0 @. E8 \' @6 u' `4 A
printf("Bad Input!\n");7 Y5 v4 Y, w5 p. q1 S$ R, L
fflush(stdin);
! W2 \) s! Q2 E; u# ?- N' q& M return -1;4 C6 ^+ x3 C& S! q4 {0 ?/ j
}! U0 I3 g7 X! T
printf("opnd出栈:[%f]\n",a.data);
$ Q9 n) {- T& U7 X# M% {3 } opn_tmp.data=operate(a.data,opr_t.ch,b.data); /*计算*/# {; r' v1 M# r. E, }2 A9 b
Push(opnd,opn_tmp); /*将计算结果压入操作数寄存器*/6 K3 |3 w) a! r+ q$ `9 H: M, ~+ Y: g
printf("结果入栈:[%f]\n",opn_tmp.data);; ]4 y; y# I* x6 F5 i- K* {) Q. A
break;1 K5 K& z7 ~: H* Y! I: e
}
! s+ C1 i9 Q- x' m! H }
, I- R0 T, n7 z: P# J' }1 S3 Q GetTop(optr,opr_top); /*取出运算符寄存器栈顶结点*/ 9 Z: e$ m2 m6 ?& r) q' Z# k* n
}
% A2 m/ o0 M- N GetTop(opnd,opn_tmp);
. z. C; K' q& E DestroyStack(optr);0 a/ K9 R- b! ~# V$ v
DestroyStack(opnd);7 ~; ~+ N G8 @: e
return opn_tmp.data;6 @4 |* j4 ]2 }5 h7 i# v9 o, B! L( K" X
}
7 _# S, s) u! }+ Z1 \! F6 G: n% ]5 m' m% Q% n! e! S
char *killzero(char *res,float result)
. r# I' I6 R$ o{! x9 R% q# j' h! K
int i;5 ]( @8 x w2 E8 z9 @$ J* u
/ f- N0 c) U# ]" p6 X+ M
sprintf(res,"%f",result);5 b- }, }2 G" M! }/ r
i=(int)strlen(res)-1;- G T6 f: i2 \2 t5 x$ r* z
while(i&&res=='0')' N& Y+ p( E" c7 d3 r n; u
{% B6 t& i; x1 {9 }
res='\0';5 z: c) T) M/ j9 I* I: ?
i--;! S: e" T2 J+ u& G5 Y/ ^8 B7 w
}
( C; `9 L5 Q2 W2 Y2 y if(res=='.'): F! X" t l3 e3 n4 `' g, _9 Y
res='\0';
/ `; q! k c2 r5 P2 J9 w# l return res;9 ^! v; f9 y$ I% z& ]- _( R z3 W% o- U
}2 B& t7 ?/ E9 R
. o& ~( V1 t( M5 O; T2 T7 Oint main()% Q2 I- ?5 Z4 p/ ]3 H+ O, I
{, [: I. j7 ~$ I( Y& B" T6 s3 C4 x
char ch;2 K8 x- ^. A5 A) v# p: w
char res[64];
3 F6 Y6 V, N" c* ? float result;
7 t. V& U1 N L& O6 J while(1)
0 E6 `) \0 w) X8 ~9 F N, U {8 d) z7 Q2 |- D5 M3 C
result=compute();
& O9 ]: z9 }$ u printf("\nThe result is:%s\n",killzero(res,result));/ {0 B I9 s+ T! Q
printf("Do you want to continue(y/n)?:") ;
$ x/ N0 b W; i$ \/ L ch=getch();
. C2 Q2 G: f! I" m7 f putchar(ch);
( R+ ]: b( ^3 D4 O" J if(ch=='n'||ch=='N'), }$ Z& p: h! {# b1 a
break;
7 d0 Z, R# O) M! M8 E- p else
% C& C/ L% u, h: s: U system("cls");7 o+ P. N3 u4 p1 f: b
}
3 |3 C* ?! \" l, Z' s return 0;
1 X; ], l7 n3 ^}
# p8 l1 a" G' f; ]
, v! r. i0 P# q0 B[ 本帖最后由 zw2004 于 2008-1-21 17:21 编辑 ] |
|