一位一位的对着加,注意存储进位,小的数加完后把大数剩下的加进来,注意前导零和相加等于0
// 高精度加法 #include<iostream> #include<string> using namespace std; int res[10000001];//记录结果的数组 string a,b; long long k,r,i,j; bool flag; int main(){ cin>>a>>b; if(a.size()<b.size()||a.size()==b.size()&&a<b){//把大的字符串放在前面方便操作 swap(a,b); } for(i = a.size() - 1,j = b.size()-1;j>=0;i--,j--){//从低位相加,相加他们的公共位 res[k++] = (r+a[i]-'0'+b[j]-'0')%10;//相同位的数相加后取个位 r = (r+a[i]-'0'+b[j]-'0') /10;//记录进位 } while(i>=0){//再把大数的没有运算的部分相加 res[k++] = (r+a[i]-'0')%10;//位数和进位的相加后取个位 r = (r+a[i]-'0')/10;//记录进位 i--; }// if(r){ res[k++] = r;//如果还有进位,进到最高位 } for(i = k-1;i>=0;i--){//输出 if(res[i]!=0||flag){//防止前导0输出的操作. cout<<res[i]; flag = true; } } if(!flag){//如果都为 0,则说明结果为0 cout<<0<<endl; } return 0; }
以上代码是两个正数相加,若有负数,则需要另行判断:
如果两个数都是负数,那么去掉负号,输出结果前加上负号即可。
如果两个数有一个数是负数,先去掉负号,比较大小
如果去掉负号的数大于另一个数,则需要用去掉负号的数减去另一个数,再输出负号(此时用高精度减法)
如果去掉负号的数小于另一个数,则需要用另一个数减去去掉负号的数,(此时用高精度减法)
一位一位的对着减,注意存储借位,小的数减完后把大数剩下的借位减进来,注意前导零和相减等于0
// 高精度减法 #include<iostream> #include<string> using namespace std; int res[10000001]; //记录结果 string a,b; long long k = 0,r = 0,i,j; bool flag; int main(){ cin>>a>>b; if(a.size()<b.size()||(a.size()==b.size()&&a<b)){//如果第一个数比第二个数小,说明结果为负数. cout<<"-"; swap(a,b); } for(i = a.size() - 1,j = b.size() - 1;j >= 0;i--,j--){ res[k++] = (a[i]-b[j]-r);// 两个相同位的数相减再减去 借的位数. r=0;//清零 if(res[k-1]<0){//如果是负数,就借一当十,并标记 res[k-1]+= 10; r = 1;//这次的借的进位 } } while(i>=0){// 较大的数,剩下的位继续运算 res[k++] = a[i] - '0'- r;//减去借的 r = 0;//清零 if(res[k-1]<0){//如果是负数,就借一当十,并标记 res[k-1]+= 10; r = 1;//这次的借的进位 } i--; } for(i = k - 1;i>=0;i--){// 从后往前输出 if(res[i]!=0 || flag){//防止前导0 cout<<res[i]; flag = true; } } if(!flag){ cout<<0<<endl;//如果都没有输出,说明相减结果为0 ,就输出0 } return 0; }
以上代码是两个正数相减,若有负数,则需要另行判断:
List item
如果两个数都是负数,去掉负号,用后一个数减前一个数。
如果两个数有一个数是负数,先去掉负号,比较大小
如果第一个数是负数,相加,输出负号(此时用高精度加法)
如果第二个数是负数,相加(此时用高精度加法)
相信大家都手动计算过乘法,就是一个数的每一位乘另一个数的每一位最后相加即可,当然,我们程序也是这样模拟.
这里有一个基本的知识点,相信大家在手写竖式的时候知道,就是
c[i+j] += a[i]+b[j] (因为a和b都是从0下标开始的,如果从下标1开始,就c[i+j-1]+=a[i]+b[j])
// 高精度乘法 //结果最多 有10000000 位 #include<iostream> #include<string> #include<algorithm> using namespace std; string a,b; int k; int res[10000001];//'3'-'3'+'48' '6' - 48 int main() { cin>>a>>b; reverse(a.begin(),a.end()); reverse(b.begin(),b.end()); for(int i = 0; i < a.size(); i++) { for(int j = 0; j<b.size(); j++) { res[i+j] += (a[i]-48)*(b[j]-48);// } } for(k = 0; k<=a.size()+b.size(); k++) { // n位数 * m位数 最多等于 n+m位数. res[k] += res[k-1] / 10;//k位 等于 该位的值加上 进位. res[k - 1] %= 10; // k位计算未必,前面那一位的值就确定了. 直接写该位的个位即可. } while(!res[k]&&k>=1) { k--;//从后往前寻找第一个不为0的位 } while(k>=0) { //输出结果. cout<<res[k]; k--; } return 0; }
手动模拟除法过程,每次读到新位 然后除 除数,得到的就是该位的结果。如果除不尽,就用0代替. 每次的余数用于下一轮的计算.
#include<bits/stdc++.h> using namespace std; int res[10000001]; string s; long long k = 0,a,b,i; bool flag; int main(){ cin>>s>>b;//输入被除数,除数 for(i = 0; i < s.size();i++){ a = a*10+s[i]-'0';//加上被除数的这一位. res[k++] = a / b; a %= b; // 求余下一轮乘10+再加一位继续乘. } for(i = 0; i < k; i++){//输出结果 if(res[i]!=0||flag){ cout<<res[i]; flag = true;//防止前导0. } } if(!flag){ cout<<0<<endl;//如果都没有输出,则说明相除结果为0 } return 0; }
以上代码是两个正数相除,若有负数,则需要另行判断:
如果两个数都是负数,去掉负号,不管他。
如果两个数有一个数是负数,去掉负号,输出时加上。
这个和高精度除法差不多,不需要记录和输出商就差不多
#include<bits/stdc++.h> using namespace std; //int res[10000001]; string s; long long k = 0,a,b,i; bool flag; int main(){ cin>>s>>b;//输入被除数,除数 for(i = 0; i < s.size();i++){ a = a*10+s[i]-'0';//加上被除数的这一位. //res[k++] = a / b; a %= b; // 求余下一轮乘10+再加一位继续乘. } cout<<a<<endl; return 0; }