【C++算法】——高精度(加,减,乘,除)

前言

高精度算法就是为了去解决一些比较大的数,这些数大到long long都存不下。,这里的主要思想就是用字符串来存。

下面的内容有很多用到c++的容器,不明白的可以先去学习stl。

一  高精度加法

首先第一步就是去模拟我们自己写的加法,,从我们自己写的加法上面来看,第一它是从个位开始加,如果大于10就会产生进位,这个进位要加到下一位去。

我们写加法是从个位开始,但是用代码去写,就需要倒过来,因为个位是不好去进位的,如果用个位去进位,那么就会导致整块的移动,这样效率就会很低了

图一是我们自己算,图二则是我们用代码去实现的过程

所以有了上面的准备,就可以写出下面代码

#include<iostream>
#include<vector>
using namespace std;vector<int> add(const vector<int>& A, const vector<int>& B)//加法函数,这里传引用是为了提高效率
{int t = 0;vector<int>C;//用来返回for (int i = 0; i < A.size(); i++)//因为之前已经逆序了,所以这里直接从0开始遍历{t +=A[i];//首先把最长的数的最后一位加上if (i < B.size()) t += B[i];//因为B短,所以我们需要去判断B是否已经结束C.push_back(t % 10);//最后我们是插入t%10,如果大于就进位,小于就不进位t /= 10;//这里相当于是进位的过程}if (t) C.push_back(1);//还有A结束的时候,可能还有一个进位没有处理,这里把它尾插return C;
}int main()
{string a, b;vector<int>A, B, C;cin >> a >> b;for (int i = a.size()-1; i >=0; i--)//逆置{A.push_back(a[i] - '0');//转换}for (int i = b.size() - 1; i >= 0; i--){B.push_back(b[i] - '0');}if (A.size() > B.size()) C = add(A, B);//这里是调整A,B那个数长,长的放上面,比较好操作else C = add(B, A);for (int i = C.size()-1; i >= 0; i--)//因为是逆序相加的,所以这里需要再逆序倒过来输出{cout << C[i];}cout << endl;return 0;}

 主函数里面的处理还是比较简单的,关键在于两个数的相加

二  高精度减法

其实减法也差不多,一样的反转,但是不同的就是我们需要用一个数去存一个借位,而不是进位,因为一个数减另外一个数不够我们就需要去借位,这样才能够减,第二就是我们在进行减法的时候需要的是去判断两个数的大小哪个更加大,而不是和加法一样去判断长度。

一样的,下面看代码理解

bool cmp(vector<int>& A, vector<int>& B)//比较函数
{if (A.size() != B.size())return A.size() > B.size();for (int i = A.size() - 1; i >= 0; i--){if (A[i] != B[i])return A[i] > B[i];}return true;
}vector<int> sub(vector<int>& A, vector<int>& B)//减法函数
{int t = 0;vector<int>C;for (int i = 0; i < A.size(); i++){t = A[i] - t;//一开始没有借位if (i < B.size()) t -= B[i];C.push_back((t + 10) % 10);//这个是如果t>0,说明没有借位,如果小于0,就借位了//这里+10是先算它进位,然后再%10,如果没有进位,那就是它本身//如果进位了,那我们插入的就是10-t;if (t < 0) t = 1;//借位等于1,下次循环,A[i]就需要-1else t = 0;}while (C.size() > 1 && C.back() == 0)C.pop_back();//这里需要去掉前导零return C;
}
int main()
{string a, b;vector<int>A, B, C;cin >> a >> b;for (int i = a.size()-1; i >=0; i--)//这里操作和加法是一样的{A.push_back(a[i] - '0');}for (int i = b.size() - 1; i >= 0; i--){B.push_back(b[i] - '0');}if (cmp(A, B)) C = sub(A, B);//这是判断大小else C = sub(B, A), cout << '-';//如果A小于B,那么我们可以换成-(B-A)//这里要多输出一个符号for (int i = C.size()-1; i >= 0; i--){cout << C[i];}cout << endl;return 0;}

三  高精度乘法

关于高精度乘法来说,就没有减法那么多处理了,甚至比加法还简单一点,这里的乘法是一个多位数和一个低位数的相乘

vector<int> mul(vector<int>& A, int b)
{int t = 0;vector<int>C;for (int i = 0; i < A.size(); i++){t += A[i] * b;//t是进位C.push_back(t % 10);t /= 10;}if (t) C.push_back(t);//最后一位有进位就插入while (C.size() > 1 && C.back() == 0) C.pop_back();//处理前导零return C;
}int main()
{string a;//这里直接正常操作就行int b;vector<int>A, C;cin >> a >> b;for (int i = a.size()-1; i >=0; i--){A.push_back(a[i] - '0');}C = mul(A, b);for (int i = C.size()-1; i >= 0; i--){cout << C[i];}cout << endl;return 0;}

 

四  高精度除法

这里的除法和其他的又有点不一样,但是不一样的不会很多,第一就是我们除一个数可能除不尽,所以这里需要一个余数去存。

vector<int> div(vector<int>& A, int b,int &r)
{r = 0;vector<int>C;for (int i = A.size()-1; i >= 0; i--)//这里和其他的不一样,因为我们除法只能从个位开始除{r = r * 10 + A[i];//这里表示余数和下一个数的相加C.push_back(r / b);r %= b;}reverse(C.begin(), C.end());//这里因为上面的操作把C变为正序了,所以这里要反过来,因为//后面打印是按逆序打印,这里就和上面同一了while (C.size() > 1 && C.back() == 0)C.pop_back();//去前导零return C;
}int main()
{string a;int b;vector<int>A, C;cin >> a >> b;for (int i = a.size()-1; i >=0; i--)//这里操作和上面差不多{A.push_back(a[i] - '0');}int r;C = div(A, b,r);for (int i = C.size()-1; i >= 0; i--){cout << C[i];}cout << endl;cout << r;return 0;}

五 练习

a-b

这里直接用上面的代码就行

 

#include <iostream>
#include <vector>using namespace std;
bool cmp(vector<int>& A, vector<int>& B)//比较函数
{if (A.size() != B.size())return A.size() > B.size();for (int i = A.size() - 1; i >= 0; i--){if (A[i] != B[i])return A[i] > B[i];}return true;
}vector<int> sub(vector<int>& A, vector<int>& B)//减法函数
{int t = 0;vector<int>C;for (int i = 0; i < A.size(); i++){t = A[i] - t;//一开始没有借位if (i < B.size()) t -= B[i];C.push_back((t + 10) % 10);//这个是如果t>0,说明没有借位,如果小于0,就借位了//这里+10是先算它进位,然后再%10,如果没有进位,那就是它本身//如果进位了,那我们插入的就是10-t;if (t < 0) t = 1;//借位等于1,下次循环,A[i]就需要-1else t = 0;}while (C.size() > 1 && C.back() == 0)C.pop_back();//这里需要去掉前导零return C;
}
int main()
{string a, b;vector<int>A, B, C;cin >> a >> b;for (int i = a.size()-1; i >=0; i--)//这里操作和加法是一样的{A.push_back(a[i] - '0');}for (int i = b.size() - 1; i >= 0; i--){B.push_back(b[i] - '0');}if (cmp(A, B)) C = sub(A, B);//这是判断大小else C = sub(B, A), cout << '-';//如果A小于B,那么我们可以换成-(B-A)//这里要多输出一个符号for (int i = C.size()-1; i >= 0; i--){cout << C[i];}cout << endl;return 0;}

a+b

#define _CRT_SECURE_NO_WARNINGS 1
#include<iostream>
#include<vector>
using namespace std;
const int N = 1e6 + 10;
vector<int>add(vector<int>& A, vector<int>& B)
{vector<int>C;int t = 0;for (int i = 0; i < A.size() || i < B.size(); i++){if (i < A.size()) t += A[i];if (i < B.size()) t += B[i];C.push_back(t % 10);t /= 10;}if (t)C.push_back(1);return C;}
int main()
{string a, b;cin >> a >> b;vector<int>A, B;for (int i = a.size() - 1; i >= 0; i--) A.push_back(a[i] - '0');for (int i = b.size() - 1; i >= 0; i--) B.push_back(b[i] - '0');vector<int>C;C = add(A, B);for (int i = C.size() - 1; i >= 0; i--){cout << C[i];}return 0;
}

 

六  总结

以上高精度算法,加法和乘法比较简单,除法和减法需要一点细节理解

加法没有去前导零的操作,其他都有,以上就是高精度的全部内容了,希望对你有所帮助

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/357808.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

基于TCAD与紧凑模型结合方法探究陷阱对AlGaN/GaN HEMTs功率附加效率及线性度的影响

来源&#xff1a;Investigation of Traps Impact on PAE and Linearity of AlGaN/GaN HEMTs Relying on a Combined TCAD–Compact Model Approach&#xff08;TED 24年&#xff09; 摘要 本文提出了一种新型建模方法&#xff0c;用于分析GaN HEMTs的微波功率性能。通过结合工…

Python 虚拟环境 requirements.txt 文件生成 ;pipenv导出pip安装文件

搜索关键词: Python 虚拟环境Pipenv requirements.txt 文件生成;Pipenv 导出 pip requirements.txt安装文件 本文基于python版本 >3.9 文章内容有效日期2023年01月开始(因为此方法从这个时间开始是完全ok的) 上述为pipenv的演示版本 使用以下命令可精准生成requirement…

深度学习 --- stanford cs231学习笔记五(训练神经网络的几个重要组成部分之二,数据的预处理)

数据的预处理(Data Preprocessing) 2 Data Preprocessing数据的预处理 数据预处理的几种方法 2&#xff0c;1 数据的零点中心化 数据的零点中心化的目的就是为了把数据的整体分布拉回到原点附近&#xff0c;也就是让数据的整体均值变为0。 ​ 2&#xff0c;2 数据的标准化 数据…

TWM论文阅读笔记

这是ICLR2023的一篇world model论文&#xff0c;用transformer来做世界模型的sequence prediction。文章贡献是transformer-based world model&#xff08;不同于以往的如transdreamer的world model&#xff0c;本文的transformer-based world model在inference 的时候可以丢掉…

【教学类65-01】20240622秘密花园涂色书01(通义万相)(A4横版2张,一大3小 38张纸76份)

背景需求&#xff1a; 用通义万相制作秘密花园涂色书 关键词&#xff08;中文&#xff09;&#xff1a;秘密花园涂色书&#xff0c;简单笔画&#xff0c;卡通&#xff0c;黑白轮廓&#xff0c;未着色&#xff0c;幼儿插图&#xff0c;线条画&#xff0c;没有背景&#xff0c;没…

【计算机网络】已解决:“‘ping‘ 不是内部或外部命令,也不是可运行的程序或批处理文件”报错

文章目录 一、问题分析背景二、可能出错的原因三、错误代码示例四、正确解决方法与示例五、注意事项 已解决“‘ping’ 不是内部或外部命令&#xff0c;也不是可运行的程序或批处理文件”报错 一、问题分析背景 在Windows操作系统中&#xff0c;ping 命令是一个常用的网络诊断…

yii2 ActiveForm使用技巧

持续更新&#xff1a; 1、搜索输入框&#xff1a;form-inline <?php $form ActiveForm::begin([action > [index],method > get,options > [class > form-inline] &#xff08;增加此行代码&#xff09; ]); ?>

python watchdog 配置文件热更新

目录 一、Watchdog示例 二、aiohttp服务配置热更新 在同事的golang代码中学习到了config.json热更新的功能&#xff0c;这里自己也学习了一下python写web服务的时候怎么来实现配置的热更新。主要是利用Watchdog这个第三方python库&#xff0c;来监控文件系统的改变&#xff0…

卧槽,6。套死你猴子,Tomcat访问html页面显示源码?

卧槽&#xff0c;6。Tomcat访问html页面显示源码&#xff1f; 元凶text/explain //踩坑&#xff01;&#xff01;&#xff01;不能用 servletResponse.setContentType("text/explain&#xff0c;否则访问html会看到源码&#xff0c;而不是渲染页面; charsetUTF-8"…

体验了一下AI生产3D模型有感

我的实验路子是想试试能不能帮我建一下实物模型 SO 我选择了一个成都环球中心的网图 但是生成的结果掺不忍睹&#xff0c;但是看demo来看&#xff0c;似乎如果你能给出一张干净的提示图片&#xff0c;他还是能做出一些东西的 这里我延申的思考是这个物体他如果没看过背面&…

骑马与砍杀战团mod制作-基础-军队笔记(一)

骑马与砍杀战团mod制作-基础-军队装备笔记&#xff08;一&#xff09; 资料来源 学习的资料来源&#xff1a; b站【三啸解说】手把手教你做【骑砍】MOD&#xff0c;基础篇&#xff0c;链接为&#xff1a; https://www.bilibili.com/video/BV19x411Q7No?p4&vd_sourcea507…

测试测量-DMM直流精度

测试测量-DMM直流精度 最近去面试&#xff0c;发现了自己许多不足&#xff0c;比如我从未考虑过万用表准或者不准&#xff0c;或者万用表有多准&#xff1f; 在过去的实验室中&#xff0c;常用的DMM有KEYSIGHT 34401A以及 KEITHLEY THD2015&#xff0c;就以这两台为例&#x…

朴素贝叶斯案例

一、朴素贝叶斯算法&#xff1a; 朴素贝叶斯算法&#xff0c;是一种基于贝叶斯定理与特征条件独立假设的分类方法&#xff0c;基于贝叶斯后验概率建立的模型&#xff0c;它用于解决分类问题。朴素&#xff1a;特征条件独立&#xff1b;贝叶斯&#xff1a;基于贝叶斯定理。属于…

07-appium常用操作

一、press_keycode 1&#xff09;方法说明 press_keycode方法是appium的键盘相关函数&#xff0c;可以实现键盘的相关操作&#xff0c;比如返回、按键、音量调节等等。也可以使用keyevent方法&#xff0c;功能与press_keycode方法类似。 常见按键编码&#xff1a;https://www.…

FreeCAD中事务机制实现原理分析

1.基本实现思路 实现一个文件的撤销重做最简单的思想就是&#xff0c;在每个撤销重做节点处保存一份文件的内容&#xff0c;撤销重做时&#xff0c;分别替换对应节点处的文件内容即可。这种做法开销太大&#xff0c;每个节点处都需要保存一份完整的文档内容&#xff0c;每次撤…

Hadoop3:MapReduce中的Partition原理及自定义Partition

一、默认Partition分区配置 以WC案例来进行验证。 1、设置setNumReduceTasks 修改的代码 这行代码&#xff0c;确定了reduceTask的数量&#xff0c;也确定了分区逻辑 在mapper文件中&#xff0c;打上断点 计算分区的代码 这里会对每一个kv进行计算&#xff0c;然后&#…

【JavaEE】Spring Web MVC详解

一.基本概念. 1.什么是Spring Web MVC? 官方链接: https://docs.spring.io/spring-framework/reference/web/webmvc.html Spring Web MVC is the original web framework built on the Servlet API and has been included in the Spring Framework from the very beginning…

浅析MySQL-基础篇01

目录 执行一条select语句&#xff0c;发生了什么&#xff1f; MYSQL执行流程是怎么样的&#xff1f; 第一步&#xff1a;连接器 第二步&#xff1a;查询缓存 第三步&#xff1a;解析SQL 解析器 第四步&#xff1a;执行SQL 预处理器 优化器 执行器 执行一条select语句…

hive on spark 记录

环境&#xff1a; hadoop 2.7.2 spark-without-hadoop 2.4.6 hive 2.3.4 hive-site.xml <property><name>hive.execution.engine</name><value>spark</value> </property> <property><name>spark.yarn.jars</name>&l…

【git1】指令,commit,免密

文章目录 1.常用指令&#xff1a;git branch查看本地分支&#xff0c; -r查看远程分支&#xff0c; -a查看本地和远程&#xff0c;-v查看各分支最后一次提交, -D删除分支2.commit规范&#xff1a;git commit进入vi界面&#xff08;进入前要git config core.editor vim设一下vi模…