在算法竞赛之中,有时候一些题目的意思很容易就可以看出来解决步骤,但是数据却不是平常的数据量,而是高精度数据,这时候要是因为高精度的问题而使得这道题失去了AC的机会岂不是会被队友喷死,所以今天就教教大学关于高精度的一些算法吧。
个人对于高精度的算法,感觉就是很原始的小时候学习加减乘除时候的做法。怎么说呢,当然是一位一位进行处理的,可能乘法有一些什么快速乘法的,这个等后面再进行讲解,现在就说说平常自己针对高精度是怎么进行处理的吧。
首先呢,因为是高精度,那么数字的范围不大可能是int乃至__int64就可以存放的下来的,一般高精度的数字都是利用字符串直接进行存放的,所以我们的函数默认是传递两个字符串进来,对其进行相对应的操作,最后返回相对应的数据处理结果即可。
-
高精度加法:
高精度加法的话,可能是整数与整数相加,也有可能是小数与小数进行运算,也出现不同号进行相加,当然在进行运算的时候,肯定是要判断两个数字的正负性,然后才会决定进行什么对应的操作,要是同号的话,那么就直接计算其绝对值的结果,然后加上相对应的符号。
我们先来介绍一下关于高精度加法之中的整数与整数进行加法运算吧,首先
就是先求出两个字符串的最长长度,然后在比较短的字符串前面给它默认填上相对应的字符串0,比如3210与123相加,最后的处理结果就是3210 + 0123,这样做的好处就是只要判断最首位运算之后,是否会进位即可。然后我们相对应的还要利用一个变量,判断当前的这步运算是否进位。是进行,则变量为1,若是不进位,则变量为0,同时变量参与下一步的运算之中。大概的步骤是如此,接下来我们举个例子吧:
1234567890000000000000000 + 99665433100000000000000000
那么处理之后的结果就是·
01234567890000000000000000
+ 99665433100000000000000000
--------------------------------
100900000990000000000000000
我们可以看的出来,是在进行7 + 3的时候产生了进位,这时候的变量就变为了1,那么之后进行的就是6 + 3 + 1 = 10,还是产生了进位,所以变量还是1,当前位%10的结果是0,所以当前位的结果位0,一直及逆行到2 + 6 + 1 = 9,没有产生进位,所以当前位的结果为9,下一步是9 + 1 = 10,所以当前位的结果位0,产生进位,首位的运算就是9 + 0 + 1 = 10,所以首位的结果是0,产生进位,所以单独输出1.最后的运算结果就是 100900000990000000000000000。
然后小数与小数进行高精度加法的时候,第一点就是将判断符号,然后将字符串根据小数点拆分成小数部分和整数部分,不存在的则用字符串"0"填充,然后利用上述的算法步骤进行计算,小数计算之后,是将后面补零,比如0.12 + 0.123变化为0.120 + 0.123,然后计算完小数之后则继续计算整数部分
代码:(整数 + 整数)
#include <stdio.h> #include <string.h> char *strrev(char str[]){ int len=strlen(str); for(int i=0;i<len/2;i++){ char ch=str[i]; str[i]=str[len-i-1]; str[len-i-1]=ch; } char *p=str; return p; } int main(){ char str[3][1005]={'