返回列表 发帖

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

在9月8日那天我特意编写的,给大家分享的,
) z+ U1 R2 V* s一个很方便的函数模板,可以并且只可以计算含括号的四则表达式
) @! i* d$ A. k( \2 Z只有一个函数接口:int GetExpValue(_Tstream& istrin, _T& nReturn)
/ L1 B2 l! @  U! l! g8 o参数解释:  \' B+ ]9 _2 i  u$ d
istrin: 一个输入流,可以是标准IO流,可以是文件流,也可以是串流& ^# `' x& n  q
nReturn:用于接收计算结果的变量,计算所使用的类型由这个变量确定! i) S% g% {6 }* M6 Y) @( w
返回值:2 S" T5 P7 w, O3 w& {2 n8 P( h
返回非0表示计算成功,0表示计算失败有错误6 w9 u' b; U0 |6 V' _
. }! }% A: F4 @! R

% g. P3 B8 H7 I: M. P; O, s1 V% A# x7 O2 M. g
程序代码:
" u% F' W& I' G7 h- D  Q4 e: M  @+ T1 d8 Q. A
namespace fy_Exp{8 x( H8 c/ z. K* t- `- y
namespace {template <class _T>% `3 J0 V$ |9 A7 a  p* E
inline _T GetExpValue(_T t[], char& csym){
, Y) X+ w" f. w! d    char c=csym; csym=0;4 N) k/ w8 @2 L) n
    switch(c){
3 c8 ?6 V6 ]9 ^; m8 U  R    case '+':return t[0] += t[1];
, S" r. j0 z0 Z  h) a# ~    case '-':return t[0] -= t[1];3 L, M3 r5 V$ P+ `
    case '*':return t[0] *= t[1];
- g6 J, ~6 l- A    default: return t[0] /= t[1];//case '/':
9 R. j5 o5 v  {/ Q9 S6 _* }- J- ?* K, i    }( Z- i. j. ], q8 e
}}0 k4 }$ z) U- {& e
template <class _T, class _Tstream>
7 i' m& L* h, G4 m/* _Tstream: inputstream, _T: get return value
4 \/ y- q2 G& ^' L* Return nonzero if get value successfully */; w& x2 r" a1 {* `+ {6 t! J
int GetExpValue(_Tstream& istrin, _T& nReturn){
( n. v. T/ ]& A5 x& W    _T t[3] = {0}; //雨中飞燕之作% m5 X' ~# P  G; z/ R
    char csym[3] = "++";
& e1 C- j3 ]4 |$ O8 r1 ^% l    int nLevel = 1, nERR = 0;8 _* V; g" z$ u9 w4 Z
    if(!(istrin>>t[1]))istrin.clear();2 A1 ^' R3 d' E3 Z$ \
    for(;;){
/ D  e# S/ O7 b$ T1 H+ E/ Q        if(istrin>>csym[2]){
4 F9 |, ~$ J$ Z5 o6 @6 `            switch(csym[2]){4 @$ l( h- i( a; O: b( B
            case '(':9 g, |, A" |2 a' p; k' t# z0 d% K
                if(!csym[1]){nLevel=0x100; nERR=1;}else( a$ R% R: O' f# `5 a, h0 R
                if(!GetExpValue(istrin, t[2]))nLevel|=0x10;
$ b  Z# m* Y0 k                else{nLevel=0x100; nERR=1;}7 D2 S1 W) L9 m6 ?2 ]. u" ?
                break;* K6 w- ?/ K7 |
            case ')':
8 X( a" z% u, {  [* B$ Q! @                {nLevel = 0x100;}break;7 _1 t$ ]! |8 Q9 J3 f; d$ r7 \
            case '+':case '-':case '*':case '/':/ Q. ]6 Z" u5 j
                {csym[nLevel++] = csym[2];}break;
6 c# y7 Z- ^# C7 z- y( F            case ' ':case '\r':case '\n':case '\t':continue;# R' P) O  |' O/ J8 @+ W
            default:# v' y, Q6 T, l) C$ e; Z
                {nLevel=0x100; nERR=1;}& r/ t# V0 |5 C+ o- @, y
            }/ x: A; T; n$ D# f5 ~8 k1 {" l
            if(nLevel==0x100)break;
' T! `$ w- Y' a5 X1 A- r) g            if(nLevel&0x10 || istrin>>t[2]){
  l1 E/ \. a( P  n3 U                nLevel &= 0xF;* n9 c& ~& Z( c/ D
                if(nLevel==1){t[1]=t[2];csym[1]=0;continue;}% s/ C' U5 g6 M7 U/ J
                if(csym[1]=='*'||csym[1]=='/'){4 y: u. f, a" Y7 M# |
                    GetExpValue(t+1, csym[1]);
" V0 w# l  n5 n  m                }
1 ]9 U; ]7 s$ N: A- y/ ~' j                else{
7 L! G- U7 s' j( Z8 Q3 X                    GetExpValue(t, csym[0]);
( B0 p+ h# o$ r0 X( B" b2 a* C                    t[1]=t[2];csym[0]=csym[1];csym[1]=0;
3 d. H0 r  L- B4 M                }
2 U6 J- k: y7 g/ ^8 R. x                nLevel = 1;. s( V' d! ]4 K$ x; Z
            }1 }: C- E+ x+ H5 d: `% O
            else istrin.clear();( Z( W8 q# k- {- {
        }
! D+ B: e4 l- y; O* ]        else{nERR = -1; break;}
( P! I3 B" a! x    }
2 [" W# N9 C# U9 M6 J3 F- |    if(csym[1])t[2]=0,nReturn=GetExpValue(t+1, csym[1]);
+ P& u( x2 s; x% @    else nReturn=GetExpValue(t, csym[0]);$ j9 a' a$ @9 N2 o
    return nERR==-1?1:0;
& [; P) T4 e/ U4 ]1 K}}7 R4 G% X, z' S
% n1 f' @% `3 ?, ^3 K+ K) T
5 ]1 |: H% d6 `( q6 A
9 N9 T) }3 `, b% k! y
函数模板使用示例:
$ Q$ R* u5 A7 s$ k6 h在以上那段代码的后面加上以下代码:" H. u! ^8 P+ d' d9 J$ Q
- T" g2 k: W" }8 h/ q
" s% Q6 O) C# n) L; t) Z& m$ y

