Bjarne Stroustrup 《C++程序设计原理与实践》
文法:
std_lib_facilities.h
1 #include <iostream>
2 #include <string>
3 #include <vector>
4 #include <algorithm>
5 #include <cmath>
6 #include <stdio.h>//C语言的标准I/O库
7 using namespace std;
8
9 double primary();
10 double term();
11 double expression();
12
13 //内联函数,防止在看到输出之前窗口关闭
14 //这是Windows操作系统的特点,而不是C++的特点
15 inline void keep_window_open()
16 {
17 char ch;
18 //std::cin >> ch;
19 getchar();
20 }
21
22 inline void error(string s)
23 {
24 cout << s << endl;
25 }
main.cpp
1 /**********************************************************
2 *
3 * 2013-2-4
4 *
5 * 简单计算器
6 *
7 * CocoonFan
8 *
9 ***********************************************************/
10 /***********************************************************
11 *
12 ***********************************************************/
13
14 #include "std_lib_facilities.h"
15 const char number = '8';//代表数字
16 const char quit = 'q';
17 const char print = ';';
18 const string prompt = " >>";
19 const string result = "=";
20
21 class Token{
22 public:
23 char kind;//运算符号的类型
24 double value;
25
26 //constructor
27 Token(char ch)
28 //以冒号开始的成员初始化列表仅用于构造函数中
29 :kind(ch),value(0){}
30 Token(char ch, double val)
31 :kind(ch),value(val){}
32 };
33
34 class Token_stream{
35 public:
36 Token_stream();
37 Token get();
38 void putback(Token t);
39 private:
40 bool full;
41 Token buffer;
42 };
43
44 //constructor
45 Token_stream::Token_stream()
46 :full(false),buffer(0){}
47
48 //put a Token back
49 void Token_stream::putback(Token t)
50 {
51 if(full){//if buffer is full...
52 error("putback() into a full buffer");
53 }
54 buffer = t;
55 full = true;
56 }
57
58 //read a Tocken
59 Token Token_stream::get()
60 {
61 if(full){//do we hava a Token ready?
62 full = false;
63 return buffer;
64 }
65
66 char ch;
67 cin >> ch;
68
69 switch(ch){
70 case ';':
71 case 'q':
72 case '(':
73 case ')':
74 case '+':
75 case '-':
76 case '*':
77 case '/':
78 return Token(ch);
79 case '.':
80 case '0':
81 case '1':
82 case '2':
83 case '3':
84 case '4':
85 case '5':
86 case '6':
87 case '7':
88 case '8':
89 case '9':
90 {
91 cin.putback(ch);
92 double val;
93 cin >> val;
94 return Token(number,val);
95 }
96 default:
97 error("Bad token");
98
99 }
100 }
101
102
103 Token_stream ts;
104
105 double expression()
106 {
107 double left = term();
108 Token t = ts.get();
109
110 while(true){
111 switch(t.kind){
112 case '+':
113 left += term();
114 t = ts.get();
115 break;
116 case '-':
117 left -= term();
118 t = ts.get();
119 break;
120 default:
121 ts.putback(t);
122 return left;
123 }
124 }
125 }
126
127 double term()
128 {
129 double left = primary();
130 Token t = ts.get();
131
132 while(true){
133 switch(t.kind){
134 case '*':
135 left *= primary();
136 t = ts.get();
137 break;
138 case '/':
139 {
140 double d = primary();
141 if(d == 0){
142 error("divide by zero");
143 }
144 left/=d;
145 t = ts.get();
146 break;
147 }
148 default:
149 ts.putback(t);
150 return left;
151 }
152 }
153 }
154
155 double primary()
156 {
157 Token t = ts.get();
158 switch(t.kind){
159 case '(':
160 {
161 double d = expression();
162 t = ts.get();
163 if(t.kind != ')'){
164 error("')'expcted");
165 }
166 return d;
167 }
168 case number:
169 return t.value;
170 case '-':
171 return -primary();
172 case '+':
173 return primary();
174 default:
175 error("primary expected");
176 }
177 }
178 int main()
179 {
180 double val = 0;
181 while(cin){
182 cout << prompt;
183 Token t = ts.get();
184
185 if(t.kind == quit) break;
186 if(t.kind == print)
187 cout << result << val << endl;
188 else
189 ts.putback(t);
190 val = expression();
191 }
192 }
运行结果:
原文链接: https://www.cnblogs.com/CocoonFan/archive/2013/02/07/2908623.html
欢迎关注
微信关注下方公众号,第一时间获取干货硬货;公众号内回复【pdf】免费获取数百本计算机经典书籍
原创文章受到原创版权保护。转载请注明出处:https://www.ccppcoding.com/archives/77762
非原创文章文中已经注明原地址,如有侵权,联系删除
关注公众号【高性能架构探索】,第一时间获取最新文章
转载文章受原作者版权保护。转载请注明原作者出处!