获得本站免费赞助空间请点这里
返回列表 发帖

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

在9月8日那天我特意编写的,给大家分享的,0 Z2 C/ q2 f3 \. T
一个很方便的函数模板,可以并且只可以计算含括号的四则表达式% m3 f; @2 p# k) u, p4 s1 g: m& j
只有一个函数接口:int GetExpValue(_Tstream& istrin, _T& nReturn). z1 F2 I, Y3 ?! I5 H' v
参数解释:
' G8 a6 e2 B6 p0 g( I/ J; o, iistrin: 一个输入流,可以是标准IO流,可以是文件流,也可以是串流
- G: W9 J, y2 Z* G! w! D3 |nReturn:用于接收计算结果的变量,计算所使用的类型由这个变量确定5 I$ A/ y# j$ ~" p
返回值:
8 N0 O, h# x) [' X; c" H返回非0表示计算成功,0表示计算失败有错误% Q7 T7 k' o- B- W+ c

# `1 q) c: s9 C: \% o   Y5 K% u7 G$ e* H7 @

$ G/ \( y& Q" r2 I" F程序代码:
2 `) H. @! t! j- C4 H3 N
9 `9 a. s, ]2 y5 A4 {3 v5 Knamespace fy_Exp{
$ G+ d, G/ c/ U% i, ^7 B2 ?7 nnamespace {template <class _T>; z4 r7 g+ z) i
inline _T GetExpValue(_T t[], char& csym){* R5 m3 ?1 v. B  B7 M; F2 T+ x
    char c=csym; csym=0;0 t( C8 o' d" _5 @9 x7 Z# {9 ?& Z0 Q
    switch(c){
3 ^- |  K# J# T% q$ L' B    case '+':return t[0] += t[1];
1 Q  {0 P1 C9 d9 i    case '-':return t[0] -= t[1];! d7 W. _% \# k) N
    case '*':return t[0] *= t[1];3 _. `# ?- T3 T2 i7 V: e# ?) q+ u
    default: return t[0] /= t[1];//case '/':
1 f9 g& Y, h7 ?9 Z* U    }
$ P, q/ @' B+ h0 _& b; v}}
( C8 k5 h) k. g0 d4 y$ mtemplate <class _T, class _Tstream>
# _/ i! ?! [% |/* _Tstream: inputstream, _T: get return value7 `: P" k' q/ X
* Return nonzero if get value successfully */
5 J! O7 L5 P% \int GetExpValue(_Tstream& istrin, _T& nReturn){
6 {7 j7 ^% n6 Q6 S    _T t[3] = {0}; //雨中飞燕之作9 j( v: ^: a' J
    char csym[3] = "++";  e: k1 k( i9 I* @
    int nLevel = 1, nERR = 0;3 V/ j+ n# }5 a
    if(!(istrin>>t[1]))istrin.clear();$ M; W( r5 m' T5 B3 _+ b" h
    for(;;){( X* c" Y: g1 R% c
        if(istrin>>csym[2]){
$ \7 R: x* w- O3 M$ e            switch(csym[2]){  Y0 Z! k  ]2 t; D7 q# `
            case '(':. Q8 z0 k! c* A; ?; i" ^
                if(!csym[1]){nLevel=0x100; nERR=1;}else
4 j$ a, Y9 M* H4 O3 \, X7 l                if(!GetExpValue(istrin, t[2]))nLevel|=0x10;
1 k$ ]1 q2 W6 G( h9 O; U% P                else{nLevel=0x100; nERR=1;}
" g2 K+ _+ n1 w# N                break;5 b" L( M$ [$ t) |5 h9 X
            case ')':
4 |) \8 a9 r" n- R) h1 i1 s                {nLevel = 0x100;}break;
& q$ g8 ^3 W! V' ]+ I: [' Y            case '+':case '-':case '*':case '/':0 c5 @' n  }7 U1 m0 U' A3 x" ?
                {csym[nLevel++] = csym[2];}break;6 S; O2 f% ^/ L0 T8 A4 q! U
            case ' ':case '\r':case '\n':case '\t':continue;5 v# C9 }4 V$ ~/ n, m
            default:! \+ p. ]4 x& h% ?# Z/ S9 N
                {nLevel=0x100; nERR=1;}5 M' w0 W7 n8 Z) G) p3 l
            }, O4 z' i* l, q. |3 z
            if(nLevel==0x100)break;9 A) \1 ~% [& o% H) l3 |* A
            if(nLevel&0x10 || istrin>>t[2]){% o9 R2 X& J9 G* Z/ n& ?! ^% h
                nLevel &= 0xF;: f% u- `" l# Q: L0 t2 ^& C* V
                if(nLevel==1){t[1]=t[2];csym[1]=0;continue;}
7 F6 V& I/ X4 o5 `                if(csym[1]=='*'||csym[1]=='/'){
, L- `& q6 n3 Q- S                    GetExpValue(t+1, csym[1]);
8 K2 [6 R) H4 M+ T$ n9 Q                }* X3 P- Q" a, r! w" R/ u
                else{* Q: x5 \/ u  Z% I/ {9 f8 Y
                    GetExpValue(t, csym[0]);
5 B5 J2 ?! o! G- y                    t[1]=t[2];csym[0]=csym[1];csym[1]=0;" S3 r8 w7 F. G& i3 C8 o+ ~# a
                }
6 O7 s% @  Y* B" `3 w3 S) {                nLevel = 1;
7 y+ q; F7 I4 Y% i            }
7 g% S3 F  T& D; e            else istrin.clear();, J2 o7 S) `  M5 ]
        }% x6 O9 o2 @. B3 u8 }$ S+ R. ^
        else{nERR = -1; break;}
) T! N8 ?! J  G$ C1 A: a    }
% g; f* i2 A: K$ k1 W: V, Y5 s) ?    if(csym[1])t[2]=0,nReturn=GetExpValue(t+1, csym[1]);* \! F2 {/ y' n9 K$ Y: d
    else nReturn=GetExpValue(t, csym[0]);  O# B# n. F! h/ c
    return nERR==-1?1:0;
! F) ~1 x8 r5 i3 }% {& v}}
% G+ _! w; ~" s) z, p2 F1 n
( V' G( d/ z& W0 t- p. V# i& E
' r: d6 |  _: F
. l6 p6 l9 V/ ^3 n8 `/ Y( E函数模板使用示例:
5 U& d. @0 H* S5 a在以上那段代码的后面加上以下代码:0 N+ c1 j( ~2 m) C
8 d3 D+ O& |2 q/ q2 b2 l( |
- i% l1 H' w7 [. M( N
& A4 {% \" d$ x
程序代码: 1 e$ E2 {0 X4 W. f' e- v5 D
, o$ W+ {4 H/ f0 `
#include<strstream>, c+ ~' `4 s! M
#include<iostream>
2 \) |6 k1 {* O/ m( z7 e#include<string>$ ^$ J% K: ]5 ^3 i) ~3 q7 `
using namespace std;8 W! K* o. _6 B
int main(void)
  I2 f2 f. J7 R7 [" ?4 {4 [2 S{" J0 E- q' D" Y$ s3 G! ^3 [6 P
    string s1;
. \( e( U1 n: `! _, v0 ~* V/ h    while(cin>>s1): u0 V# J3 v9 @# S
    {
, K# m6 ~, Y- E5 m/ z        istrstream isin(s1.data());
* ]. X2 S! ^/ \/ ?  x, _+ Q0 [        double d;( V; S# K7 D, F2 e7 w6 e( U
        if(fy_Exp::GetExpValue(isin, d))( P" N, b, r: l, O0 a
        {+ q: k9 l& ?" b* P
            cout<<d<<endl;
& [3 r# R4 Q$ h! Y        }
* S# ]2 D# n5 |$ M9 a5 y        else
  a. r5 ]' [% w4 j4 K- o        {
& S, z) i6 e  ^( `            cout<<"ERROR"<<endl;
; G2 g0 Y3 w, k( m* n0 A' X        }/ D' q! \* G8 |
    }% Q, \1 J: G/ Y, [: D9 [8 c7 h. J, V
    return 0;3 ?9 t5 D' T+ u+ Q. H! n
}
' O' x7 K  @% b
7 u) c9 a, C! X8 x  N8 o, A  x/ N  Y" c! f! |% t) Y9 H4 h
然后编译执行就可以了(*^_^*)
/ Y9 n9 q* [4 H) \- b' D1 }' H% H其它:TC++上一定编译错误,不保证在VC6上也能通过编译" o$ R- i6 U/ O! b$ e9 Y, f9 b. m
      建议使用VC7或VC更高版本,或者使用GNU C++编译

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