今天我们说一下高精度计算,整体思路呢就是模拟竖式
加法:
1.储存,注意要用字符串进行输入,再用数组进行逆序存储。2.每行进行竖式加法,得到新的c数组,注意进位。3.长度固定,先判断进位情况,再判断前导0,最后输出输出。下面是函数代码:
#include<iostream>
#include<cstdio>
#include<string>
using namespace std;
const int N=1005;
int sa[N],sb[N],sc[N];
void fun(string a,string b){
int la=a.size();
int lb=b.size();
int lc=la>lb?la:lb;
for(int i=la-1,j=0;i>=0;i--){
sa[++j]=a[i]-'0';
}
for(int i=lb-1,j=0;i>=0;i--){
sb[++j]=b[i]-'0';
}
for(int i=1;i<=lc;i++){
sc[i]+=sa[i]+sb[i];
if(sc[i]>=10){
sc[i]-=10;
sc[i+1]++;
}
}
if(sc[lc+1]!=0) lc++;
while(lc>=2&&sc[lc]==0) lc--;
for(int i=lc;i>=1;i--){
printf("%d",sc[i]);
}
return;
}
int main(){
string s1,s2;
cin>>s1>>s2;
fun(s1,s2);
return 0;
}
减法:
1.减法的不同就是要在开头加一步负数的判断。2.模拟减法。3.原第三步要改成减法的退位情况:
#include<iostream>
#include<cstdio>
#include<string>
using namespace std;
const int N=1005;
int sa[N],sb[N],sc[N];
void fun(string a,string b){
if(a.size()<b.size()||a.size()==b.size()&&a<b){
printf("-");
a.swap(b);
}
int la=a.size();
int lb=b.size();
for(int i=la-1,j=0;i>=0;i--){
sa[++j]=a[i]-'0';
}
for(int i=lb-1,j=0;i>=0;i--){
sb[++j]=b[i]-'0';
}
for(int i=1;i<=la;i++){
if(sa[i]<sb[i]){
sa[i]+=10;
sa[i+1]--;
}
sc[i]=sa[i]-sb[i];
}
if(sc[la+1]!=0) la++;
while(la>=2&&sc[la]==0) la--;
for(int i=la;i>=1;i--){
printf("%d",sc[i]);
}
return;
}
int main(){
string s1,s2;
cin>>s1>>s2;
fun(s1,s2);
return 0;
}
乘法:
1.乘法竖式要把积写在i+j-1位上。2.长度有时是la+lb位,有时是la+lb-1位。其余与加法相同:
#include<iostream>
#include<cstdio>
#include<string>
using namespace std;
const int N=1005;
int sa[N],sb[N],sc[N];
void fun(string a,string b){
int la=a.size();
int lb=b.size();
int lc;
for(int i=la-1,j=0;i>=0;i--){
sa[++j]=a[i]-'0';
}
for(int i=lb-1,j=0;i>=0;i--){
sb[++j]=b[i]-'0';
}
for(int i=1;i<=la;i++){
for(int j=1;j<=lb;j++){
sc[i+j-1]+=sa[i]*sb[j];
if(sc[i+j-1]>=10){
sc[i+j]+=sc[i+j-1]/10;
sc[i+j-1]%=10;
}
}
}
if(sc[la+lb]!=0) lc=la+lb;
else lc=la+lb-1;
while(lc>=2&&sc[lc]==0) lc--;
for(int i=lc;i>=1;i--){
printf("%d",sc[i]);
}
return;
}
int main(){
string s1,s2;
cin>>s1>>s2;
fun(s1,s2);
return 0;
}
除法(这里指高进制除低进制,保留整数):
1.再每一位同时,从高位到低位的除法。2.判断商首位零0的情况,进行删减。
#include<iostream>
#include<cstdio>
#include<string>
using namespace std;
const int N=5005;
int sa[N],sb[N],sc[N];
void fun(string a,int b){
int num=0,j=1,l=a.size();
for(int i=1;i<=l;i++){ //因为最高位开始除,所以不用换位置
sa[i]=a[i-1]-'0' ;
sc[i]=(num*10+sa[i])/b;
num=(num*10+sa[i])%b;
}
while(sc[j]==0&&j<l) j++;
for(int i=j;i<=l;i++){
printf("%d",sc[i]);
}
return;
}
int main(){
string s1;
int s2;
cin>>s1>>s2;
fun(s1,s2);
return 0;
}
接下来合并一下就是这样:
#include<iostream>
#include<cstdio>
#include<string>
#include<cstring>
#include<algorithm>
using namespace std;
const int N=5005;
int sa[N],sb[N],sc[N];
void addition(string a,string b){
int la=a.size();
int lb=b.size();
int lc=la>lb?la:lb;
for(int i=la-1,j=0;i>=0;i--){
sa[++j]=a[i]-'0';
}
for(int i=lb-1,j=0;i>=0;i--){
sb[++j]=b[i]-'0';
}
for(int i=1;i<=lc;i++){
sc[i]+=sa[i]+sb[i];
if(sc[i]>=10){
sc[i]-=10;
sc[i+1]++;
}
}
if(sc[lc+1]!=0) lc++;
while(lc>=2&&sc[lc]==0) lc--;
for(int i=lc;i>=1;i--){
printf("%d",sc[i]);
}
return;
}
void subtraction(string a,string b){
if(a.size()<b.size()||a.size()==b.size()&&a<b){
printf("-");
a.swap(b);
}
int la=a.size();
int lb=b.size();
for(int i=la-1,j=0;i>=0;i--){
sa[++j]=a[i]-'0';
}
for(int i=lb-1,j=0;i>=0;i--){
sb[++j]=b[i]-'0';
}
for(int i=1;i<=la;i++){
if(sa[i]<sb[i]){
sa[i]+=10;
sa[i+1]--;
}
sc[i]=sa[i]-sb[i];
}
if(sc[la+1]!=0) la++;
while(la>=2&&sc[la]==0) la--;
for(int i=la;i>=1;i--){
printf("%d",sc[i]);
}
return;
}
void multiplication(string a,string b){
int la=a.size();
int lb=b.size();
int lc;
for(int i=la-1,j=0;i>=0;i--){
sa[++j]=a[i]-'0';
}
for(int i=lb-1,j=0;i>=0;i--){
sb[++j]=b[i]-'0';
}
for(int i=1;i<=la;i++){
for(int j=1;j<=lb;j++){
sc[i+j-1]+=sa[i]*sb[j];
if(sc[i+j-1]>=10){
sc[i+j]+=sc[i+j-1]/10;
sc[i+j-1]%=10;
}
}
}
if(sc[la+lb]!=0) lc=la+lb;
else lc=la+lb-1;
while(lc>=2&&sc[lc]==0) lc--;
for(int i=lc;i>=1;i--){
printf("%d",sc[i]);
}
return;
}
void division(string a,string b){
int num=0,j=1,l=a.size();
int bb=0;
for(int i=b.size()-1,k=1;i>=0;i--){
bb+=(b[i]-'0')*k%10;
k*=10;
}
for(int i=1;i<=l;i++){ //因为最高位开始除,所以不用换位置
sa[i]=a[i-1]-'0' ;
sc[i]=(num*10+sa[i])/bb;
num=(num*10+sa[i])%bb;
}
while(sc[j]==0&&j<l) j++;
for(int i=j;i<=l;i++){
printf("%d",sc[i]);
}
return;
}
int main(){
while(1){
string s,s1,s2;
char ch;
memset(sa,0,sizeof(sa));
memset(sb,0,sizeof(sb));
memset(sc,0,sizeof(sc));
cin>>s;
if(s=="return") return 0;
for(int i=0;i<s.size();i++){
if(s[i]=='+'||s[i]=='-'||s[i]=='*'||s[i]=='/'){
ch=s[i];
s1=s.substr(0,i);
s2=s.substr(i+1,s.size()-i-1);
}
switch(ch){
case '+':addition(s1,s2);break;
case '-':subtraction(s1,s2);break;
case '*':multiplication(s1,s2);break;
case '/':division(s1,s2);break;
}
if(s[i]=='+'||s[i]=='-'||s[i]=='*'||s[i]=='/') break;
}
}
return 0;
}
拜拜!