返回列表 发帖

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

在9月8日那天我特意编写的,给大家分享的,
* j2 z8 B& I0 b) u! E% k% E4 H" r- ]一个很方便的函数模板,可以并且只可以计算含括号的四则表达式. s) S6 W6 M5 Y+ d
只有一个函数接口:int GetExpValue(_Tstream& istrin, _T& nReturn)
3 g% j9 O$ w; a/ W参数解释:6 @) r- o( H. L% d
istrin: 一个输入流,可以是标准IO流,可以是文件流,也可以是串流
9 g! n0 Q3 F9 E6 Q0 `4 I' EnReturn:用于接收计算结果的变量,计算所使用的类型由这个变量确定
& s% @1 A+ F+ P返回值:" V& S5 D& g5 u$ N
返回非0表示计算成功,0表示计算失败有错误
5 h( z, Z3 ^& H! P! T) _: p: S' o5 y7 |
) u0 L9 n% Y/ ~4 d: ?0 _( u
  y  Q0 s% v3 v4 z  X; r
程序代码:
, I; r: A4 i: E9 g& _" H" J* P0 n/ {7 r3 \! V) g! i! ~/ ~
namespace fy_Exp{
4 @: N* J8 ~' `( m# F0 C  lnamespace {template <class _T>
! k  a& n" A+ Minline _T GetExpValue(_T t[], char& csym){
1 v2 _/ D6 E8 M% ?$ W2 d    char c=csym; csym=0;( J4 m6 {) }3 O4 ?. @& c
    switch(c){1 N5 G5 M" e! H$ J# k1 p5 q6 q
    case '+':return t[0] += t[1];
9 h3 f0 k; U" F. ~( w    case '-':return t[0] -= t[1];
+ D. m* l( P% I/ `( S/ `" }7 ^2 {: x    case '*':return t[0] *= t[1];
3 j: n6 {, _: w1 G2 p% Z" l    default: return t[0] /= t[1];//case '/':6 \( f8 j& M2 k5 \* `  z
    }" D' d8 \3 e% M' f8 u
}}0 p' }, `' `  \; l  {
template <class _T, class _Tstream>
/ h) H3 m4 s7 f/* _Tstream: inputstream, _T: get return value5 F: e/ f+ k0 l7 O1 L4 R* }
* Return nonzero if get value successfully */
5 L4 x7 M9 q% O( C$ k* zint GetExpValue(_Tstream& istrin, _T& nReturn){
0 I7 `) K) L/ e; h" d    _T t[3] = {0}; //雨中飞燕之作) ?9 r7 g5 s* s+ ^: [
    char csym[3] = "++";
3 ?( }( F0 F3 ~- r6 s    int nLevel = 1, nERR = 0;
( V3 u" }  ~0 o6 w    if(!(istrin>>t[1]))istrin.clear();
6 X' M# x' y' H; M) U1 J    for(;;){& A( g7 M1 U7 j8 t
        if(istrin>>csym[2]){
, V$ Z9 d2 G, j! k9 @' L: i            switch(csym[2]){
! a- E% f% K' ~+ Y            case '(':
( f+ H7 H  Y- q                if(!csym[1]){nLevel=0x100; nERR=1;}else! q/ P) ]: h8 Q- J9 E
                if(!GetExpValue(istrin, t[2]))nLevel|=0x10;
. q( j9 M5 ?  J  @, ?( |                else{nLevel=0x100; nERR=1;}# j3 H2 r' z3 P9 C8 S2 T8 ~
                break;  S7 i2 m) a) c! Q, c5 R
            case ')':
$ z7 k7 B! w. w5 v9 c& @                {nLevel = 0x100;}break;
0 I3 [1 f3 o. t1 r/ m7 h* R            case '+':case '-':case '*':case '/':
' G! [3 s, A& ?- z                {csym[nLevel++] = csym[2];}break;
" e: C$ p8 U' \8 I/ P2 a1 e1 }# |            case ' ':case '\r':case '\n':case '\t':continue;
  }, f3 P* `- j4 O. `7 _$ ?            default:7 ?2 g4 d( P7 G" k
                {nLevel=0x100; nERR=1;}
, b6 H) w  }, s& u            }
- H5 U+ s* u6 S+ x  G; c) J& z            if(nLevel==0x100)break;: J$ i7 n% w" J- @/ F& y
            if(nLevel&0x10 || istrin>>t[2]){
0 t; T2 `$ F) T6 n+ T$ E( o                nLevel &= 0xF;% E9 z5 c* n% C7 Y
                if(nLevel==1){t[1]=t[2];csym[1]=0;continue;}* r% Z0 P' L7 j6 P
                if(csym[1]=='*'||csym[1]=='/'){7 T# F0 M; Q! {2 D  L$ A! @
                    GetExpValue(t+1, csym[1]);
: S% T0 H% \! E5 p  `$ f) m$ m4 u                }8 _6 B7 ?; J7 x: D; i- u
                else{3 E3 ^' R$ O+ i. U. C6 K
                    GetExpValue(t, csym[0]);
/ g+ [2 Q; d$ g+ C) {% |                    t[1]=t[2];csym[0]=csym[1];csym[1]=0;5 u' e; f; @0 ?$ S
                }6 q( |& X' T" ?  S
                nLevel = 1;/ R# o' P; T* K- s0 a9 d6 B
            }
; d. R9 y, A3 o/ j+ c' [* o5 K4 ]            else istrin.clear();. C1 w. Z2 Y5 x7 s  p
        }6 h7 Y* n, U  g; M- j
        else{nERR = -1; break;}
