每日打卡一小时(第十九、二十天)

一.问题描述

6-3 【CPP0024】设计并实现大数类BigNum

定义一个整数型大数类,要求能够完成100位以内的较大整数的加法和减法计算,main(void)函数完成对其的测试。

BigNum类结构说明:

 
BigNum类的数据成员包括:
①私有数据成员:数值域num(char []型)。
BigNum类成员函数包括:
①有参构造函数BigNum(char c[])和拷贝构造函数BigNum(const  BigNum  &),其中有参构造函数参数默认值为"+0",输出信息"BigNum Constructor run",拷贝构造函数输出信息"BigNum CopyConstructor run"
②析构函数,析构函数输出信息"BigNum Destructor run"
③公有函数成员void  setNum(char c[])char const *getNum(void) const分别返回和设置数值域。
④重载“+”运算符,实现两个BigNum对象相加的运算
⑤重载“-”运算符,实现两个BigNum对象相减的运算
⑥公有成员函数void show() const用于显示BigNum对象的信息,显示格式为:BigNum(<数值域>)
 

建议:大数存储时专门存储符号位且低位存储在前,高位存储在后。这样便于运算实现。

二.设计思路

1.注意构造和设置值时位数倒置

2.注意计算时同号和异号带来的转换

3.注意每个数的位数高低

4.注意减法时数的大小比较方式(先比较位数再比较去符号后数的大小)

三.代码实现

复制代码
#include <iostream>
using namespace std;
#define N 100
#include<cstring>
class BigNum
{
private:
    char num[N];
public:
    BigNum(char c[N] = "+0");
    BigNum(const BigNum& p);
    ~BigNum()
    {
        cout << "BigNum Destructor run" << endl;
    }
    void setNum(char c[N]);
    char const* getNum(void) const;
    BigNum operator + (const BigNum& a);
    BigNum operator - (BigNum& b);
    void show() const;
};


BigNum::BigNum(char c[N])
{
    int i, j, a = strlen(c);
    if (c[0] != '-')
    {
        num[0] = '+';
        if (c)
        {
            for (i = strlen(c), j = 0; i >= 1; i--, j++)//输入的数据倒置
            {
                num[i] = c[j];
            }
        }
        num[a + 1] = '\0';
    }
    else
    {
        num[0] = c[0];
        for (i = strlen(c) - 1, j = 1; i >= 1; i--, j++)
        {
            num[i] = c[j];
        }
        num[a] = '\0';
    }
    cout << "BigNum Constructor run" << endl;
}

BigNum::BigNum(const BigNum& p)
{
    int i = 0;
    for (i; p.num[i] != '\0'; i++)
    {
        num[i] = p.num[i];
    }
    num[i] = '\0';
    cout << "BigNum CopyConstructor run" << endl;
}
void BigNum::setNum(char c[N])
{
    int i, j, a = strlen(c);
    if (c[0] != '-')
    {
        num[0] = '+';
        if (c)
        {
            for (i = strlen(c), j = 0; i >= 1; i--, j++)
            {
                num[i] = c[j];
            }
        }
        num[a + 1] = '\0';
    }
    else
    {
        num[0] = c[0];
        for (i = strlen(c) - 1, j = 1; i >= 1; i--, j++)
        {
            num[i] = c[j];
        }
        num[a] = '\0';
    }
}

char const* BigNum::getNum(void) const
{
    return num;
}

BigNum BigNum::operator + (const BigNum& a)
{
    if (num[0] == '+' && a.num[0] == '-')////如果异号将加法转为减法
    {
        BigNum s2(a);
        s2.num[0] = '+';
        return  (*this) - s2;
    }
    if (num[0] == '-' && a.num[0] == '+')
    {
        BigNum s2(a);
        num[0] = '+';
        return s2 - (*this);
    }
    BigNum s;
    int i;
    char s2[N];
    for (i = 0; a.num[i] != '\0'; i++)
    {
        s2[i] = a.num[i];
    }
    s2[i] = '\0';
    int len1 = strlen(num);
    int len2 = strlen(s2);
    int Max = 0;
    if (len1 > len2)//先比较位数大小
    {
        Max = len1;
        num[len1] = '0';
        for (i = len2; i <= len1; i++)
        {
            s2[i] = '0';
        }
    }
    else
    {
        if (len1 < len2)
        {
            Max = len2;
            s2[len2] = '0';
            for (i = len1; i <= len2; i++)//将位数小的数的再高的位数全置为‘0‘
            {
                num[i] = '0';
            }
        }
        else
        {
            Max = len1;
            s2[len2] = '0';
            num[len1] = '0';
        }
    }
    if ((num[0] == '+' && s2[0] == '+') || (num[0] == '-' && s2[0] == '-'))//进行计算
    {
        for (i = 1; i <= Max; i++)
        {
            int c = ((num[i] - '0') + (s2[i] - '0'));
            if (c >= 10)//满十进一
            {
                c -= 10;
                s.num[i] = char(c + '0');
                s2[i + 1]++;
            }
            else
            {
                s.num[i] = char(c + '0');
            }
        }
        s.num[i] = '\0';
        if (num[0] == '+' && s2[0] == '+')//符号判断
        {
            s.num[0] = '+';
        }
        if (num[0] == '-' && s2[0] == '-')
        {
            s.num[0] = '-';
        }
    }

    return s;
}

