返回列表 发帖

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

在9月8日那天我特意编写的,给大家分享的,& p+ J1 m* D& o
一个很方便的函数模板,可以并且只可以计算含括号的四则表达式) P, T5 b  Q$ S
只有一个函数接口:int GetExpValue(_Tstream& istrin, _T& nReturn)5 H" S- X: D: g8 C# B
参数解释:
6 V% W, x- _& i, [& {+ d; Cistrin: 一个输入流,可以是标准IO流,可以是文件流,也可以是串流% x4 l# ?) t. h' K1 G
nReturn:用于接收计算结果的变量,计算所使用的类型由这个变量确定
7 Z' e( o- B5 t" o; E+ ^返回值:* s/ H6 N! I2 l+ C! n
返回非0表示计算成功,0表示计算失败有错误
9 o/ d; u  ?) i* F
& d, w0 K! k1 J( W7 C8 ?. D ( k- ]% U1 H# J$ K$ ?6 ?

4 |: z# D, ^3 F, }3 v) o/ G6 C- c程序代码: ( W5 X+ x* z5 G' ^! g* y/ o& ^
( Z. @* O! o& y/ Q
namespace fy_Exp{" S, U  N/ G' @0 |
namespace {template <class _T>; ?  _  U4 P8 R) F( x  R4 Y
inline _T GetExpValue(_T t[], char& csym){6 D/ ~$ W4 N. [+ C0 X  h1 e
    char c=csym; csym=0;2 g7 d' V) ?4 X
    switch(c){* x- K$ o: i+ x+ I
    case '+':return t[0] += t[1];
0 b  H: t, e/ G    case '-':return t[0] -= t[1];
8 j5 {* t/ E+ y# M1 g    case '*':return t[0] *= t[1];' y5 ?) h! f$ ^$ e* F
    default: return t[0] /= t[1];//case '/':7 \# r0 h! x% ~
    }
/ n/ _- W! o- y0 q& ^; @( \}}
+ D& R' {1 t# b  W! L' n; ~template <class _T, class _Tstream>/ C) W4 y) G4 }  ^) t# ?
/* _Tstream: inputstream, _T: get return value
  r) [4 g# c- F! Z0 A" _' S- m8 s! D* Return nonzero if get value successfully */
, e3 G& J# N, X' ?- u- [7 jint GetExpValue(_Tstream& istrin, _T& nReturn){
, O; `0 ~( Q3 P$ C( Y    _T t[3] = {0}; //雨中飞燕之作1 x+ r! j6 E8 s$ @( t; u! }, N
    char csym[3] = "++";
, v7 C' i4 R) r# w- l$ _    int nLevel = 1, nERR = 0;& H3 j- l' p1 s' p% o- X6 n
    if(!(istrin>>t[1]))istrin.clear();' n- d( p/ b" N
    for(;;){6 ^: @' ~+ O6 t' ?3 N5 H' B
        if(istrin>>csym[2]){6 a' h3 y' S4 k
            switch(csym[2]){7 b% `4 I+ }7 X" h  E* h- E- r
            case '(':
! ]; e+ [0 T* x/ {$ O5 y2 S7 r                if(!csym[1]){nLevel=0x100; nERR=1;}else8 ^- L+ S3 I3 F  M* T7 K+ C
                if(!GetExpValue(istrin, t[2]))nLevel|=0x10;" l& M2 y3 |& j# v* M, h
                else{nLevel=0x100; nERR=1;}
4 C+ ^9 @; Y5 k* [2 k5 g1 Z! I                break;
. l* R. }+ V6 U4 T; y* Z" }            case ')':
" h" `  N& C% J8 R                {nLevel = 0x100;}break;$ U+ G2 n, C8 x3 p
            case '+':case '-':case '*':case '/':3 L0 i/ f( M. Q' t
                {csym[nLevel++] = csym[2];}break;( N- Y8 t0 G1 V# ]# p- [
            case ' ':case '\r':case '\n':case '\t':continue;9 L; W, w1 l* F( ^6 y
            default:
5 J) p" ?# a8 `, Y" l9 E                {nLevel=0x100; nERR=1;}, x: [8 N; p* Z/ ?/ N
            }5 V' s& _8 ~) K  r6 H0 t5 R
            if(nLevel==0x100)break;; h2 y9 m7 P# E, R* v  v# q5 c
            if(nLevel&0x10 || istrin>>t[2]){
  Z$ |0 {, I! t/ d                nLevel &= 0xF;
! V' @3 D: k: Z( F4 U% ~                if(nLevel==1){t[1]=t[2];csym[1]=0;continue;}; o( G5 w6 r8 L5 A; }* l1 P3 K6 f
                if(csym[1]=='*'||csym[1]=='/'){
$ }% r- d2 H* G' F9 W- U                    GetExpValue(t+1, csym[1]);. D2 b$ t4 F& q. h* e4 j& N
                }
" H2 k' C; S( ?- K2 `                else{0 V7 v4 F6 h  g5 r4 S9 Q
                    GetExpValue(t, csym[0]);0 l* t9 B! X# O1 [9 W
                    t[1]=t[2];csym[0]=csym[1];csym[1]=0;
6 |0 ~; x: P; _: W8 F: E% i3 M                }; F/ w$ w3 [6 }- [) W- J& A
                nLevel = 1;  ?8 x4 p$ L# F3 v1 ]1 e2 h1 V6 \# j
            }' j7 W1 ?# V  _; [# Z
            else istrin.clear();7 V. r/ F& l8 ~! r) d% _' X! v0 S
        }2 U' i4 e. n/ @# c+ h
        else{nERR = -1; break;}& K/ P6 R5 \& Z$ Y4 P
    }