, z' U6 o7 b6 G    }
. ^* [: N% ]: e0 G    if(csym[1])t[2]=0,nReturn=GetExpValue(t+1, csym[1]);9 ]# L2 H1 l5 j* p/ p) W1 N
    else nReturn=GetExpValue(t, csym[0]);
# R+ T$ W* {* q7 b0 h  c6 k. Q    return nERR==-1?1:0;
) K- s, x+ x& Y9 n  B}}
7 _% }4 `$ s0 ^# u3 ]! E* l* ]+ i1 D$ z5 o
0 f4 R* u: w' C3 ?. D& R  M$ z

8 l, T& i, t7 ?" X7 _函数模板使用示例:1 p% }& v  A  }( H) s2 }
在以上那段代码的后面加上以下代码:
: x. S6 V! @5 L0 }
. _1 f  i. f5 u2 N3 U/ d3 K# q- n
9 ?% N- [( L; {6 m& f# R; g7 C: J7 j, b7 p
程序代码:
6 ^' Z: J! L+ r2 [0 a  C, Q* g% Z: ^7 _4 T" @/ l
#include<strstream>7 @8 M8 L9 d# F$ K
#include<iostream>2 x" [/ o. s! X- t2 D( ^
#include<string>
3 R7 {" U% i) Zusing namespace std;) ~8 V6 K" V/ x& d. e1 I; O
int main(void)# g, c( M( K. L2 f) ^. y
{
1 q' m/ `( A  a0 _3 Q% N    string s1;/ v2 d% {9 X& y9 A4 N9 K
    while(cin>>s1)* t% G3 a) N! `) d8 k$ j
    {3 b+ [( V+ p/ y
        istrstream isin(s1.data());
3 H/ w0 ?/ e- ~- C6 r" ]        double d;" V5 K* }' g) M+ x
        if(fy_Exp::GetExpValue(isin, d))7 J1 o7 b" ~) G, k6 m; I( T4 z
        {
/ H2 E/ H% k7 P0 N            cout<<d<<endl;* l2 x# Z3 K' E! h9 G( i$ v$ c* y
        }
1 H) ]) l; y3 Z/ x        else, ?3 u* Y" ]) Z
        {5 I6 o! G8 T6 j7 x- d' Y
            cout<<"ERROR"<<endl;9 x4 R# [+ [3 h; K
        }
9 X9 v- j8 C" R, }$ u3 n+ t1 q    }9 X7 Q% {4 w2 S* b* N4 f
    return 0;+ J- P  O% ~: K! ~
}
# Q- a: t: V1 d0 F0 V$ X. S
+ G* T7 l' t! U; l* ^8 q/ B5 k
: V7 }  a: ^4 Z1 D1 Q+ K" B# d然后编译执行就可以了(*^_^*)4 o0 z; i! V9 y5 M' [# [
其它:TC++上一定编译错误,不保证在VC6上也能通过编译
3 |7 I; G; \0 u( X3 i( o( |      建议使用VC7或VC更高版本,或者使用GNU C++编译

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