当前位置: 首页 > web >正文

高精度加减

1、高精度加法

主要有以下几步:

  1. 输入处理:使用字符串来存储大整数,避免数值范围限制。
  2. 对齐数字:确保两个数字的数位对齐(前面补零)。
  3. 逐位相加:从最低位开始,逐位相加并处理进位。
  4. 最高进位:在最后检查是否有剩余进位。
  5. 结果反转:因为是从低位开始计算,所以最后需要反转字符串。
int a[N], b[N], c[N];  // 方便进位和数位对齐的逆序整型数组
void addBigNumber(string num1, string num2) {// 计算长度int len1 = num1.length(), len2 = num2.length();// 逆序存储到整型数组for(int i = 0; i < len1; i++) a[i] = num1[len1 - 1 - i] - '0';for(int i = 0; i < len2; i++) b[i] = num2[len2 - 1 - i] - '0';// 循环较长数字的位数int len = max(len1, len2);for(int i = 0; i < len; i++) {c[i] += a[i] + b[i];  // 这一位加上两个数的和c[i + 1] += c[i] / 10;  // 这一位超过10进位到下一位c[i] %= 10;  // 这一位超过10要取余} if(c[len]) len++;  // 如果最高位有进位,长度加1for(int i = len - 1; i >= 0; i--) cout << c[i];  // 逆序输出
}
string addBigNumber(string num1, string num2) {// 分别计算两数的最后一位数下标,并初始化进位int i = num1.size() - 1, j = num2.size() - 1, carry = 0;string res;// 只要有数字没加完 或 有进位没处理就继续运算while(i >= 0 || j >= 0 || carry) {int sum = carry;  // 这一位的结果先赋为进位值if(i >= 0) sum += num1[i--] - '0';  // 第一个数没加完就加if(j >= 0) sum += num2[j--] - '0';  // 第二个数没加完就加carry = sum / 10;  // 计算是否有进位res += sum % 10 + '0';  // 对10取余处理进位}reverse(res.begin(), res.end());  // 翻转答案return res;
}
string addBigNumber(string num1, string num2) {// 确保 num1 是较长的数字if(num1.length() < num2.length()) swap(num1, num2);string res;  // 最终答案int carry = 0;  // 进位,初始为0int len1 = num1.length(), len2 = num2.length();  // 长度// 从最低位开始相加,加到较长数字的位数for(int i = 0; i < len1; i++) { // 较长数字正常 -'0' 转化为 int 即可int digit1 = num1[len1 - 1 - i] - '0';// 如果超出了较短数字的位数,默认补0即可int digit2 = i < len2 ? num2[len2 - 1 - i] - '0' : 0;// 这一位的总和等于:两数相加并加上进位int sum = digit1 + digit2 + carry;carry = sum / 10;  // 下一位的进位等于这一位总和对10整除res += sum % 10 + '0';  // 最终这一位的结果要对10取余,并且恢复为字符串}// 如果还有进位,说明最高位也发生了进位,超出了原有最长位数,要单独处理if(carry) res += carry + '0'; // 由于前面是从最低位开始加的,这里要对结果进行翻转reverse(res.begin(), res.end());return res;
}

2、高精度减法

主要有以下几步

  1. 比较大小:比较两个数字字符串的大小,确定减数和被减数,并标记负号。
  2. 对齐数字:确保两个数字的数位对齐(前面补零)。
  3. 逐位相减:从最低位开始,逐位相减并处理借位。
  4. 结果处理:移除结果中的前导零,判断是否添加负号。
  5. 结果反转:因为是从低位开始计算,所以最后需要反转字符串。
string subBigNumber(string num1, string num2) {char op = ' ';  // 记录符号// 确保 num1 > num2,否则记录负号并交换if(num1.size() < num2.size() || num1.size() == num2.size() && num1 < num2) {op = '-';swap(num1, num2);}string res;  // 最终答案int borrow = 0;  // 借位,初始为0int len1 = num1.size(), len2 = num2.size();  // 长度// 运算按较长数字的长度for(int i = 0; i < len1; i++) {// 较长数字正常 -'0' 转化为 int 即可int digit1 = num1[len1 - 1 - i] - '0';// 如果超出了较短数字的位数,默认补0即可int digit2 = i < len2 ? num2[len2 - 1 - i] - '0' : 0;// 这一位的结果等于:两数相减并减去借位int dif = digit1 - digit2 - borrow;// 判断是否需要借位if(dif < 0) borrow = 1;else borrow = 0;// 这一位的结果先加10再取余,可以处理需要借位的负数,并 + '0' 转字符res += (dif + 10) % 10 + '0';}// 处理前导0,但注意保留一个,因为结果可能为0while(res.size() > 1 && res.back() == '0') res.pop_back();// 处理负号if(op == '-') res += '-';// 翻转字符串reverse(res.begin(), res.end());return res;
}
http://www.xdnf.cn/news/5247.html

相关文章:

  • 普通IT的股票交易成长史--股价起伏的真相-缺口(2)
  • 2010-2020年 分省工业品月度产量数据-社科数据
  • 分析AMD业绩突飞猛进的原因
  • [ctfshow web入门] web71
  • SpringBoot项目容器化进行部署,meven的docker插件远程构建docker镜像
  • gvm安装go报错ERROR: Failed to use installed version
  • Linux进程信号的捕捉处理方式
  • 【Java学习】枚举(匿名类详解)
  • 基于大模型的新型隐球菌脑膜炎智能诊疗全流程系统设计与实现的技术方案文档
  • CD37.【C++ Dev】string类的模拟实现(上)
  • fastmcp: 更好用的 MCP Python 框架
  • SlideLoss与FocalLoss在YOLOv8分类损失中的应用及性能分析
  • 指针运算典型例题解析
  • IOC和Bean
  • 【读书笔记】《编码:隐匿在计算机软硬件背后的语言》01 逻辑与开关
  • Android方法耗时监控插件开发
  • Java 基础面试题
  • 自定义类型-结构体(一)
  • 【Rust】枚举和模式匹配
  • 2025年数维杯赛题C题专家 组委会C题专家疑集锦
  • 5.8线性动态规划2
  • SpringMVC-执行流程
  • 40、C# 数组、链表、哈希、队列、栈数据结构的特点、优点和缺点
  • AI:生成对抗网络(GAN)
  • 【Vue】vuex的getters mapState mapGetters mapMutations mapActions的使用
  • yocto的大致工作流程
  • CSS渲染性能优化
  • MySQL进阶篇2_SQL优化、锁
  • 探索 JWT(JSON Web Token):原理、结构与实践应用对比
  • RK3568-OpenHarmony(1) : OpenHarmony 5.1的编译