返回列表 发帖

一个计算四则表达式的模板

在9月8日那天我特意编写的,给大家分享的,5 s0 E/ A$ M& V+ h5 z9 \, ?
一个很方便的函数模板,可以并且只可以计算含括号的四则表达式6 K  Z1 Y  ~! ?8 z8 H, ?. u
只有一个函数接口:int GetExpValue(_Tstream& istrin, _T& nReturn)' V! g, b  q# {; ?! R
参数解释:
7 r8 ?; ^' T' @! B* U. ?istrin: 一个输入流,可以是标准IO流,可以是文件流,也可以是串流
6 H0 |. ?3 t! Q4 g  ^  F- r- r& KnReturn:用于接收计算结果的变量,计算所使用的类型由这个变量确定  y+ a; i' n! O4 {) V0 [$ P% C
返回值:
3 u% I  a! N8 F3 p, n9 B返回非0表示计算成功,0表示计算失败有错误5 s" }9 R) B( Q

; |' J8 |4 U- k7 J0 r9 g, N
: l, ]1 {. V9 L* _% g6 t5 A6 q7 x2 a% ^- ~
程序代码:
$ {- ~2 P7 M2 J2 {. u* L
% L7 v. M( b" Cnamespace fy_Exp{
& p7 B' v5 n/ r2 }7 R: n( a2 nnamespace {template <class _T>
) n/ m6 ^2 i- ~! l' U/ Yinline _T GetExpValue(_T t[], char& csym){
6 z3 u# I) @, x' H% @( \9 t    char c=csym; csym=0;
/ L# A0 C. ]+ o7 A- B9 o! h  O8 r+ z    switch(c){
2 Y# ~& z4 j# G5 B& f) I! W    case '+':return t[0] += t[1];4 m8 A  X8 Z8 L* A5 ^9 l
    case '-':return t[0] -= t[1];
: u! O1 m. z: w: F- U    case '*':return t[0] *= t[1];% q' k% h6 O) O: V5 W* U/ {
    default: return t[0] /= t[1];//case '/':1 E, h" R; h. r# N0 F3 h
    }
! d  ]4 B  a+ s3 h+ }}}3 c( {0 z3 ?( u# s
template <class _T, class _Tstream>" m  ^/ _5 C' J
/* _Tstream: inputstream, _T: get return value3 h* D1 M& Y$ P: }/ A
* Return nonzero if get value successfully */' o( j0 G$ D! M$ C% |
int GetExpValue(_Tstream& istrin, _T& nReturn){; b0 ~1 g+ C; j$ W# T$ f) B$ c( M2 \
    _T t[3] = {0}; //雨中飞燕之作/ K. A/ k9 U! C
    char csym[3] = "++";/ D# F% A) N; L) l$ Q" {& X
    int nLevel = 1, nERR = 0;
% `3 u8 ^8 E# I3 a. u+ ^    if(!(istrin>>t[1]))istrin.clear();
# Q( B% r3 D& Z+ P    for(;;){
) W% J; W. U1 g" N        if(istrin>>csym[2]){
' y! d( E3 y8 e# o9 n  B            switch(csym[2]){
7 c0 L. W  r) \4 L+ X  T7 u& {            case '(':
; u( J& J: a) B1 g5 x" p. g                if(!csym[1]){nLevel=0x100; nERR=1;}else
. Q# r* [4 Y& m  T6 B                if(!GetExpValue(istrin, t[2]))nLevel|=0x10;+ C( j+ n3 S8 {: l" o! E4 M
                else{nLevel=0x100; nERR=1;}& K$ n/ D9 `* S! `/ [( J* v  y) K8 S
                break;
+ \. \+ W4 z* C) G9 G+ S% [+ A' a            case ')':
. e( q, C- W; i) y* H' `                {nLevel = 0x100;}break;
  \( E, x9 C  t, h6 r8 W            case '+':case '-':case '*':case '/':9 H% @: @1 [2 _, p  K0 u
                {csym[nLevel++] = csym[2];}break;+ Y0 B7 y. M2 q1 K( Y$ g( q
            case ' ':case '\r':case '\n':case '\t':continue;4 V2 s& ?1 t. A1 z
            default:, A, x2 H1 N( J
                {nLevel=0x100; nERR=1;}4 I) p5 B5 E1 `0 t
            }) ?8 l1 u# c, M! R) D, H% D- }
            if(nLevel==0x100)break;# n; b. m' n$ i/ R0 G4 d& ~) r* @
            if(nLevel&0x10 || istrin>>t[2]){* }: D. Z! V2 p% f
                nLevel &= 0xF;
- t4 p2 z* m  j$ ~& S                if(nLevel==1){t[1]=t[2];csym[1]=0;continue;}- B+ O2 a( f! R! o+ X9 s9 Y
                if(csym[1]=='*'||csym[1]=='/'){
/ C3 s1 k+ X% x/ J  d+ l: r                    GetExpValue(t+1, csym[1]);
6 O; L* D" F& y                }
; _+ e7 q0 f& }' f! Z1 C4 @4 |                else{( O" q+ B3 B8 `
                    GetExpValue(t, csym[0]);( B: [, @7 I( [# l. H+ s# u* h' Q
                    t[1]=t[2];csym[0]=csym[1];csym[1]=0;
6 @$ [+ ^- Y9 B7 D' T4 y1 W( S$ Q                }
+ i8 B, V7 J" y$ s6 @) s$ X                nLevel = 1;% ?( d8 y( J2 d, Y) q: s9 _; X. c
            }2 f) G7 V/ f3 Y: E
            else istrin.clear();
1 Y# @! _: Z2 _/ I7 P2 j0 F        }
$ ^$ L8 X( i& K3 U5 o0 y3 h; G        else{nERR = -1; break;}
" n+ @' P: @! V    }" w9 J% d! s# v8 l5 q
    if(csym[1])t[2]=0,nReturn=GetExpValue(t+1, csym[1]);
, H2 B, z0 ?. s9 J/ Z3 y    else nReturn=GetExpValue(t, csym[0]);
5 W! ~; C8 q2 J5 c    return nERR==-1?1:0;- {8 ?" R' J( r7 ?
}}8 r: s4 F7 D1 b: r/ N9 ]/ j% w1 n
7 w, @" L2 [9 R; v: m3 P. i- Y! ?
4 Q  C. P- C5 U! A+ m) U# d4 b: y

1 l' c7 O$ s0 ^函数模板使用示例:& H2 G! H- K& D" S: K
在以上那段代码的后面加上以下代码:
$ F, O4 d3 w5 e2 @' R: p
) Z+ w7 r: v: T
& F/ ~6 Z% _  `/ Q8 @
! \7 v) h8 b8 M6 Z2 p程序代码: ) y! u0 b5 @& p+ c8 g. [* r

0 W  z8 r9 }# p1 n2 m) r5 Z#include<strstream>+ Q) s9 f4 a: H' V$ v
#include<iostream>8 S9 k$ w+ ], \
#include<string>
$ z# T; C. X0 D. }  uusing namespace std;, y% \& R/ F0 C! a- Y1 Z
int main(void)
* s, O- P! P0 L7 v) {2 Y0 t{
- a' ^9 e) g6 G9 v; g# i, |    string s1;8 P  X/ N/ l1 F% m
    while(cin>>s1)
) {+ Y* u/ q) `9 f, p) n" G: ?  W, S    {
5 E$ n$ X7 G/ O& ?: n  z5 _6 N        istrstream isin(s1.data());
3 c% v) `1 `2 \        double d;
! v; t: J5 U- M" [        if(fy_Exp::GetExpValue(isin, d))
1 P+ J* F+ l; M7 {4 \        {8 O3 i, C0 k% V7 w- {& C. b. E
            cout<<d<<endl;7 z% o1 n3 F+ j- I7 N2 e
        }% N$ y4 \8 y$ \" r, d- F
        else/ v; N& O" h# P3 ~
        {1 P2 e9 f$ I& \1 ~2 R
            cout<<"ERROR"<<endl;
5 r9 k. U; O6 X        }
9 t; _, ]! q1 m  z( F" I    }8 i  f! h$ k* A/ `3 Y! o. ]
    return 0;
) c9 w" F+ ]- H  l9 H}
0 Q. X9 v) N; T& I/ R5 g5 b: e5 u2 p. ?1 Y4 a
: H3 _2 b) E6 Z! v1 b9 u
然后编译执行就可以了(*^_^*)5 t% ]( w3 Z$ X- ^; ?
其它:TC++上一定编译错误,不保证在VC6上也能通过编译
0 N6 @4 A% W8 N* o      建议使用VC7或VC更高版本,或者使用GNU C++编译

返回列表
【捌玖网络】已经运行: