【算法】大数加减

超长的整型加减法可以用数组int来存储,每个单元可以存储1~9位数字,然后模拟手算过程

大数乘除法,稍复杂,(挖坑)续更..

====================分割线====================

  1 /*************************************************
  2 Copyright: CheerM
  3 Author: CheerM
  4 Date: 2016-11-02
  5 Description: 实现超长int型的加减运算。输入任意长度整数的简单计算式,e.g.A+B,A-B,可获得运算结果
  6 **************************************************/
  7
  8 #ifndef _001_H_
  9 #define _001_H_
 10
 11 #include <iostream>
 12 #include <string>
 13 #include <vector>
 14 #include <iomanip>
 15
 16 using namespace std;
 17
 18 const int max = 1000000000;
 19
 20 /*************************************************
 21 Function:       strToInt
 22 Description:    将字符串表示的整形数字,转为用vector<int>数组存储,因为32位环境下,int最大为2147483647,则可用每一位数组来存储1,000,000,000内的9位数
 23 Calls:          None
 24 Input:          一个任意长的字符串str,表示原始输入的数字
 25                 一个vector<int>类型的指针num,指向存储转变后的数字的数组
 26 Output:         None
 27 Return:         int,数组num的长度
 28 *************************************************/
 29 int strToInt(const string str, vector<int>& num) {
 30     int digits[9] = {1, 10, 100, 1000, 10000, 100000, 1000000, 10000000, 100000000};
 31     int sum = 0, len = str.size();
 32     for (int i = 0; i < len; i ++) {
 33         sum += (str[len - 1 - i] - ‘0‘) * digits[i % 9];
 34         if (i % 9 == 8) {
 35             num.push_back(sum % max);
 36             sum /= max;
 37         }
 38     }
 39
 40     if (sum || num.empty()) num.push_back(sum % max);
 41
 42     vector<int>::iterator it = num.end() - 1;
 43
 44     /*当且仅当num==0时,最高位可以为0*/
 45     while (it != num.begin()) {
 46         if ((*it) == 0)num.erase(it--);
 47         else break;
 48     }
 49
 50     return num.size();
 51 }
 52
 53
 54 /*************************************************
 55 Function:       add
 56 Description:    将字符串表示的整形数字,转为用vector<int>数组存储,模拟手算加法过程
 57 Calls:          None
 58 Input:          2个任意长的字符串str,表示原始输入的数字
 59 Output:         输出相加结果
 60 Return:         None
 61 *************************************************/
 62 void add(string a, string b) {
 63     vector<int> num1, num2;
 64     int len1 = strToInt(a, num1);
 65     int len2 = strToInt(b, num2);
 66
 67     int carry = 0, temp = 0;
 68     vector<int> c;
 69     /*模拟手算加法过程*/
 70     for (int i = 0; i < len1 || i < len2; i ++) {
 71         if (i < len1 && i < len2) {
 72             temp = num1[i] + num2[i] + carry;
 73         }
 74         else if (i >= len1) {
 75             temp = num2[i] + carry;
 76         }
 77         else {
 78             temp = num1[i] + carry;
 79         }
 80
 81         if (temp >= max) {
 82             carry = 1;
 83             temp -= max;
 84         }
 85         else {
 86             carry = 0;
 87         }
 88         c.push_back(temp);
 89     }
 90
 91     /*输出结果,中间不足9位的数字要左补0来补足9位*/
 92     cout << " = ";
 93     cout << c[c.size() - 1];
 94     for (int i = c.size() - 2; i >= 0; i--)
 95     {
 96         cout << setfill(‘0‘) << setw(9);
 97         cout << c[i];
 98     }
 99     cout << endl;
100 }
101
102 /*************************************************
103 Function:       subtract
104 Description:    将字符串表示的整形数字,转为用vector<int>数组存储,模拟手算减法过程
105 Calls:          None
106 Input:          2个任意长的字符串str,表示原始输入的数字
107 Output:         输出相减结果
108 Return:         None
109 *************************************************/
110 void subtract(string a, string b) {
111     bool negNum = false; /*标记结果是否为负数*/
112     if (a.size() < b.size() || (a.size() <= b.size() && a < b)) negNum = true;
113     vector<int> num1, num2;
114     int len1, len2;
115     if (!negNum) {
116         len1 = strToInt(a, num1);
117         len2 = strToInt(b, num2);
118     }
119     else {
120         len1 = strToInt(b, num1);
121         len2 = strToInt(a, num2);
122     }
123
124
125     int borrow = 0, temp = 0;/*借位初始化为0*/
126     vector<int> c;
127     /*模拟手算减法过程*/
128     for (int i = 0; i < len1; i ++) {
129         if (i < len1 && i < len2) {
130             temp = num1[i] - num2[i] - borrow;
131         }
132         else if (i >= len2) {
133             temp = num1[i] - borrow;
134         }
135
136         if (temp < 0) {
137             borrow = 1;
138             temp += max;
139         }
140         else {
141             borrow = 0;
142         }
143         c.push_back(temp);
144     }
145
146     /*输出结果,中间不足9位的数字要左补0来补足9位*/
147     cout << " = ";
148     if (negNum) cout << " - ";
149     cout << c[c.size() - 1];
150     for (int i = c.size() - 2; i >= 0; i--)
151     {
152         cout << setfill(‘0‘) << setw(9);
153         cout<< c[i];
154     }
155
156     cout << endl;
157 }
158
159 void LargeNumOperation(int t) {
160     string a, b;
161     char c;
162     while(t--) {
163         cin >> a >> c >> b;
164         switch (c)
165         {
166         case ‘+‘:
167             add(a, b);
168             break;
169         case ‘-‘:
170             subtract(a, b);
171             break;
172         default:
173             break;
174         }
175     }
176 }
177
178 #endif

