返回列表 发帖

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

在9月8日那天我特意编写的,给大家分享的,7 n8 }$ m5 t+ S3 U) {6 L
一个很方便的函数模板,可以并且只可以计算含括号的四则表达式
4 [6 b* H; p$ w! O, w! W, Z  h2 K只有一个函数接口:int GetExpValue(_Tstream& istrin, _T& nReturn)7 c; m* Y% Z  l3 a4 H3 A
参数解释:/ |7 r6 G0 z( t6 n# J; b7 _
istrin: 一个输入流,可以是标准IO流,可以是文件流,也可以是串流
* N* [! q$ B  OnReturn:用于接收计算结果的变量,计算所使用的类型由这个变量确定' ?/ S9 V  |# ^4 ^7 j+ R$ x
返回值:
/ b8 g" @9 p  }$ q9 }: l3 Q& s% |返回非0表示计算成功,0表示计算失败有错误0 w  i6 N! C: O; i

8 y3 d* P- D: Q# G ; G! j8 b3 M5 E( a5 E
6 g) g5 T9 @* X- `
程序代码: / o2 [+ F7 c! r! {/ r0 V
) z9 P) u) i- t+ E& @
namespace fy_Exp{9 D2 w4 g, Z" R
namespace {template <class _T>
/ W* D$ G& J( W4 {inline _T GetExpValue(_T t[], char& csym){0 O3 _0 E/ i# c/ e
    char c=csym; csym=0;& A1 D2 m- c& a: s( p' t  ^& K0 f) |
    switch(c){
6 ~, S' S: [/ [! s, W, X    case '+':return t[0] += t[1];4 R# ]/ Q$ G* q- M, K6 I1 e
    case '-':return t[0] -= t[1];
3 K" M: L7 b) X+ W! E3 |    case '*':return t[0] *= t[1];
* P# T0 u3 d& Y) u, }' s+ ]) [    default: return t[0] /= t[1];//case '/':& Y5 L$ F: n& f
    }8 b" y! T, a& T+ \" Y* F
}}
  }& o, U* e8 z9 a; Utemplate <class _T, class _Tstream>
$ L; z, h  a( s$ Z- M  [/* _Tstream: inputstream, _T: get return value$ s' g; k. S# c9 N
* Return nonzero if get value successfully */6 T/ V0 T; n5 s! ^
int GetExpValue(_Tstream& istrin, _T& nReturn){4 s% b+ b$ p' W
    _T t[3] = {0}; //雨中飞燕之作9 D+ A: {! _" c6 P
    char csym[3] = "++";
7 @% ?  F1 h  K. F) ~* a    int nLevel = 1, nERR = 0;' e% O. ?) q2 H6 l4 }! ?  D
    if(!(istrin>>t[1]))istrin.clear();
+ [! h2 \4 g+ E, K& Z, V    for(;;){
% G6 v/ V' J! f! M        if(istrin>>csym[2]){9 L0 d9 l) w" W4 f$ F
            switch(csym[2]){
: V  n* \1 j9 X5 f% ^2 f$ \            case '(':: z4 g4 {% @0 \+ o4 V4 @- ^; C3 j
                if(!csym[1]){nLevel=0x100; nERR=1;}else5 A5 N: X% C4 j! p  @! I! Q
                if(!GetExpValue(istrin, t[2]))nLevel|=0x10;9 K( e$ x! K& Z- {6 t* B, ^( _: K! B
                else{nLevel=0x100; nERR=1;}
3 H3 w$ ~5 G* A" V6 h" E5 O$ E                break;$ X6 _  W  U& |8 `; m6 c
            case ')':2 C: }4 A3 r9 C. a+ \2 w3 y
                {nLevel = 0x100;}break;  H. M& u! N7 U- I+ d9 M  ~) L
            case '+':case '-':case '*':case '/':4 [8 E% i4 F' E' y& u- j
                {csym[nLevel++] = csym[2];}break;
; R; y* z9 G. e. S: K; {/ J* Z            case ' ':case '\r':case '\n':case '\t':continue;" K# P; r) R; r0 A# Z
            default:8 f. s' H$ y1 j' C0 W, U/ Z$ ~
                {nLevel=0x100; nERR=1;}
" U% R& S. R6 N6 R' g# E1 E  m            }
7 W) ^$ ]8 _+ s7 Y+ a            if(nLevel==0x100)break;
5 v6 i5 @5 H* I; h$ B            if(nLevel&0x10 || istrin>>t[2]){
! ~( F; a# }# g- |6 O                nLevel &= 0xF;$ e7 _3 @' X+ c0 X4 u' U
                if(nLevel==1){t[1]=t[2];csym[1]=0;continue;}3 S5 l) d% }' _5 J* C; q2 U/ x' q: `6 m
                if(csym[1]=='*'||csym[1]=='/'){! {% @$ m- N9 Z* g( i0 g$ a) O
                    GetExpValue(t+1, csym[1]);
; _" p5 [  T: O* H5 Z$ n# l3 x! N& P                }
: g- a" S" j& m; G' L                else{* }( D# D5 G9 R
                    GetExpValue(t, csym[0]);, X( G3 ?* Y0 S& e
                    t[1]=t[2];csym[0]=csym[1];csym[1]=0;+ T. W9 O' t# I' W- c1 H7 {, @
                }8 |9 s1 `4 I- C; Q4 u4 R
                nLevel = 1;
3 Z  H9 j6 u- M& F            }
/ e& n! T& L6 I& m7 D: s% a            else istrin.clear();/ F9 M2 {4 f2 |0 j; N/ i, H
        }
) `$ R+ `3 |: d8 }' e  N2 Q* h        else{nERR = -1; break;}
/ }7 d9 U" f# F6 b: ^' t    }* f0 X1 B1 X5 b& q4 n7 G2 }/ Z
    if(csym[1])t[2]=0,nReturn=GetExpValue(t+1, csym[1]);# U# O' W. D; m1 e, @$ w: k
    else nReturn=GetExpValue(t, csym[0]);
  f! ^" G$ W0 i0 I; o; N0 ~1 G    return nERR==-1?1:0;
