POJ1001(变态高精度)

POJ1001

人生如戏,mgb

这题不难(然而弱码了3个小时。。。),但是个人人为还是很能提高码代码的能力的

简单来讲就是一题高精度小数幂运算,判断条件比较多(注意0的幂的情况)

弱的做法比较直白,一开始就直接把前面后面的0去除掉,然后记录小数点后的位数,把小数高精度乘变成整数的高精度乘,最后把小数点点进去就好了

这里顺便优化一下用了快速幂,中间因为没有写好快速幂出了一点问题,感觉分过程写代码真的很重要,然后高精度的优化弱就不写了,哪天再碰到高精度的弱就写优化的高精度(毕竟都没有写过),顺便贴一下代码

#include <iostream>
#include <string>

using namespace std;

string mul(string s1, string s2);
void Exponentiation(string s, int n);

int main()
{
    string s;
    int n;

    while (cin >> s >> n)
        Exponentiation(s, n);

    return 0;
}

string mul(string s1, string s2)
{
    if (s1.empty() || s2.empty())
        return "";      //由于程序里0是不表示的,然后在下面s1.size()+s2.size()-1会出错,于是直接退出
    int a[1000] = { 0 };
    int b[1000] = { 0 }, c[1000] = { 0 };
    for (int i = s1.size() - 1; i >= 0; i--)
        b[s1.size() - 1 - i] = s1[i] - '0';
    for (int i = s2.size() - 1; i >= 0; i--)
        c[s2.size() - 1 - i] = s2[i] - '0';

    for (int i = 0; i < s1.size(); i++)
        for (int j = 0; j < s2.size(); j++) {
            a[i + j] += b[i] * c[j];
        }
    int i = 0;

    while (i < (s1.size() + s2.size() - 1) || a[i]) {
        a[i + 1] += a[i] / 10;
        a[i] = a[i] % 10;
        i++;
    }
    i--;

    string s;
    while (i >= 0) {
        s = s + (char)(a[i] + '0');
        i--;
    }

    return s;
}

void Exponentiation(string s, int n)
{
    string ss = "1";
    int pos = s.find('.');
    int m = 0;
    if (pos == string::npos) {
        for (int i = 0; i < s.size(); i++)
            m = (s[i] - '0') + m * 10;
        pos = 0;
    }
    else {
        while (s[s.size() - 1] == '0')
            s.erase(s.size() - 1, 1);
        for (int i = 0; i < pos; i++)
            m = (s[i] - '0') + m * 10;
        for (int i = pos + 1; i < s.size(); i++)
            m = (s[i] - '0') + m * 10;
        pos = s.size() - pos - 1;
    }
    pos *= n;   //pos 即最后会有几位小数

    s.clear();
    while (m) {
        s = (char)(m % 10 + '0') + s;
        m = m / 10;
    }           //s 即小数转换后的整数

    while (n != 1) {        //快速幂
        if (n % 2 == 0)
            s = mul(s, s);
        else {
            ss = mul(ss, s);
            s = mul(s, s);
        }
        n = n / 2;
    }
    s = mul(s, ss);
    if (s.empty())
        s = "0";    //结果为0的话s会是空,所以加一下

    int size = s.size();
    if (pos == 0)
        cout << s;
    else if (size < pos) {
        cout << '.';
        for (int i = 0; i < pos - size; i++)
            cout << '0';
        cout << s;
    }
    else {
        for (int i = 0; i < size; i++)
            if (i == size - pos)
                cout << '.' << s[i];
            else
                cout << s[i];
    }
    cout << endl;

    return;
}

顺便吐个槽,POJ上面第一题a+b,第二题难度就跳成这个了,真是操蛋

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值