返回列表 发帖

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

在9月8日那天我特意编写的,给大家分享的,' a& c. p% I9 R+ l: |
一个很方便的函数模板,可以并且只可以计算含括号的四则表达式
" `5 N/ P1 F; c4 ^) v- R只有一个函数接口:int GetExpValue(_Tstream& istrin, _T& nReturn)% {6 u1 f4 B; l9 `$ z+ o* {1 o7 f
参数解释:
. G1 _+ F( p: }: K, B1 j7 n+ N1 ~, Fistrin: 一个输入流,可以是标准IO流,可以是文件流,也可以是串流; p) A% I3 ^0 s( h2 r5 ^
nReturn:用于接收计算结果的变量,计算所使用的类型由这个变量确定
" L; X. I0 d/ v( Z7 R返回值:
% ~3 u% E9 W2 }5 d) U# s返回非0表示计算成功,0表示计算失败有错误
0 B+ M9 y9 h2 y1 L- x# Y
( \+ M# j. I% n% X9 l1 z' w" s) N4 p
/ `) o: |; J5 w$ Y1 x! U
5 F) W5 t- n4 Q  h* X程序代码:
0 Q6 A* K7 R, ~( t$ A* T
* E1 R. @- ?9 k0 O& Anamespace fy_Exp{
  n- c, b' S+ j6 j" Nnamespace {template <class _T>
0 V' V$ d/ W3 o8 Z  q% sinline _T GetExpValue(_T t[], char& csym){
3 M' q6 ?8 |: n! u7 S; _    char c=csym; csym=0;
7 I2 c& a5 K! V0 Q    switch(c){
) p/ K# ?8 O, R% A1 H5 u    case '+':return t[0] += t[1];
7 j8 E" _, l: K7 m8 z5 X) N    case '-':return t[0] -= t[1];, F5 K! V' Z, h; D# s5 ~
    case '*':return t[0] *= t[1];% H3 S; H1 }5 Q$ X
    default: return t[0] /= t[1];//case '/':; V" t$ r+ M# g: S( L8 [1 n7 y! h
    }
6 ?# z# D4 b6 A1 T$ G; T! [}}
- I/ g! u, R8 y1 Btemplate <class _T, class _Tstream>
6 a) Q) I' @8 S. {+ W) C; C/ H/* _Tstream: inputstream, _T: get return value
, r8 X3 H5 s: v6 m' V, Y) o1 s* Return nonzero if get value successfully */
2 a5 G7 }* X$ l2 }7 I% t2 Hint GetExpValue(_Tstream& istrin, _T& nReturn){
$ \( Y* x3 |& U* V    _T t[3] = {0}; //雨中飞燕之作: D( I& o- y2 ^# I) _  T2 I7 _
    char csym[3] = "++";
8 Q/ c1 g) l* R' n" o$ M    int nLevel = 1, nERR = 0;1 f9 o! N% @! ]4 b, _1 ~* t# g
    if(!(istrin>>t[1]))istrin.clear();# G  c+ ^1 }7 C; ~' j$ p
    for(;;){8 u- [' C2 S4 y. H( h; q' L9 Z
        if(istrin>>csym[2]){
2 A' ~2 b$ r- F7 H, {$ X& v            switch(csym[2]){
0 T* W. y8 h+ y/ T* w9 z            case '(':- C4 k1 M# B! u# g  u/ x2 J2 v
                if(!csym[1]){nLevel=0x100; nERR=1;}else
, A& t/ b3 z8 y! c3 X+ l                if(!GetExpValue(istrin, t[2]))nLevel|=0x10;
' l3 b9 M9 o; |7 z7 Z( ^                else{nLevel=0x100; nERR=1;}/ f; ^: c8 A$ a1 _/ Z9 h( E7 |, H2 I
                break;+ s9 H6 ~5 ?0 {: J
            case ')':; R) M2 ?4 Q7 Z
                {nLevel = 0x100;}break;- l0 @, ^# H9 I# O3 \! S* k
            case '+':case '-':case '*':case '/':
  o! ?( r% N0 `( j6 q6 y% N                {csym[nLevel++] = csym[2];}break;! ?& d$ d) n: W; s; y
            case ' ':case '\r':case '\n':case '\t':continue;5 [; Y# r* }6 ?8 |7 G0 @4 {7 L
            default:
) d3 D( U5 a* b2 O- ~                {nLevel=0x100; nERR=1;}9 b3 l9 j$ S, z! d) c
            }
