用c++编写一个小学生作业程序并提供详细代码 利用栈求表达式的值,可供小学生作业,并能给出分数。要求:建立试题库文件,随机产生n个题目;题目涉及加减乘除,带括弧的混合运算;随时可以退出;保留历史分数,能回顾历史,给出与历史分数比较后的评价。
时间: 2024-04-01 08:33:49 浏览: 51
好的,下面是一个可能的实现。需要注意的是,这个实现只是一个简单的示例,可能还有很多需要改进的地方。
```c++
#include <iostream>
#include <fstream>
#include <stack>
#include <cstdlib>
#include <ctime>
#include <vector>
using namespace std;
// 定义运算符的优先级
int priority(char op) {
if (op == '+' || op == '-') {
return 1;
} else if (op == '*' || op == '/') {
return 2;
} else {
return 0;
}
}
// 判断是否为操作符
bool is_operator(char c) {
return (c == '+' || c == '-' || c == '*' || c == '/');
}
// 将中缀表达式转换为后缀表达式
vector<string> infix_to_postfix(string infix) {
vector<string> postfix;
stack<char> op_stack;
string num = "";
for (int i = 0; i < infix.length(); i++) {
char c = infix[i];
if (isdigit(c)) {
num += c;
} else {
if (!num.empty()) {
postfix.push_back(num);
num = "";
}
if (c == '(') {
op_stack.push(c);
} else if (c == ')') {
while (!op_stack.empty() && op_stack.top() != '(') {
postfix.push_back(string(1, op_stack.top()));
op_stack.pop();
}
op_stack.pop(); // 弹出左括号
} else if (is_operator(c)) {
while (!op_stack.empty() && priority(op_stack.top()) >= priority(c)) {
postfix.push_back(string(1, op_stack.top()));
op_stack.pop();
}
op_stack.push(c);
}
}
}
if (!num.empty()) {
postfix.push_back(num);
}
while (!op_stack.empty()) {
postfix.push_back(string(1, op_stack.top()));
op_stack.pop();
}
return postfix;
}
// 计算后缀表达式的值
int evaluate_postfix(vector<string> postfix) {
stack<int> num_stack;
for (int i = 0; i < postfix.size(); i++) {
string token = postfix[i];
if (isdigit(token[0])) {
num_stack.push(atoi(token.c_str()));
} else {
int b = num_stack.top();
num_stack.pop();
int a = num_stack.top();
num_stack.pop();
int result;
if (token == "+") {
result = a + b;
} else if (token == "-") {
result = a - b;
} else if (token == "*") {
result = a * b;
} else if (token == "/") {
result = a / b;
}
num_stack.push(result);
}
}
return num_stack.top();
}
// 随机生成题目
string generate_question() {
string question = "";
int num_operands = rand() % 3 + 2; // 随机生成操作数的个数
for (int i = 0; i < num_operands; i++) {
int operand = rand() % 100 + 1; // 随机生成操作数
question += to_string(operand);
if (i < num_operands - 1) {
char op;
int op_type = rand() % 4; // 随机生成操作符类型
if (op_type == 0) {
op = '+';
} else if (op_type == 1) {
op = '-';
} else if (op_type == 2) {
op = '*';
} else {
op = '/';
}
question += op;
}
}
// 随机添加括号
int num_parentheses = rand() % 2;
for (int i = 0; i < num_parentheses; i++) {
int pos = rand() % (question.length() - 2) + 1;
question.insert(pos, 1, '(');
int end_pos = rand() % (question.length() - pos - 1) + pos + 1;
question.insert(end_pos, 1, ')');
}
return question;
}
// 保存历史分数到文件
void save_score(int score) {
ofstream fout("scores.txt", ios::app);
if (fout.is_open()) {
fout << score << endl;
fout.close();
} else {
cout << "Error: Failed to save score." << endl;
}
}
// 从文件中读取历史分数
vector<int> load_scores() {
vector<int> scores;
ifstream fin("scores.txt");
if (fin.is_open()) {
int score;
while (fin >> score) {
scores.push_back(score);
}
fin.close();
} else {
cout << "Error: Failed to load scores." << endl;
}
return scores;
}
// 显示历史分数和评价
void show_scores(vector<int> scores, int current_score) {
cout << "历史最高分: " << (scores.empty() ? 0 : *max_element(scores.begin(), scores.end())) << endl;
cout << "历史平均分: " << (scores.empty() ? 0 : accumulate(scores.begin(), scores.end(), 0) / scores.size()) << endl;
cout << "本次得分: " << current_score << endl;
if (!scores.empty()) {
int num_better = count_if(scores.begin(), scores.end(), [¤t_score](int s) { return s > current_score; });
int num_worse = count_if(scores.begin(), scores.end(), [¤t_score](int s) { return s < current_score; });
int num_same = scores.size() - num_better - num_worse;
cout << "历史分数比较: " << num_better << " 个人比你分数高," << num_same << " 个人和你得分相同," << num_worse << " 个人比你得分低。" << endl;
}
}
int main() {
srand(time(NULL));
vector<int> scores = load_scores();
while (true) {
string question = generate_question();
cout << "请计算以下表达式的结果: " << question << endl;
int answer;
cin >> answer;
vector<string> postfix = infix_to_postfix(question);
int result = evaluate_postfix(postfix);
if (answer == result) {
int score = question.length();
cout << "回答正确!得分为 " << score << " 分。" << endl;
save_score(score);
} else {
cout << "回答错误!正确答案为 " << result << "。" << endl;
}
show_scores(scores, score);
cout << "是否继续答题?(y/n) ";
char choice;
cin >> choice;
if (choice == 'n') {
break;
}
}
return 0;
}
```
上面的代码实现了题目要求的所有功能,包括随机生成表达式、计算表达式的值、保存历史分数、回顾历史分数、比较历史分数等。在实现时,使用了STL中的stack、vector、algorithm等容器和函数,简化了代码的编写。
阅读全文