001.h

测试结果:

时间: 2024-12-28 21:18:38

【算法】大数加减的相关文章

POJ 2756 Autumn is a Genius 使用string的大数加减

本题就是说一个小神童,能计算加减法. 不过题目知识说这个小神童,到底有多神,要我们自己发现. 因为最后给出的数据非常非常巨大,听说接近50k就是超过50000个数位相加,可想而知他多神. 看来题目也是考IQ啊! 如果以为是超级水题,按照一般加减法做,肯定是WA了. 这里给出使用string的加减法运算,因为string是长度可增可减的,所以不管是多少位,只要内存支持,那么本算法都可以支持了.也可以使用vector这些容器.不过string应该更加省点内存. 注意: POJ比较讨厌的就是不支持C+

字符串大数加减运算问题

这里自己利用STL模板中的容器和链表实现字符串大数加减运算. 1 #include<iostream> 2 #include<vector> 3 #include<list> 4 using namespace std; 5 6 list<char> Input_Number(list<char> ilist)//输入链表字符串,以‘#’作为结束符 7 { 8 cout<<"please Input string ,end

大数加减1——将两个数均前后倒置,以对齐最低位

#include <stdio.h> //将读入的数据存储到num[1]~num[x]中,num[0]表示存入数据的长度. void read(int num[]) { int i; char ch; for (i = 0; i<500; i++) num[i] = 0; i = 1; while ((ch = getchar()) != '\n') { num[i] = ch - '0'; i++; num[0]++; } } //将数据num[]中的数翻转,以便计算 void rev

常见的编程问题(一)少大数加减

存储区的概念 常见的存储区域可分为: 栈 由编译器在需要的时候分配,在不需要的时候自动清除的变量的存储区.里面的变量通常是局部变量.函数参数等. 堆 由new分配的内存块,他们的释放编译器不去管,由我们的应用程序去控制,一般一个new就要对应一个delete.如果程序员没有释放掉,程序会一直占用内存,导致内存泄漏,在程序结束后,操作系统会自动回收. 由malloc等分配的内存块,它和堆是十分相似的,不过它是用free来释放分配的内存. 全局/静态存储区 全局变量和静态变量被分配到同一块内存中,在

大数加减乘模板

大数加法: 1 #include <stdio.h> 2 3 #include <string.h> 4 5 #define M 100 //定义了数量M是100作为数组初始化的数量 6 7 8 9 int main() 10 11 { 12 13 int i, j, len_s1, len_s2; // len_s1是字符数组s1的长度, len_s2是字符数组s2的长度, 14 15 char s1[M], s2[M]; 16 17 int num1[M] = {0}; //

大数加减乘法

大数的相关计算问题一直是编程比赛常考的题目,在蓝桥杯比赛之前又把大数的加减乘法做了一遍.大数除法比较难,还没有去尝试实现,以后有机会了再继续补全好了. 算法分析:三种方法相似,都是按位操作,动态存储.处理好输入数据后,对每一位的逐个操作,很容易得到答案. 大数加法 #include <iostream> #include <cstdio> #include <cstring> #include <cmath> #define MAX 1010 using n

[算法]大数相减

今天在小米OJ上看到一道题(https://code.mi.com/problem/list/view?id=3), 很有意思, 试着做了一下 描述: 两个长度超出常规整形变量上限的大数相减,请避免使用各语言内置大数处理库,如 Java.math.BigInteger 等. 输入: 有 N 行测试数据,每一行有两个代表整数的字符串 a 和 b,长度超过百位.规定 a>=b,a, b > 0. 测试结果可以用 linux 小工具 bc进行测试是否正确. 输出: 返回表示结果整数的字符串. 输入样

大数加减运算

1 #include<iostream> 2 #include<string> 3 4 using namespace std; 5 6 void BDplus(string str1, string str2) 7 { 8 int len1 = str1.length(); 9 int len2 = str2.length(); 10 char *value = NULL; 11 if (len1 >= len2) 12 { 13 //value= (char*)mallo

SPOJ VLATTICE - Visible Lattice Points 【“小”大数加减】

题目链接 一道比较简单的莫比乌斯反演,不过ans会爆long long,我是用结构体来存结果的,结构体中两个LL型变量分别存大于1e17和小于1e17的部分 #include<bits/stdc++.h> using namespace std; typedef long long LL; const int maxn=1e6; int prime[maxn+5]; bool check[maxn+5]; int mu[maxn+5]; void init() { mu[1]=1; int t