捌玖网络工作室's Archiver

zw2004 发表于 2008-1-21 20:17

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

在9月8日那天我特意编写的,给大家分享的,["j!E9\#}7W
一个很方便的函数模板,可以并且只可以计算含括号的四则表达式0`_-y'E"}c!d [:pk}
只有一个函数接口:int GetExpValue(_Tstream& istrin, _T& nReturn)Ck6V\/G)X
参数解释:eR dD/b3{'D5C
istrin: 一个输入流,可以是标准IO流,可以是文件流,也可以是串流
wK)\3])n ~ nReturn:用于接收计算结果的变量,计算所使用的类型由这个变量确定L5t0qF-p
返回值:0]'w)V0JIQ+O
返回非0表示计算成功,0表示计算失败有错误p;h%X I9B
,uYb8q$g!K&j,r0Y
B#~b,x7s$Y
/~8`2C7Y"} xAx
程序代码:
4?W,[/x#T
oS!g E+Ok U3} namespace fy_Exp{Ttt!A/Xr
namespace {template <class _T>
5?2[b|:O4m{ inline _T GetExpValue(_T t[], char& csym){&HM1c&U[6JDB
    char c=csym; csym=0;!KZ.~X&~/bao
    switch(c){
at%Cad     case '+':return t[0] += t[1]; g oQ l"CK"fQ
    case '-':return t[0] -= t[1];
J#C"fEu4nx_     case '*':return t[0] *= t[1];3fw3X^I1?(}u
    default: return t[0] /= t[1];//case '/':d.z)|7gvL$of
    }
KO.v7L-[;bCR }}
5{&s WS*KGt)? template <class _T, class _Tstream>
a4L4x)z@hiPd*n /* _Tstream: inputstream, _T: get return value
GX1}1k\|'v2[ B * Return nonzero if get value successfully */
@_v;z!K int GetExpValue(_Tstream& istrin, _T& nReturn){PDWN8a&F}
    _T t[3] = {0}; //雨中飞燕之作 gf)L;Of%{
    char csym[3] = "++";A)O |&Xo:S@F;G
    int nLevel = 1, nERR = 0;
lg?&MX)b3C L     if(!(istrin>>t[1]))istrin.clear();*M9kiH }j9D f%yA l
    for(;;){
I$b"ci/I3`1h b"c4q         if(istrin>>csym[2]){
8^?{ bH ^-i'S8_ }             switch(csym[2]){#[ ~A0I!i?!CdWhQ
            case '(': O$l d7H-q
                if(!csym[1]){nLevel=0x100; nERR=1;}else
[} }g!]jC)G                 if(!GetExpValue(istrin, t[2]))nLevel|=0x10;
&[ ~+s:Bb2F p5A                 else{nLevel=0x100; nERR=1;}
mcC7wt+Y/h6Xy                 break;
D(Mp\e'J/s             case ')':)c,i5IH;^
                {nLevel = 0x100;}break;
;M Csfo9yc$a             case '+':case '-':case '*':case '/':{1Wyo9s5~ }~c
                {csym[nLevel++] = csym[2];}break;
pcg)P^             case ' ':case '\r':case '\n':case '\t':continue; E3V,bC"jpPH
            default:
F` M%m7} PU:\~                 {nLevel=0x100; nERR=1;}
W@,D8t7ay#TG             }
fTX'`x9y0|             if(nLevel==0x100)break;'b0w a8z`
            if(nLevel&0x10 || istrin>>t[2]){
-ET&WXI                 nLevel &= 0xF;
x/Z$jY-q!Y8O                 if(nLevel==1){t[1]=t[2];csym[1]=0;continue;}
/Ii-PK/N9l/wF/m                 if(csym[1]=='*'||csym[1]=='/'){xv l6Z*P'BI
                    GetExpValue(t+1, csym[1]);4@{p2R.b0th
                }&a.}c:d\,H#x/mu
                else{7Pgt9H#k7wT$g,h
                    GetExpValue(t, csym[0]);
/e6x? l%Y6K                     t[1]=t[2];csym[0]=csym[1];csym[1]=0;@(m2pe/|^@#i vXd
                }DS"M ] x+R6|'k#B4n
                nLevel = 1;
-bWV3g.o             }${'L;N fJHs?5e
            else istrin.clear();
0Y3P2J%X2{p$P*f"m         }S[v\9FR-A7s$Sr
        else{nERR = -1; break;}
za,~dC@:b     }
v ^&oq5C|'Mo     if(csym[1])t[2]=0,nReturn=GetExpValue(t+1, csym[1]); I q7n s~TS
    else nReturn=GetExpValue(t, csym[0]);
8UxE3i2SNi5k'W     return nERR==-1?1:0;
+U t xW;N g"g{0Sl;M }}0fz-` |/[Jt
ACv6O vrI

`E4kT)N ~r M
zn7F HP 函数模板使用示例:_y+NM mKK-cL9K
在以上那段代码的后面加上以下代码:%L r+{*?ek&u
5u7loP(xx!VZx4h
i&@6Fx xf!gA

FXd3`Z/V_ 程序代码:
4|+^-W5_!|z q s:q+~6F(gZv#aLb
#include<strstream>2Jf7rxE @@3z/C
#include<iostream>
)O%QS:cw [-QIr #include<string>%}JED`X-Fh
using namespace std;
!p&qE y_U/J int main(void)8F3v en ySrI/ee
{
$m6@7e0nV2P     string s1;*Vx$PSdm
    while(cin>>s1)
9Uk@;{?3k|G)g     {:{oU7KCe5i
        istrstream isin(s1.data());JNZ(OAQ5I
        double d;&c2h&hax4O;L
        if(fy_Exp::GetExpValue(isin, d))
&n0_ h7rg(nZh         { E0a!w zyS
            cout<<d<<endl;
,Th/hwP.xHiYX         }
7n$[1V&| C'Og         else
[ w(N-}eT8~qzfU-Q         {.ZPPo ZG!rq Q
            cout<<"ERROR"<<endl;
%` Q W#a5k         }
.n c.J2h6zh*b     }sDr4VI/zDM
    return 0;L`n(~c
}*N&eM$sP@
,l^ VeRR?JV

R:N~,b3R1vvH 然后编译执行就可以了(*^_^*) rn;h&Q g lxpd
其它:TC++上一定编译错误,不保证在VC6上也能通过编译
7vg6T%K+u_I5v       建议使用VC7或VC更高版本,或者使用GNU C++编译

页: [1]
【捌玖网络】已经运行:


Powered by Discuz! Archiver 7.2  © 2001-2009 Comsenz Inc.