BigNum BigNum::operator - (BigNum& b)
{
    if (num[0] == '+' && b.num[0] == '-')//将异号转化为加法
    {
        BigNum s2(b);
        s2.num[0] = '+';
        return  (*this) + s2;
    }
    if (num[0] == '-' && b.num[0] == '+')
    {
        BigNum s2(b);
        s2.num[0] = '-';
        return  (*this) + s2;
    }
    BigNum s;
    int i;
    char s2[N];
    for (i = 0; b.num[i] != '\0'; i++)
    {
        s2[i] = b.num[i];
    }
    s2[i] = '\0';
    int len1 = strlen(num);
    int len2 = strlen(s2);
    int Max = 0;
    if (len1 > len2)
    {
        Max = len1;
        num[len1] = '0';
        for (i = len2; i <= len1; i++)
        {
            s2[i] = '0';
        }
    }
    else
    {
        if (len1 < len2)
        {
            Max = len2;
            s2[len2] = '0';
            for (i = len1; i <= len2; i++)
            {
                num[i] = '0';
            }
        }
        else
        {
            Max = len1;
            s2[len2] = '0';
            num[len1] = '0';
        }
    }
    if ((num[0] == '+' && s2[0] == '+') || (num[0] == '-' && s2[0] == '-'))
    {
        if (num[0] == '-' && s2[0] == '-')
        {
            s2[0] = '+';
            num[0] = '+';
            for (i = 0; num[i] != '\0'; i++)
            {
                char ch;
                ch = num[i];
                num[i] = s2[i];
                s2[i] = ch;
            }
        }
        char s1[N];
        char s3[N];
        int j;
        for (i = Max, j = 0; i > 0; j++, i--)
        {
            s1[j] = num[i];
        }
        s1[j] = '\0';
        for (i = Max, j = 0; i > 0; j++, i--)
        {
            s3[j] = s2[i];
        }
        s3[j] = '\0';
        if (strcmp(s1, s3) > 0)
        {
            s.num[0] = '+';
            for (i = 1; i <= Max; i++)
            {
                int c = ((num[i] - '0') - (s2[i] - '0'));
                if (c < 0)
                {
                    c += 10;
                    s.num[i] = char(c + '0');
                    num[i + 1]--;
                }
                else
                {
                    s.num[i] = char(c + '0');
                }
            }
            s.num[i] = '\0';
        }
        else
        {
            if (strcmp(s1, s3) < 0)
            {
                s.num[0] = '-';
                for (i = 1; i <= Max; i++)
                {
                    int c = ((s2[i] - '0') - (num[i] - '0'));

                    if (c < 0)
                    {
                        c += 10;
                        s.num[i] = char(c + '0');

                        s2[i + 1]--;
                    }
                    else
                    {
                        s.num[i] = char(c + '0');

                    }
                }
                s.num[i] = '\0';
            }
            else
            {
                s.num[0] = '+';
                s.num[1] = '0';
                s.num[2] = '\0';
            }
        }
    }
    return s;
}

void BigNum::show() const
{
    char ch[N] = "+0";
    char c[N] = "+00";
    if (strcmp(ch, num) == 0 || strcmp(c, num) == 0)
    {
        cout << "BigNum(" << ch << ")" << endl;
    }
    else
    {
        cout << "BigNum(" << num[0];
        int i;
        int flag;
        for (i = strlen(num) - 1; i >= 0; i--)
        {
            if (num[i] != '0')
            {
                flag = i;
                break;
            }
        }
        for (i = flag; i >= 1; i--)
        {
            cout << num[i];
        }
        cout << ")" << endl;
    }
}
int main(void) {
    char c[100], op;
    cin >> c;
    BigNum b1(c), b2(b1);
    b1.show();
    cin >> c;
    b2.setNum(c);
    b2.show();
    cin >> op;
    if (op == '+') (b1 + b2).show();
    if (op == '-') (b1 - b2).show();
    return 0;
}
复制代码

 

posted @   伐木工熊大  阅读(28)  评论(2编辑  收藏  举报
相关博文:
阅读排行:
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 25岁的心里话
· 按钮权限的设计及实现
点击右上角即可分享
微信分享提示