返回列表 发帖

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

在9月8日那天我特意编写的,给大家分享的,( c; Q$ G2 |& N  F0 U/ Q$ g
一个很方便的函数模板,可以并且只可以计算含括号的四则表达式
. k( g1 L* a% F只有一个函数接口:int GetExpValue(_Tstream& istrin, _T& nReturn)+ j' n% i$ ^% j+ _0 q3 v+ ^' Q
参数解释:
+ \. k( Y* u7 V; qistrin: 一个输入流,可以是标准IO流,可以是文件流,也可以是串流6 K/ `1 }: \" q# W0 Q6 Q0 I
nReturn:用于接收计算结果的变量,计算所使用的类型由这个变量确定! D# k: p5 v5 V' P! e
返回值:
  v+ ^, |5 K% ^  G! \* N9 \返回非0表示计算成功,0表示计算失败有错误7 ~7 z, e% U2 T3 m/ i& v* g

! ^; u1 ^! y- ~3 }* A
  c3 i- e8 y  G8 ?& @  c
/ W2 r! h: R9 R7 j$ Q/ B程序代码:
" {& m! j- T0 I8 y% L. V' X& w, f3 `- m# M( S
namespace fy_Exp{* B4 S' ]5 O+ b
namespace {template <class _T>
- \$ A0 i- z/ xinline _T GetExpValue(_T t[], char& csym){
* I( L+ G6 z8 c1 s3 g5 m! p4 b' K; T    char c=csym; csym=0;8 T+ N( ?7 \6 R% x
    switch(c){3 Z* n: R* v9 B" A( Y/ h
    case '+':return t[0] += t[1];; _; b% f$ ^5 B- G
    case '-':return t[0] -= t[1];( y, W# Q. m2 K) r8 L
    case '*':return t[0] *= t[1];
2 v/ o; u/ [/ B  Q    default: return t[0] /= t[1];//case '/':
. t3 V9 F( t" s! E. F0 ]2 j8 L4 X  u    }, ^" C3 f0 h% A+ b6 K
}}
% Z: B' e  p8 H8 \template <class _T, class _Tstream>
3 }6 {: ~- @) a( ^4 w/* _Tstream: inputstream, _T: get return value0 H$ V# U; V% u
* Return nonzero if get value successfully */( P$ D, R  q& i  t
int GetExpValue(_Tstream& istrin, _T& nReturn){7 N1 E! f/ ~# o# b
    _T t[3] = {0}; //雨中飞燕之作
& z. Z9 h, P. K9 T! N/ g; {! q    char csym[3] = "++";
) P- \7 m* b  w: U6 i5 @    int nLevel = 1, nERR = 0;$ n1 C3 y6 I: X; T5 S% H+ B
    if(!(istrin>>t[1]))istrin.clear();
5 j5 D7 r! p* L- }    for(;;){
  y8 ?. E9 D8 P) @        if(istrin>>csym[2]){
, I0 }# R2 k0 C) Z/ @% ?. b; C            switch(csym[2]){# a5 A# ^% P; m
            case '(':
7 R# x$ s5 o8 [9 H6 r* M. e                if(!csym[1]){nLevel=0x100; nERR=1;}else0 l% V  k+ H* J  f
                if(!GetExpValue(istrin, t[2]))nLevel|=0x10;
- T5 M/ |& t  s  U. u& A. r! P7 t' ]                else{nLevel=0x100; nERR=1;}
& V( P) \9 g. L) W$ f8 x                break;8 Y4 b4 o- h3 E
            case ')':
. b1 S* s9 z$ y8 C' H0 @                {nLevel = 0x100;}break;
" y, f, H" X9 x0 M4 E" V            case '+':case '-':case '*':case '/':/ z3 `0 r! W4 T5 n# E' c
                {csym[nLevel++] = csym[2];}break;( s; E2 p2 s* C3 p* B$ _" j; ]
            case ' ':case '\r':case '\n':case '\t':continue;
% i  O: L" ]) B6 Q, D4 \9 N/ G            default:
+ f9 h7 n3 A4 d2 G! M- Z( s/ J  L                {nLevel=0x100; nERR=1;}+ S" U+ {! L. D
            }8 y$ A$ ~6 ^6 ^6 T5 d. R$ u# F3 U+ T
            if(nLevel==0x100)break;! W2 i# d8 M- j# C
            if(nLevel&0x10 || istrin>>t[2]){
1 z# ~+ ^) J. l                nLevel &= 0xF;
. t. Q6 U) Z8 f. d) z                if(nLevel==1){t[1]=t[2];csym[1]=0;continue;}
& m- u, M- R. m! l/ [- c  Z                if(csym[1]=='*'||csym[1]=='/'){
( z& t# _' c* I/ f: |                    GetExpValue(t+1, csym[1]);
+ B- X. w5 a% K5 v; V9 x# g                }
9 h, q0 y4 ?/ s7 [. K- E+ ^2 a& Y                else{5 e3 Z1 P$ A( d$ \2 a( j) B4 c
                    GetExpValue(t, csym[0]);
' T9 w: l1 L+ R                    t[1]=t[2];csym[0]=csym[1];csym[1]=0;& e, L0 g+ X+ v* s
                }" ?4 @9 H& q% g; p& [7 c2 k
                nLevel = 1;
8 A1 s4 A. e! c0 j" m. v            }$ b* ?5 ?) V2 C. r; L
            else istrin.clear();- `) r2 f5 v# I* n$ @% S
        }
* X) J5 ~: |. A0 s7 z        else{nERR = -1; break;}
9 J* v6 c% _; ]0 \/ Z* |    }
- h9 ?2 H- M; }, K    if(csym[1])t[2]=0,nReturn=GetExpValue(t+1, csym[1]);( G5 i+ P7 A0 Z; r8 v5 g) M/ E
    else nReturn=GetExpValue(t, csym[0]);' Z1 U; N: N, R8 z( j7 _) `( l' W
    return nERR==-1?1:0;7 G; m6 f5 T3 O9 e8 ~
}}
& g$ I5 Z$ M1 m/ `9 |, t1 q( x1 A9 q7 T/ Q( B9 k& K

# f& T# D0 O7 f0 X% ~; K% G! C+ ?- p
函数模板使用示例:- T; B& e3 m! @% K; p
在以上那段代码的后面加上以下代码:
  G1 j5 Z# H; b2 l5 ~5 f2 Z4 U3 F1 |9 o6 h" O
+ E0 V$ P3 U6 Q7 x# |( E" a

( j6 o5 i  o5 O9 H% G程序代码: * M0 E7 L% A& [' U

* F' v3 |$ q& x% p#include<strstream>! F& J) U5 F; O0 j, E: h9 v9 b" Y
#include<iostream>
' c# a, k% w' H3 x# k4 o#include<string>  o7 d; K( X2 y" k% J9 q8 N9 c0 ~
using namespace std;
3 Q* B, m; V% P9 f! K0 r+ k2 Lint main(void)& o! P3 n9 U3 D. y1 {$ d+ i% r
{
1 X2 b# H' Y! p+ `0 Q    string s1;' H  W4 [, g' T$ ?6 q9 D
    while(cin>>s1)9 ~& s2 n! I2 l3 @( i+ I0 k0 e
    {4 K. E8 W0 _8 [% o1 U* |
        istrstream isin(s1.data());8 P7 F; o: s# H. |. F6 W
        double d;
: K' J. Y2 w: |0 L$ |0 o; |        if(fy_Exp::GetExpValue(isin, d))+ y8 I! H# Y. d
        {2 c, U: B' d! _  A, x
            cout<<d<<endl;
* Y0 i/ N& T& z4 e. ]0 y. E        }0 H( u7 \* c4 W1 y* u$ ]
        else
) X/ ^6 S; r" W$ L        {
* w( P5 r" c5 z0 C4 B2 E: C            cout<<"ERROR"<<endl;
, e2 t, A- b8 d% d' S        }/ k) W' }* S5 N& g7 N
    }; N( K9 v2 u, }& ]. ^
    return 0;, E2 @8 }/ s0 n* t
}( k  q  G1 f' d; x

+ M- W' y4 o8 d4 t& i% m  U) s
& x+ h2 k; M/ y' [8 o: x然后编译执行就可以了(*^_^*)/ ]: t% W6 i8 v' H
其它:TC++上一定编译错误,不保证在VC6上也能通过编译
9 Z8 ~+ g' e- C2 O/ D; \      建议使用VC7或VC更高版本,或者使用GNU C++编译

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