码迷,mamicode.com
首页 > 其他好文 > 详细

四则运算3

时间:2016-03-19 12:55:54      阅读:282      评论:0      收藏:0      [点我收藏+]

标签:

在原来的四则运算基础上,对程序进行了扩充。

题目要求:

    1.学生写的程序必须能够判定用户输入的答案是否正确

    2.程序必须能够处理四种运算的混合算式。

解决办法;

   1.调用随机生成四则运算函数,按照要求生成所需的题目数量以及范围等,并将生成的算式保存在txt文件中。

   2.对TXT文件进行操作,读取每一行字符串。

   3.判断用户输入的结果是否正确,需要运用堆栈来对输入的字符串进行计算,并返回结果。

   4.对结果进行判断。

   5,将生成的TXT文件删除。

代码:

 

//四则运算3
//成员:张勋 王楗
#include <iostream>
#include <fstream>
#include <string>
#include <cmath>
#include <sstream>
#include <time.h>
using namespace std;

#define true 1
#define false 0
#define OPSETSIZE 8

typedef int Status;
unsigned char Prior[8][8] =
{ // 运算符优先级表
    // ‘+‘ ‘-‘ ‘*‘ ‘/‘ ‘(‘ ‘)‘ ‘#‘ ‘^‘
    /*‘+‘*/>, >, <, <, <, >, >, <,
    /*‘-‘*/>, >, <, <, <, >, >, <,
    /*‘*‘*/>, >, >, >, <, >, >, <,
    /*‘/‘*/>, >, >, >, <, >, >, <,
    /*‘(‘*/<, <, <, <, <, =,  , <,
    /*‘)‘*/>, >, >, >,  , >, >, >,
    /*‘#‘*/<, <, <, <, <,  , =, <,
    /*‘^‘*/>, >, >, >, <, >, >, >
};
typedef struct StackChar
{
    char c;
    struct StackChar *next;
}SC;       //StackChar类型的结点SC
typedef struct StackFloat
{
    float f;
    struct StackFloat *next;
}SF;       //StackFloat类型的结点SF

SC *Push(SC *s, char c)          //SC类型的指针Push,返回p
{
    SC *p = (SC*)malloc(sizeof(SC));
    p->c = c;
    p->next = s;
    return p;
}
SF *Push(SF *s, float f)        //SF类型的指针Push,返回p
{
    SF *p = (SF*)malloc(sizeof(SF));
    p->f = f;
    p->next = s;
    return p;
}
SC *Pop(SC *s)    //SC类型的指针Pop
{
    SC *q = s;
    s = s->next;
    free(q);
    return s;
}
SF *Pop(SF *s)      //SF类型的指针Pop
{
    SF *q = s;
    s = s->next;
    free(q);
    return s;
}


float Operate(float a, unsigned char theta, float b)      //计算函数Operate
{
    switch (theta)
    {
    case +: return a + b;
    case -: return a - b;
    case *: return a*b;
    case /: return a / b;
    case ^: return pow(a, b);
    default: return 0;
    }
}