0 N) v; Z9 ^3 k6 Y4 d; Z: m            if(nLevel==0x100)break;; K% k) [" m, N* m! W
            if(nLevel&0x10 || istrin>>t[2]){: Y: t; ?5 P; }' i
                nLevel &= 0xF;7 s/ p) q) w: ^: |( o- N
                if(nLevel==1){t[1]=t[2];csym[1]=0;continue;}" H, ~' q; Q8 G/ s  l
                if(csym[1]=='*'||csym[1]=='/'){
" j) Q0 L) F# t% x9 Q; i5 v, u$ j                    GetExpValue(t+1, csym[1]);
; }9 f( q; k% _                }
0 y4 [- C4 F, `. r' f+ W                else{) u& D  e: u. k$ _3 V7 d
                    GetExpValue(t, csym[0]);
9 b/ h, T: {6 d) a2 w- j( b                    t[1]=t[2];csym[0]=csym[1];csym[1]=0;
7 F0 q! F  ^- W- A3 c7 y5 l1 m                }
% Q/ ~2 e( T8 U. c$ F$ e                nLevel = 1;; }3 C8 S* o9 x3 w$ w
            }
' r, w$ b( L: v( Y4 r7 P* b            else istrin.clear();
/ K  \9 ^# J& P; F        }- q9 C6 J$ q% O. w- C
        else{nERR = -1; break;}
! P" H" c: u" k8 ^    }! m- I1 y  m, ]
    if(csym[1])t[2]=0,nReturn=GetExpValue(t+1, csym[1]);
/ G# |3 ^0 f! y2 f- _8 G    else nReturn=GetExpValue(t, csym[0]);
( Y/ r) c9 G8 c' j0 Z5 N    return nERR==-1?1:0;5 Y: }5 a' _: p3 h3 b/ U2 y4 l7 w
}}
, W- ~3 j5 }7 q. X& E, }+ C2 K' h0 @+ z" Q

2 x2 U: K. h! u8 m1 ~% V  p/ L. n2 G: C' N1 `
函数模板使用示例:
! I' W* L" S; F( F8 Y( Y: b在以上那段代码的后面加上以下代码:( \: W( i$ A2 X5 Q

) [2 ~7 u) v7 _. R/ I0 p; j; L ' `/ X/ w7 M& E0 @3 A; L" F
* u0 J3 T2 ?! G" P
程序代码:
/ l3 I% g* W" ^  k/ X2 K% Y
7 _+ ~0 W* d- l6 E7 s  k% C  H( w#include<strstream>
, |- J8 n% Y) Z. R#include<iostream>+ `* f0 E( L. b/ V8 Z. f
#include<string>9 J$ M3 j7 N2 ~. J- y9 X6 }8 A1 O
using namespace std;* }& p  t( c  o4 w% q3 S2 ^5 @
int main(void)) y& u9 c- P7 O( V6 Y
{
7 U6 u6 {- x6 B* B: V% n2 v0 a    string s1;& w- S- t* L9 W6 j; H$ ^+ L
    while(cin>>s1)1 S' B/ F7 y  K& ~" `
    {
$ W8 y  B" ?7 G+ J5 @# G/ f        istrstream isin(s1.data());
! J1 N4 f8 [. a7 q9 N" }        double d;/ v/ O6 q8 K! u" Q. s% ^. A! @
        if(fy_Exp::GetExpValue(isin, d))
" S- V1 e7 I+ y6 |  S* r        {
+ o) ^) S! ?- Y) A            cout<<d<<endl;
) Z: s* U9 V8 L8 Y        }
* r. \+ S5 W: v* O5 K        else4 i. i7 }5 j4 |; U1 E% r& a
        {
/ p! [6 |2 M$ B5 q. [- G1 f+ X" M            cout<<"ERROR"<<endl;
& E/ k4 D3 x" X+ |5 W/ J        }
# E* x" ?9 z- {3 a3 o6 C4 U    }
. b/ D2 ^. M# `8 U5 V    return 0;/ Z' F8 Y$ H. U/ I0 z, f
}
  e: O0 k0 G7 E9 `
3 s: p: u  R$ w4 m+ p
* o4 W' N2 J+ Q9 }7 S+ j然后编译执行就可以了(*^_^*)
0 o+ H1 y7 }$ U* j3 R其它:TC++上一定编译错误,不保证在VC6上也能通过编译
1 G& B+ V6 I6 w* o8 B6 ]  m      建议使用VC7或VC更高版本,或者使用GNU C++编译

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