C++基础与深度解析--peoject2 长整数加法

1、project2要求和运行示例
在这里插入图片描述运行示例:
在这里插入图片描述

在这里插入图片描述运行示例:
在这里插入图片描述

在这里插入图片描述运行示例:
在这里插入图片描述

2、项目代码

#include <iostream>
#include <fstream>
#include <cassert>
#include <vector>
#include <string.h>
#include <sstream>
#include <algorithm>
#include <cstring>
int char_to_num(char ch){
    if(ch>='a') ch=ch-32;
    if(ch>='0'&&ch<='9')
        return ch-'0';
   if(ch>='A')
        return ch-'A'+10;
}
char num_to_char(int num){
    if(num>=0&&num<=9)
        return (char)('0'+num-0);
    if(num>=10&& num<=36)
        return (char)('A'+num-10);
}

struct IntPair {   //定义结构化数组,用于读取数据的时候返回两个vector
    std::vector<char> v1,v2;
}typedef IntPair;
void check_vector(std::vector<char> v,char c)//检查输入数据是否合法,否则会提示错误
{
    if(c>='a') c=c-32;
    int t=0;
    if(v[0]==45) //首位是否为符号位
       t=1;
    for(int i=0+t; i<v.size(); ++i)
    {  if(v[i]>='a') v[i]=v[i]-32;
       if(v[i]<'0'||v[i]>'Z'||(v[i]>'9'&&v[i]<'A')||v[i]>=c)  //每一项是否合法
       {
           std::cout<<"error! long integer exists wrong character!"<<std::endl;
           std::exit(0);
       }
    }
}
std::vector<char> display(std::vector<char> &v)//vector显示
{
    if(v.size()==1&&v[0]=='0');
    else
        {
            while(v[0]==43||v[0]==48)//不显示数据前头的+和数字0
            {
                std::reverse(v.begin(), v.end());
                v.pop_back();
                std::reverse(v.begin(), v.end());
            }
            if(v[0]==45)
            {
                while(v[0]==45||v[0]==48) //不显示负数前边的数字0
                {
                    std::reverse(v.begin(), v.end());
                    v.pop_back();
                    std::reverse(v.begin(), v.end());
                }
                std::reverse(v.begin(), v.end());
                v.push_back('-');
                std::reverse(v.begin(), v.end());
            }
        }

   for(int i=0; i<v.size();++i)
    {
        std::cout << v[i];//进行数字逐项输出
    }
    std::cout << "\n" << std::endl;
   return v;
}
std::vector<char> display2(std::vector<char> &v)//vector显示
{
    if(v.size()==1&&v[0]=='0');
    else
    {
        while(v[0]==43||v[0]==48)//不显示数据前头的+和数字0
        {
            std::reverse(v.begin(), v.end());
            v.pop_back();
            std::reverse(v.begin(), v.end());
        }
        if(v[0]==45)
        {
            while(v[0]==45||v[0]==48) //不显示负数前边的数字0
            {
                std::reverse(v.begin(), v.end());
                v.pop_back();
                std::reverse(v.begin(), v.end());
            }
            std::reverse(v.begin(), v.end());
            v.push_back('-');
            std::reverse(v.begin(), v.end());
        }
    }
    return v;
}
IntPair readNum(std::string file)//返回文件的数据vector1,vector2
{
  IntPair ret;
  std::fstream infile;
  infile.open(file.data());
  assert(infile.is_open());
  std::vector<char> v;
  std::string s;
  int line=1;
    while (getline(infile,s))
    {
        std::istringstream is(s); //将读出的一行转成数据流进行操作
        char d;
        while (!is.eof())
            {
                is >> d;
                v.push_back(d);
            }
            v.pop_back();
        if(line==1)
        {
            ret.v1=v;
            v.clear();
        }
        else if(line==2)
            ret.v2=v;
        ++line;
    }
    return ret;
}