- j8 ~9 B+ j* g1 g% B5 D    if(csym[1])t[2]=0,nReturn=GetExpValue(t+1, csym[1]);
/ }, m% i" a" }) o5 B% ?0 S5 W    else nReturn=GetExpValue(t, csym[0]);
" J; D6 O+ A' K* A( z5 W0 f    return nERR==-1?1:0;% F) v- T7 V6 T( Q
}}
5 d$ U8 ]' p+ p& O: V- k5 O8 L$ T& ?
* [6 j/ e, h* |8 T: s# A3 W" Q9 Q4 ~

9 q& O% C5 X- y* O6 }* J  W( s% M函数模板使用示例:) A" F9 ]" T4 {; w4 d
在以上那段代码的后面加上以下代码:
0 J/ J7 a% Y  G9 a: l" H1 [8 E9 T3 j
% b+ ^+ J1 e5 v3 C: I2 F7 a4 s* l

* z3 ?% c8 a" a% ^; h; e# e程序代码: ) k; Q5 g" S3 u! H

3 e7 _5 y$ \' f#include<strstream>  u! Q% |1 U# D6 g0 A
#include<iostream>
/ k, x1 X+ i+ |. [& ~  \6 M* L#include<string>& b7 F7 ~2 |4 E$ w* c
using namespace std;+ _# Y* F$ Y( d7 y
int main(void)
- X6 D2 ]/ V; M" X7 T4 u; w{
5 y) v, v6 F/ N    string s1;4 S0 U9 J% u, j) o6 y" j. z* z% U
    while(cin>>s1)! w4 S1 p2 e- T, D' [, h
    {4 R$ |% w, `; `, i) |& q) w
        istrstream isin(s1.data());* B- V( z  b) D& p6 q( b- i  x) T
        double d;- X: N6 a) ^8 y) |# d
        if(fy_Exp::GetExpValue(isin, d))
' t8 p/ j1 p$ H        {7 }( c+ S+ m/ [9 d
            cout<<d<<endl;2 i# ?0 x& ]% T/ y6 P1 K" r1 c
        }1 ~# a0 J6 ?4 k$ d$ D. @* P" c
        else: Y, z% G1 W8 h% Z$ |/ f
        {1 `$ ?8 J2 G/ `3 [4 O8 x
            cout<<"ERROR"<<endl;# T2 ?# r* g2 j9 Y
        }
; Z6 \% q$ o& ], ~0 {5 U* Q1 g    }
" P1 }4 z4 [$ `5 o    return 0;! `4 O& |  o0 Q9 j* O
}
& [" q2 k9 n+ T$ [  v9 r5 z5 K0 R' q! U: y

( \; Y8 X8 z. P( m% a8 i7 [然后编译执行就可以了(*^_^*)
! O: c: N; h* L其它:TC++上一定编译错误,不保证在VC6上也能通过编译. a. U- Y  B8 G+ E
      建议使用VC7或VC更高版本,或者使用GNU C++编译

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