POJ#1001_高精度幂

本文介绍了一种使用字符串处理方式来实现大数的幂运算的方法。通过定义几个关键函数,包括大数乘法、求幂、计算小数位数等,解决了实数在大范围内进行精确幂运算的问题,并详细展示了如何格式化输出结果。

题目地址:求高精度幂

题目大意是求,其中实数R的取值范围:;整数n的取值范围:

输出的要求:

如果是小数,如0.123456,则输出.123456;

如果是整数,如123456.000,则输出123456;

如果小数后面有无效的0,要去掉,如123.456000,则输出123.456


我的AC代码:

#include <iostream>
#include <string>
using std::string;

/************************************************
*参数:字符串化的大数a和大数b
*返回值:a和b的乘积
*功能:计算两个大数的乘积
*************************************************/
string Multiplication(string &a, string &b)
{
	int lenab = a.size() + b.size();
	int lena = a.size(), lenb = b.size();

	string c(lenab,'0');
	
	for (int i = lena - 1; i >= 0; --i)
	{
		int j = lenb - 1;
		int k = i + j + 1;
		while (j>=0)
		{
			int n = (a[i] - '0')*(b[j] - '0') + (c[k]-'0');
			c[k] = n % 10+'0';
			c[k-1] = ((c[k-1]-'0')+n / 10+'0');
			--j;
			--k;
		}
	}
	return c;
}

/************************************************
*参数:字符串化的大数a和幂
*返回值:无
*功能:计算大数a的n次幂
*************************************************/
void Power(string &a, int n)//求a的n次幂
{
	--n;
	string b(a);
	while (n--)
	{
		a=Multiplication(a, b);
	}
}

/************************************************
*参数:字符串化的大数a
*返回值:a的小数位数
*功能:计算大数小数点位数,如果没有小数点则返回-1
*************************************************/
int decimalPoint(string &a)
{
	int len = a.size();
	int i = a.find(".");
	if(i>=0)
		return len  - i - 1;
	return -1;
}
/************************************************
*参数:字符串化的a的n次幂结果b,n次幂后的小数点位数m
*返回值:补0的个数
*功能:>0,补0的个数;<=0,不需要补0
*************************************************/
int addZero(string &b, int m)//是否需要在前面补0
{
	int len = b.size();
	return m - len;
}

/************************************************
*参数:字符串化的大数a
*返回值:无
*功能:将带小数点的实数转成大整数
*************************************************/
void Decimal2Int(string &a)
{
	int x, y;
	x = a.find_first_not_of("0.");
	y = a.find(".");
	if (x > y)//比如0.001234,得到"1234"
		a = a.substr(x);
	else//比如1.234
	{
		a = a.substr(0, y) + a.substr(y+1);//得到"1"+"234"="1234"
	}
}

int main()
{
	string a;
	int n;
	int decimal;//记录n次幂后小数位数
	int len;
	int zero;
	while (std::cin >> a >> n)
	{
		decimal = n*decimalPoint(a);//计算次方后的小数位数
		Decimal2Int(a);//去掉小数点
		Power(a, n);//计算n次幂
		a = a.substr(a.find_first_not_of("0"));//去掉前面的0,比如得到0123456,去掉0后为123456
		len = a.size();
		zero = addZero(a, decimal);//是否需要补0
		/*按格式要求输出*/
		if (zero >= 0)
		{
			std::cout << ".";
			while (zero--)
				std::cout << "0";
			int j = a.find_last_not_of("0");//去掉后面的0
			std::cout << a.substr(0, j + 1) << std::endl;
		}
		else
		{
			std::cout << a.substr(0, len - decimal);
				
			int j = a.find_last_not_of("0");
			if (j - len + decimal + 1 > 0)//整数的话就不用输出"."
			{
				std::cout << ".";
				std::cout << a.substr(len - decimal, j - len + decimal + 1) ;
			}
			std::cout <<  std::endl;
		}
	}
	return 0;
}




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值