POJ 1001 Exponentiation 求高精度幂 - 追着光梦游

POJ 1001 Exponentiation 求高精度幂

ACM解题报告 2017-08-07

Exponentiation

Description
Problems involving the computation of exact values of very large magnitude and precision are common. For example, the computation of the national debt is a taxing experience for many computer systems. This problem requires that you write a program to compute the exact value of Rn where R is a real number ( 0.0 < R < 99.999 ) and n is an integer such that 0 < n <= 25.

Input
The input will consist of a set of pairs of values for R and n. The R value will occupy columns 1 through 6, and the n value will be in columns 8 and 9.
Output
The output will consist of one line for each line of input giving the exact value of R^n. Leading zeros should be suppressed in the output. Insignificant trailing zeros must not be printed. Don't print the decimal point if the result is an integer.
Sample Input
95.123 12
0.4321 20
5.1234 15
6.7592 9
98.999 10
1.0100 12
Sample Output
548815620517731830194541.899025343415715973535967221869852721
.00000005148554641076956121994511276767154838481760200726351203835429763013462401
43992025569.928573701266488041146654993318703707511666295476720493953024
29448126.764121021618164430206909037173276672
90429072743629540498.107596019456651774561044010001
1.126825030131969720661201
题目大意
这道题主要考察的是高精度的乘法的计算而且是带小数点的运算。重点是要模拟出手算乘法的计算过程,这样才能达到题目的要求。
主要思路:
输入的时候将小数转换为整数,根据大整数计算原理将概数计算得到结果,这种类型的关键就是输入的时候记录小数点的位置,然后分居计算的次方求出输出时小数点应该输出的位置,其基础还是基本的大数加减乘除。

#include<iostream>  
#include<cstring>  
using namespace std;  
int main()  
{  
    string r;  
    int n,weizhi;  
    const int R_LEN=160;  
    short result[R_LEN],jieguo[R_LEN],chengshu[6];  
    while(cin>>r>>n)  
    {  
        int len=0;  
        for(int i=0;i<R_LEN;++i) jieguo[i]=result[i]=0;//将变量初始化为0  
        for(int i=0;i<6;++i) chengshu[i]=0;  
        weizhi = 0;  
        size_t pos = r.find(".");  //没找到.,返回npos 
        if(pos != string::npos) //size_t是一种类型,string.find()函数,这一段是擦好找字符串r中是否含有子串‘.’不太懂 
        weizhi=(5-pos)*n;
        for(int i=5,j=0;i>=0;--i)  
        {  
            if(r[i]!='.')  
            {  
                jieguo[j]=result[j]=chengshu[j]=r[i]-'0';//提取数位  
                ++j;  
            }  
        }  
        while(n>=2)//指数大于等于2的时候计算,否则就是直接去除多余0输出了  
        {  
            --n;  
            for(int i=0;i<R_LEN;++i) result[i]=0;  
            for(int i=0;i<5;++i)//乘数数位循环  
            {  
                int c;  
                for(int j=0;j<R_LEN;++j)//被乘数数位循环  
                {  
                    if(chengshu[i]==0) break;  
                    c=chengshu[i]*jieguo[j];  
                    result[i+j]+=c;  
                    for(int t=i+j;result[t]>9;++t)//处理进位  
                    {  
                        result[t+1]+=result[t]/10;  
                        result[t]=result[t]%10;  
                    }  
                }  
            }  
            for(int i=0;i<R_LEN;++i) jieguo[i]=result[i];//结果转存,以便下一次循环计算  
        }  
        int firstindex=-1;  
        for(int i=R_LEN-1;i>=weizhi;--i)//从右往左查找小数点前第一个不为0的数  
        {  
            if(result[i]>0)  
            {  
                firstindex=i;  
                break;  
            }  
        }  
        int lastindex=-1;  
        for(int i=0;i<weizhi;++i)//从左往右查找小数点前第一个不为0的数  
        {  
            if(result[i]>0)  
            {  
                lastindex=i;  
                break;  
            }  
        }  
        if(firstindex!=-1)//输出小数点前的部分  
        {  
            while(firstindex>=weizhi)  
            {  
                cout<<result[firstindex];  
                --firstindex;  
            }  
        }  
        if(lastindex!=-1)//如果有小数部分,先输出小数点,再输出小数部分  
        {  
            cout<<'.';  
            --weizhi;  
            while(weizhi>=lastindex)  
            {  
                cout<<result[weizhi];  
                --weizhi;  
            }  
        }  
        cout<<endl;  
    }  
}      

本文由 guopengli 创作,采用 知识共享署名 3.0,可自由转载、引用,但需署名作者且注明文章出处。
  • 浏览次数: 468
  • 还不快抢沙发

    添加新评论