std::vector<char> Sum(std::vector<char> v1,std::vector<char> v2,char Myprom_inputfile)
{
    std::vector<char> sum;
    if((v1[0]==v2[0]&&(v1[0]==45))||(v1[0]!=45&&v2[0]!=45))//两个数符号位相同或者没有符号位
    {
        int t=0;
        if(v1[0]==v2[0]&&(v1[0]==45))//两个数符号位相同
        {
            if(v1[0]==45) t=1;
            std::reverse(v1.begin(), v1.end());
            std::reverse(v2.begin(), v2.end());
            v1.pop_back();
            v2.pop_back();//移除符号位
            std::reverse(v1.begin(), v1.end());
            std::reverse(v2.begin(), v2.end());
        }
        if(v1.size()==v2.size());//判断v1,v2长度是否一致,不一致的话,将其填零补充到一致
        else
        {   std::reverse(v1.begin(), v1.end());
            std::reverse(v2.begin(), v2.end());
            int length = abs(v1.size()-v2.size());
            if(v1.size()>v2.size())//将不同的数字位数补齐
            {
               for(int j=0;j<length;++j)
               {
                   v2.push_back('0');
               }
            }
            else
            {
               for(int j=0;j<length;++j)
               {
                   v1.push_back('0');
               }
            }
            std::reverse(v1.begin(), v1.end());
            std::reverse(v2.begin(), v2.end());
        }
        std::reverse(v1.begin(), v1.end());
        std::reverse(v2.begin(), v2.end());
        int label = 0;
        for(auto j=0;j< v1.size();++j)//进行加法运算
        {
           if(char_to_num(v1[j])+char_to_num(v2[j])+label>=char_to_num(Myprom_inputfile))
           {
               label = (char_to_num(v1[j])+char_to_num(v2[j])+label)/char_to_num(Myprom_inputfile);

               if(j==0) {sum.push_back(num_to_char(char_to_num(v1[j])+char_to_num(v2[j]) - label*char_to_num(Myprom_inputfile)));}
               else
                   sum.push_back(num_to_char(char_to_num(v1[j])+char_to_num(v2[j]) + label - label*char_to_num(Myprom_inputfile)));
           }
           else
           {
               sum.push_back(num_to_char(char_to_num(v1[j])+char_to_num(v2[j])+label));
               label = 0;
           }
           if((j==v1.size()-1)&&label>0) sum.push_back(num_to_char(label));
        };
        if(t) //负数补充负号
            sum.push_back('-');
       std::reverse(sum.begin(), sum.end());
    }
    //一正一负
    if(v1[0]==45||v2[0]==45)//第一个为正,第二个为负
    {
        int first = 0;
        int second = 0;
        if(v1[0]==45)
        {
            std::reverse(v1.begin(), v1.end());
            second = 1;//第二个数为正
            v1.pop_back();
            std::reverse(v1.begin(), v1.end());
        }
        if(v2[0]==45)
        {
            first = 1;//第一个数为正
            std::reverse(v2.begin(), v2.end());
            v2.pop_back();
            std::reverse(v2.begin(), v2.end());
        }
        if(v1.size()==v2.size())
        {
        }
        else
        {
            int length = abs(v1.size()-v2.size());
            if(v1.size()>v2.size())//将不同的数字位数补齐
            {
                std::reverse(v2.begin(), v2.end());
                for(int j=0;j<length;++j)
                {
                    v2.push_back('0');
                }
                std::reverse(v2.begin(), v2.end());
            }
            else
            {
                std::reverse(v1.begin(), v1.end());
                for(int j=0;j<length;++j)
                {
                    v1.push_back('0');
                }
                std::reverse(v1.begin(), v1.end());
            }
        }
        int v11=0;
        int v22=0;
        std::reverse(v2.begin(), v2.end());
        std::reverse(v1.begin(), v1.end());
        for(int i=0;i<v1.size();++i)
        {
           v11+=char_to_num(v1[i])*pow(char_to_num(Myprom_inputfile),i);
           v22+=char_to_num(v2[i])*pow(char_to_num(Myprom_inputfile),i);
        }
        if(first&&(v11>v22)) ;;
        if(first&&(v11<v22)) v2.swap(v1);
        if(second&&(v11>v22));
        if(second&&(v11<v22)) v2.swap(v1);
        for (auto j = 0; j < v1.size(); ++j)
        {
            if (v1[j]<v2[j])
            {
                v1[j] = num_to_char(char_to_num(v1[j]) + char_to_num(Myprom_inputfile));
                v1[j + 1] =v1[j+1]-1;
            }
            sum.push_back(num_to_char(char_to_num(v1[j])-char_to_num(v2[j])));
        }
        if(first&&(v11<v22)||second&&(v11>v22))
        { sum.push_back('-');}
        std::reverse(sum.begin(), sum.end());
    }
    return sum;
}
void check_second_parameter(char c)
{
    if((c>='0'&&c<='9')||(c>='a'&&c<='z')||(c>='A'&&c<='Z'));//每一项是否合法
    else
    {
        std::cout << "error! wrong character!" << std::endl;
        std::exit(0);//每一项是否合法
    }
}