8 n1 n& M, q2 p9 n- J8 E}}8 _# J) J0 _- I9 V- j: c
, y) D! O, Z% ~9 G9 ^

8 n- s* C! x5 v% u$ ?
! D4 ]& K4 K9 ^* R0 f函数模板使用示例:
. q2 l0 j9 m) W# [2 {7 s+ C4 b在以上那段代码的后面加上以下代码:
; @& M: D7 O  |( e" p3 W6 e3 ]; O! `" S" V; [! T

+ d/ o, a2 z1 O! Y' a; _2 j9 l) o9 C" ?4 A0 q# J) ]. x
程序代码: 3 ]8 Y5 X2 O  p, N+ c8 e9 u
) q. i$ j0 E/ N) D
#include<strstream>
7 y" H' C# \, M#include<iostream>2 I3 c' N' r- V: S
#include<string>$ i& u& I' d8 a+ S
using namespace std;# ?- n2 i+ S/ K3 B
int main(void)
$ {. }6 m; M. O9 C( B- S8 F{
' H1 \+ M: y0 j1 V  k    string s1;0 F& `% X+ o- D% g6 s# L2 j
    while(cin>>s1)
- E, R7 j3 v8 }. E1 z! V8 z: l    {
, g+ h! [; ~+ A) p9 h        istrstream isin(s1.data());
. k# X' _" d% g7 R/ i, p3 z        double d;
" w( j% M; ?4 b& D9 n  \7 H        if(fy_Exp::GetExpValue(isin, d))% D5 @# g: o0 `
        {% b6 m% ~; w+ w5 n- Z( p
            cout<<d<<endl;
  Q7 p" m* V& i        }
; C7 n  i, K, ]; M6 `6 v* y; E        else
" @9 }- |5 T& j7 X$ A        {$ b# ~# J: ?& F. l( F4 U6 w
            cout<<"ERROR"<<endl;) V$ [3 w; b3 p7 y- r
        }2 D" N& ?; e$ d+ b& |
    }7 ~1 o* S. r1 v4 E6 b
    return 0;0 Q3 C: W2 ?: _$ J8 K) `. N3 R
}
1 w* q& e& h* O
8 d7 x) u: x/ T. o. T- ^3 R( c$ ~
然后编译执行就可以了(*^_^*)! b' v/ p1 N& z
其它:TC++上一定编译错误,不保证在VC6上也能通过编译2 o$ k7 `2 L# C% r
      建议使用VC7或VC更高版本,或者使用GNU C++编译

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