c++高精度算法之高精加

初识高精度

高精度算法就是模拟手工计算,通过字符串来存储范围超过int数据范围的数字。

优点可实现超级计算易理解
缺点遇多次运算,易超时细节繁多(个人感觉有点费手)

那话不多说,步入正题吧。

高精加

我们先看图:

                                         1  2  3  4  5  6  7  8  9  0

                               +        9  9  9  9  9  9  9  9  9  9

                     ---------------------------------------------------

                                                        

首先,我们加法的手工计算是从右往左,用字符串就是从size()-1到0;

然后,我们就可以开始加了:

                                         1  2  3  4  5  6  7  8  9  0

                               +        9  9  9  9  9  9  9  9  9  9

                     ---------------------------------------------------

                                                                             9

第size()-1位相加,我们可以得到如下代码:

string jia(string s1,string s2)
{
   int i=s1.size()-1,j=s2.size()-1;
   char c;
   string ans="";
   c=(s1[i]-'0')+(s2[j]-'0')+'0';
   ans+=c;
}

因为是字符相加,所以要减去字符0,最后也不要忘了加上字符0;这里定义了一个字符c来储存每一位的结果,字符串ans来储存整个的结果。

从第size()-1一直加到0,我们就可以添加一个while循环:

string jia(string s1,string s2)
{
	int i=s1.size()-1,j=s2.size()-1;
	char c;
	string ans="";
	while(i>=0&&j>=0)
	{
		c=(s1[i]-'0')+(s2[j]-'0')+'0';
		ans+=c;
		i--;
		j--;
	}
} 

如上,我们就完成了没有进位且两个数字位数相同的高精加。如果需要进位,又该怎么办呢?

没关系,我们继续看图:

                                         1  2  3  4  5  6  7  8  9  0

                               +        9  9  9  9  9  9  9  9  9  9

                     ---------------------------------------1--1----------

                                                                     8  8  9

不难发现,进位其实就是相加的结果+进位mod10。而进多少,则是相加的结果+进位/10。

因此,我们就可以加上进位了:

string jia(string s1,string s2)
{
	int i=s1.size()-1,j=s2.size()-1;
	int jinwei=0;
	char c;
	string ans="";
	while(i>=0&&j>=0)
	{
		c=((s1[i]-'0')+(s2[j]-'0')+jinwei)%10+'0';
		jinwei=((s1[i]-'0')+(s2[j]-'0')+jinwei)/10;
		ans+=c;
		i--;
		j--;
	}
} 

这时候,就差一个问题了。便是实现不同位数数字相加。

我们便可以在后面加上两个循环:

string jia(string s1,string s2)
{
	int i=s1.size()-1,j=s2.size()-1;
	int jinwei=0;
	char c;
	string ans="";
	while(i>=0&&j>=0)
	{
		c=((s1[i]-'0')+(s2[j]-'0')+jinwei)%10+'0';
		jinwei=((s1[i]-'0')+(s2[j]-'0')+jinwei)/10;
		ans+=c;
		i--;
		j--;
	}
	while(i>=0)
	{
		c=((s1[i]-'0')+jinwei)%10+'0';
		jinwei=((s1[i]-'0')+jinwei)/10;
		ans+=c;
		i--;
	}
	while(j>=0)
	{
		c=((s2[j]-'0')+jinwei)%10+'0';
		jinwei=((s2[j]-'0')+jinwei)/10;
		ans+=c;
		j--;
	}
} 

你以为结束了?NO!看图:

                  9    9    9

               + 8    8    8

--------------1----1---1---------------------

            1    8    8    7

加到最后一位时,如果还需进位,则还要加上一个字符1;别忘了,我们是倒着加的,最后还要翻转过来,去掉多余的前导0。

完整代码

string jia(string s1,string s2)
{
	int i=s1.size()-1,j=s2.size()-1;
	int jinwei=0;
	string s="",ans="";
	char c;
	while(i>=0&&j>=0)
	{
		c=(s1[i]-'0'+s2[j]-'0'+jinwei)%10+'0';
		jinwei=(s1[i]-'0'+s2[j]-'0'+jinwei)/10;
		s+=c;
		i--;
		j--;
	}
	while(i>=0)
	{
		c=(s1[i]-'0'+jinwei)%10+'0';
		jinwei=(s1[i]-'0'+jinwei)/10;
		s+=c;
		i--;
	}
	while(j>=0)
	{
		c=(s2[j]-'0'+jinwei)%10+'0';
		jinwei=(s2[j]-'0'+jinwei)/10;
		s+=c;
		j--;
	}
	if(jinwei==1)
	{
		s+=1+'0';
	}
    int tag=0;
	for(i=s.size()-1;i>=0;i--)
	{
        if(tag==0&&s[i]=='0')
        {
            continue;
        }
		ans+=s[i];
        tag=1;
	}
	return ans;
}

好了,本文章到这里就结束了,再见。

(如以上代码有错误,请指出,万分感谢!)

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
以下是C++实现车床椭圆插补高精算法的示例代码: ```cpp #include <iostream> #include <cmath> using namespace std; const double PI = 3.14159265358979323846; // 计算椭圆上等分点的坐标,支持高精度计算 void CalculateEllipsePoints(double cx, double cy, double a, double b, double angle, int n, double* x, double* y) { double theta = 2 * PI / n; // 等分角度 double cosAngle = cos(angle); double sinAngle = sin(angle); for (int i = 0; i < n; i++) { double alpha = i * theta; double cosAlpha = cos(alpha); double sinAlpha = sin(alpha); double px = a * cosAlpha * cosAngle - b * sinAlpha * sinAngle + cx; double py = a * cosAlpha * sinAngle + b * sinAlpha * cosAngle + cy; x[i] = round(px); // 四舍五入保留整数部分 y[i] = round(py); } } int main() { double cx = 100; // 椭圆中心点坐标 double cy = 100; double a = 50; // 长轴和短轴长度 double b = 30; double angle = PI / 4; // 旋转角度 int n = 36; // 等分点个数 double* x = new double[n]; // 存储等分点的坐标 double* y = new double[n]; CalculateEllipsePoints(cx, cy, a, b, angle, n, x, y); // 输出等分点的坐标 for (int i = 0; i < n; i++) { cout << "x[" << i << "] = " << x[i] << ", y[" << i << "] = " << y[i] << endl; } delete[] x; delete[] y; return 0; } ``` 该示例代码在计算椭圆上等分点的坐标时,采用了高精度计算的方式,即通过四舍五入将计算结果保留整数部分,从而提高计算精度。具体实现中,与普通算法的不同之处在于,将计算得到的浮点数坐标值四舍五入后,存储在x和y数组中。这样可以保证在计算机的有限精度下,计算结果能够尽可能地接近实际值。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值