IntPair div(std::vector<char> sum, char sourc,char objec){//大数除法,结果存储在shang中
    int object = char_to_num(objec);
    int source = char_to_num(sourc);
    int decimal_num = 0;
    IntPair re;
    for(int i = 0; i<sum.size(); i=i+1 )
    {
        decimal_num = decimal_num*source+char_to_num(sum[i]);
        re.v1.push_back(num_to_char(decimal_num/object));
        decimal_num= decimal_num%object;
    }
    re.v2.push_back(num_to_char(decimal_num));
    return re;
}

int main(int argc,char *argv[]) {
    std::string path_name ;
    path_name = argv[1];
    if(argv[2]==NULL)
    {
       argv[2]=(char *)"10";
       argv[3]=(char *)"10";
    }
    else if(argv[3]==NULL)
    {
        argv[3]=argv[2];
    }
    std::string Myprom_inputfile =argv[2];
    std::string Myprom_out_type = argv[3];
    char inputfile = num_to_char(atoi(Myprom_inputfile.c_str()));
    char outputfile = num_to_char(atoi(Myprom_out_type.c_str()));
    check_second_parameter(inputfile);
    check_second_parameter(outputfile);
    IntPair ret = readNum(path_name);//返回数据
    std::cout << "第1个长数据为:"; //进行数据显示
    ret.v1 = display(ret.v1);
    check_vector(ret.v1,inputfile);
    std::cout << "第2个长数据为:" ;
    ret.v2 = display(ret.v2);
    check_vector(ret.v2,inputfile);
    std:: vector<char> sum=Sum(ret.v1,ret.v2,inputfile);
    std::cout << "2个长数据sum为:" ;
    if(inputfile==outputfile)
    {
        sum = display(sum);
    }
    std:: vector<char> result;
    std::cout<<"111"<<std::endl;
    sum = display2(sum);

    if(inputfile!=outputfile)
    {
        int t = 0;
        if(sum[0]=='-')
        {
            sum = display(sum);
            t=1;
            std::reverse(sum.begin(), sum.end());
            sum.pop_back();
            std::reverse(sum.begin(), sum.end());
        }

        IntPair re = div(sum,inputfile,outputfile);
        re.v1 = display2(re.v1);
        re.v2 = display2(re.v2);
        result.push_back(re.v2[0]);
        for(;;)
        {
            if(re.v1.size()==1&&re.v1[0]=='0') break;
            re = div(re.v1,inputfile,outputfile);
            re.v1 = display2(re.v1);
            result.push_back(re.v2[0]);
        }
        if(t==1)  result.push_back('-');

        std::reverse(result.begin(), result.end());
        for(int i=0; i<result.size(); ++i)
            std::cout<<result[i];//逆序输出

        std::cout<<std::endl;
    }
    return 0;
}
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值