1 ~3 [, u. m8 E; l7 A程序代码: 2 Z% b! h- }+ B, C* D* S

! d# n8 ?4 M  v5 K; E: q& R#include<strstream>  i3 e2 {; i" ?# `6 r
#include<iostream>% {" J" F7 o! Z9 ^) b( a' F4 l/ O
#include<string>
* R. V8 m4 C6 {( Y0 |, R2 c4 Yusing namespace std;
, Z) f- z/ P4 M) p% `int main(void)+ m6 \. X( V1 Y5 O& Q1 y
{
' o# f) u# p& ^! y& q0 Q/ V+ h    string s1;; g  @5 y( d6 r3 O' `+ y; w/ l* R
    while(cin>>s1)
$ ]8 o$ P9 C# F* o1 `    {
. z; ?" A8 a3 z+ j( j        istrstream isin(s1.data());
8 ~$ d+ t. `  G$ @! g        double d;
; G) v) x7 A" R* B4 ]( r2 s        if(fy_Exp::GetExpValue(isin, d)); B: F. B. O' N
        {
, D4 D: C9 z, E0 }$ }) y            cout<<d<<endl;$ T. X: q2 J1 e5 F6 v* L# U3 L3 E
        }
% |5 _1 A6 j: N$ {) d        else9 M' s1 [) y. Z: l
        {% w0 B1 t- Q: z( g( i  v
            cout<<"ERROR"<<endl;
# `  x, a  I5 h8 p/ Y) Y1 m- w        }
; S, \% Q0 S6 E4 f    }
" I1 O; t: M+ p8 n( i    return 0;2 S  I1 R: K9 K" P& z$ o
}! S& n6 Q  w2 N5 \

7 I  Q% E) u& Y$ b9 {8 w" e3 [! n/ [" [
然后编译执行就可以了(*^_^*), u& @. `$ Y6 L& v
其它:TC++上一定编译错误,不保证在VC6上也能通过编译0 {7 i! V0 m/ K! N  t. y
      建议使用VC7或VC更高版本,或者使用GNU C++编译

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