char OPSET[OPSETSIZE] = { +, -, *, /, (, ), #, ^ };
Status In(char Test, char *TestOp)
{
    int Find = false;
    for (int i = 0; i < OPSETSIZE; i++)
    {
        if (Test == TestOp[i])
            Find = true;
    }
    return Find;
}

Status ReturnOpOrd(char op, char *TestOp)
{
    for (int i = 0; i < OPSETSIZE; i++)
    {
        if (op == TestOp[i])
            return i;
    }
}

char precede(char Aop, char Bop)
{
    return Prior[ReturnOpOrd(Aop, OPSET)][ReturnOpOrd(Bop, OPSET)];
}


//计算运算式数值:EvaluateExpression
//-------------------------------------------------------------
float EvaluateExpression(char* MyExpression)
{
    // 算术表达式求值的算符优先算法
    // 设OPTR和OPND分别为运算符栈和运算数栈,OP为运算符集合
    SC *OPTR = NULL;       // 运算符栈,字符元素
    SF *OPND = NULL;       // 运算数栈,实数元素
    char TempData[20];
    float Data, a, b;
    char theta, *c, Dr[] = { #, \0 };
    OPTR = Push(OPTR, #);
    c = strcat(MyExpression, Dr);
    strcpy(TempData, "\0");//字符串拷贝函数
    while (*c != # || OPTR->c != #)
    {
        if (!In(*c, OPSET))
        {
            Dr[0] = *c;
            strcat(TempData, Dr);           //字符串连接函数
            c++;
            if (In(*c, OPSET))
            {
                Data = atof(TempData);       //字符串转换函数(double)
                OPND = Push(OPND, Data);
                strcpy(TempData, "\0");
            }
        }
        else    // 不是运算符则进栈
        {
            switch (precede(OPTR->c, *c))
            {
            case <: // 栈顶元素优先级低
                OPTR = Push(OPTR, *c);
                c++;
                break;
            case =: // 脱括号并接收下一字符
                OPTR = Pop(OPTR);
                c++;
                break;
            case >: // 退栈并将运算结果入栈
                theta = OPTR->c; OPTR = Pop(OPTR);
                b = OPND->f; OPND = Pop(OPND);
                a = OPND->f; OPND = Pop(OPND);
                OPND = Push(OPND, Operate(a, theta, b));
                break;
            } //switch
        }
    } //while
    return OPND->f;
}
//符号函数
//-------------------------------------------------------------
string fuhao(int chu)
{
    string fu;
    int num_3;
    if (chu == 1)
    {
        num_3 = (rand() % 100) % 4;
        if (num_3 == 0) fu = +;
        else if (num_3 == 1) fu = -;
        else if (num_3 == 2) fu = *;
        else fu = /;
        return fu;
    }
    else
    {
        num_3 = (rand() % 20) % 2;
        if (num_3 == 0) fu = +;
        else   fu = -;
        return fu;
    }
}
//分数函数
//-------------------------------------------------------------
string  fenshu()
{
    int a1 = 0, b1 = 0, a2 = 0, b2 = 0;
    a1 = (rand() % (97));
    b1 = (rand() % (100 - a1)) + a1 + 1;
    a2 = (rand() % (97));
    b2 = (rand() % (100 - a2)) + a2 + 1;
    string first_a1, second_b1;
    string first_a2, second_b2;
    first_a1 = to_string(a1);
    second_b1 = to_string(b1);
    first_a2 = to_string(a2);
    second_b2 = to_string(b2);
    string all1 = "";
    //随机产生四则运算符
    int fu = 0;
    fu = (rand() % 100) % 2;
    if (fu == 0)
    {
        all1 = "(" + first_a1 + "/" + second_b1 + ")" + "+" + "(" + first_a2 + "/" + second_b2 + ")" + "=";
    }
    else if (fu == 1)
    {
        all1 = "(" + first_a1 + "/" + second_b1 + ")" + "-" + "(" + first_a2 + "/" + second_b2 + ")" + "=";
    }
    else if (fu == 2)
    {
        all1 = "(" + first_a1 + "/" + second_b1 + ")" + "*" + "(" + first_a2 + "/" + second_b2 + ")" + "=";
    }
    else
    {
        all1 = "(" + first_a1 + "/" + second_b1 + ")" + "/" + "(" + first_a2 + "/" + second_b2 + ")" + "=";
    }
    return all1;
}
//运算函数
//-------------------------------------------------------------
string yunsuan(int chu, int kuohao, int range)
{
    int num_1, num_2;
    int geshu;
    string str_first, str_second;
    string all = "";
    int ch1;
    geshu = (rand() % (8) + 2);
    ofstream fout;
    for (int i = 1; i <= geshu; i++)
    {
        num_1 = (rand() % (range)) + 1;
        str_first = to_string(num_1);
        num_2 = (rand() % (range)) + 1;
        str_second = to_string(num_2);
        if (kuohao == 1)
        {
            ch1 = (rand() % (4)) + 1;
            switch (ch1){
            case 1:
            {
                      if (all == "") { all = str_first + fuhao(chu) + str_second; }
                      else  { all = str_first + fuhao(chu) + all; }
            }break;
            case 2:
            {
                      if (all == "") { all = str_second + fuhao(chu) + str_first; }
                      else { all = all + fuhao(chu) + str_first; }
            }break;
            case 3:
            {
                      if (all == "") { all = "(" + str_first + fuhao(chu) + str_second + ")"; }
                      else { all = "(" + str_first + fuhao(chu) + all + ")"; }
            }break;
            case 4:
            {
                      if (all == ""){ all = "(" + str_second + fuhao(chu) + str_first + ")"; }
                      else { all = "(" + all + fuhao(chu) + str_first + ")"; }
            }break;
            }
        }
        else
        {
            ch1 = (rand() % (2)) + 1;
            switch (ch1){
            case 1:
            {
                      if (all == "") { all = str_first + fuhao(chu) + str_second; }
                      else  { all = str_first + fuhao(chu) + all; }
            }break;
            case 2:
            {
                      if (all == "") { all = str_second + fuhao(chu) + str_first; }
                      else { all = all + fuhao(chu) + str_first; }
            }break;
            }
        }
    }
    string c = all.substr(0, 1);
    string b = all.substr(all.length() - 1, all.length());
    if (c == "("&&b == ")")
    {
        all = all.substr(1, all.length() - 2);
        return all + "=";
    }
    else
    {
        return  all + "=";
    }
}


//主函数
//-------------------------------------------------------------
int main(void)
{
    srand(time(NULL));
    int chu, kuohao, range;
    int calculate_fenshu = 0;//统计分数个数
    int Y_N;
    int count;//设置循环次数
    int disport;
    ofstream file;
    ofstream file_result;
    FILE *f1;
    cout << "有无除法:(1:有,2:无)" << endl;
    cin >> chu;
    cout << "是否有括号:(1:有,2:无)" << endl;
    cin >> kuohao;
    cout << "请输入数值的范围:" << endl;
    cout << "1-";
    cin >> range;
    cout << "请输入一共有多少个算式:" << endl;
    cin >> count;
    //分数
    cout << "是否产生分数(产生真分数):(1:是,2:否)" << endl;
    cin >> Y_N;
    file.open("test.txt");
    //************将生成的算式保存在文件中**********************
    if (Y_N == 1)
    {
        cout << "产生的" << count << "个算式中,希望有几个分数式:" << endl;
        cout << "分数式结果请保留两位小数:" << endl;
        cin >> calculate_fenshu;
        for (int m = 0; m < calculate_fenshu; m++)
        {
            file << fenshu() << endl;
        }
    }

    for (int i = calculate_fenshu; i <= count; i++)
    {
        file << yunsuan(chu, kuohao, range) << endl;
        //fenshu();
    }
    file.close();
    //*************************
    char a[255];
    double cin_result;
    int jishu = 0;
    cout << "是否将生成的算式以及结果输出到文件:(1:是, 2:否)" << endl;
    cin >> disport;
    cout << "生成的四则运算式为:" << endl;
    cout << endl;
    if (disport == 1)
    {
        file_result.open("rusult.txt");
        file_result << "***************************四则运算式****************************" << endl;
        if (f1 = fopen("test.txt", "r"))
        {
            for (int j = 0; j < count; j++)
            {
                fscanf(f1, "%s", a); //文件内容一行不要大于255个字符

                cout << j + 1 << ".";
                cout << a << endl;
                file_result << j + 1 << "." << a << endl;
                cout << "请输入结果:" << endl;
                file_result << "请输入结果:" << endl;
                cin >> cin_result;
                file_result << cin_result;
                file_result << endl;
                if (fabs(cin_result - EvaluateExpression(a)) < 1e-2)
                {
                    cout << "结果正确" << endl;
                    file_result << "结果正确" << endl;
                    jishu = jishu + 1;
                }
                else
                {
                    cout << "结果错误,正确答案为:" << EvaluateExpression(a) << endl;
                    file_result << "结果错误,正确答案为:" << EvaluateExpression(a) << endl;
                }
            }
            cout << "您一共答对" << jishu << "道题,答错" << count - jishu << "道题。" << endl;
            file_result << "您一共答对" << jishu << "道题,答错" << count - jishu << "道题。" << endl;
            fclose(f1);
        }
        file.close();
    }
    else
    {

        if (f1 = fopen("test.txt", "r"))
        {
            for (int j = 0; j < count; j++)
            {
                fscanf(f1, "%s", a); //文件内容一行不要大于255个字符
                cout << j + 1 << ".";
                cout << a << endl;
                cout << "请输入结果:" << endl;
                cin >> cin_result;
                if (fabs(cin_result - EvaluateExpression(a)) < 1e-2)
                {
                    cout << "结果正确" << endl;
                    jishu = jishu + 1;
                }
                else
                {
                    cout << "结果错误,正确答案为:" << EvaluateExpression(a) << endl;
                }
            }
            cout << "您一共答对" << jishu << "道题,答错" << count - jishu << "道题。" << endl;
            fclose(f1);
        }
        file.close();
    }
    system("DEL /f test.txt");
    return 0;
}

调试结果:

技术分享技术分享

再次运行。

技术分享技术分享

试验结果表明,能基本上满足要求,能对结果进行判断,

项目计划总结:        
日期\任务 听课 编写程序 查阅资料 日总计  
星期一 2 1 1 4  
星期二   2 1 3  
星期三   2 1 3  
星期四 2 2 1 5  
星期五   5 1 6  
星期六          
星期日          
周总计 4 12 5 21  
           
时间记录日志:          
日期 开始时间 结束时间 中断时间 静时间 活动 备注
3月14日 14:00 15:50 10 100 听课 软件工程
  19:30 21:50 10 180 编写程序 编写程序架构、增加新功能&查资料
3月15日 18:20 21:45 25 135 编写程序  
3月16日 14:30 17:40 10 180 查阅资料 学习数据结构相关知识
          编写程序  
3月17日 14:00 15:50 10 100 听课 软件工程
  18:20 21:20   180 编写程序 调试程序寻找错误地方
3月18日 14:10 20:40 90 300 编写程序 调试程序为主,并修改部分功能,规范代码
  21:00 22:00   60 看书  
3月19日 8:00 9:00   60 调试 最终调试
缺陷记录日志:        
日期 编号 引入阶段 排除阶段 修复时间&问题描述  
3月14日 1 编码 编译 1.5小时,计算函数的数据结构出错  
3月15日 2 编码 编码 1小时,产生的随机算式输出到文本中,并进行读取时出错。  
3月16日 3 编码 编译 1.5小时,用计算函数调试产生的文本中的算式,不能正确计算出结果  
3月17日 4 编码 编译 2小时,分数式无法正确判断结果  
3月18日 5 编码 编译 3.5小时,保存文件时,无法将答题结果输入到文件中;部分代码不规范  
           

队员:张勋:http://www.cnblogs.com/X-knight/

结对编程照片:

技术分享

四则运算3

标签:

原文地址:http://www.cnblogs.com/wangjianly/p/5294584.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!