题解 | #浮点数加法#
浮点数加法
http://www.nowcoder.com/practice/ddec753f446e4ba4944e35378ba635c8
思路:
将给定的两个字符串s1,s2的整数和小数部分分割出来 整数数部分用s1p、s2p保存,小数部分用s1n、s2n保存
处理流程:先处理小数 后处理整数 不可颠倒
总体处理方法:模拟人做数学加减法运算
处理小数部分思路:
思路分析:小数部分从高位开始对齐,低位开始相加,若两字符串长度不同,则长的字符串中比短字符串长度多出来的部分不参与运算,实际上长度字符串中0~短字符串长度-1部分参与运算
定义字符串res1保存最终结果,int型整数c保留进位信息,比较s1n和s2n长度,始终让s1n保留长的字符串,定义字符串t1、t2,t1保留s1n前面s2.length()部分,t2保留剩余部分,数***算从低位开始,用reverse(str.begin(),str.end())方法翻转字符串,再依次逐位相加,最后将res1翻转后的到正确结果。注意点,这时需要留意进位信息c的值,若为1,需要再整数处理时加上
处理整数部分:进位c沿用上面的到的值,思路和处理小数部分几乎一致,但需额外注意以下难点
难点:1.若s1p和s2p的长度不一致(始终保持s1p更长),且在s2p处理结束时会产生进位,则当前处理的值s1p[i]的值需要改变,且下一次处理还需要判断进位信息,若遇到极端情况 一直进位,且长的字符串首位为9,进位后成了10,多出一位,此时等到处理完后需要判断进位c的值,若c为1则需要在逆序序列res2的最后一位拼接字符 '1',最后再翻转字符串
#include <bits/stdc++.h> using namespace std; string s1, s2; string s1n, s1p, s2n, s2p; string dividePos(string str) { int pos; for (int i = 0; i < str.length(); i++) { if (str[i] == '.') { pos = i; break; } } return str.substr(0, pos); } string divideNeg(string str) { int pos; for (int i = 0; i < str.length(); i++) { if (str[i] == '.') { pos = i; break; } } return str.substr(pos + 1, str.length() - 1); } int main() { while (cin >> s1 >> s2) { s1p = dividePos(s1); s1n = divideNeg(s1); s2p = dividePos(s2); s2n = divideNeg(s2); string res1 = ""; string res2 = ""; int c = 0; //处理负数部分 c = 0; string t1, t2; if (s1n.length() < s2n.length()) //保证长的串在前 swap(s1n, s2n); //s1长 s2等长或更短 t1 = s1n.substr(0, s2n.length()); //截取s1与s2等长部分的子串 t2 = s1n.substr(s2n.length(), s1n.length() - s2n.length()); reverse(t1.begin(), t1.end()); reverse(s2n.begin(), s2n.end()); for (int i = 0; i < t1.length(); i++) { c = c + t1[i] - '0' + s2n[i] - '0'; res2 += (c % 10 + '0'); c = c / 10; } reverse(res2.begin(), res2.end()); res2 = res2 + t2; //注意 若负数为高位有进位 则直接加入正数部分 不用额外处理 若先处理正数再处理负数则非常复杂 //处理正数部分 if (s1p.length() < s2p.length()) swap(s1p, s2p); reverse(s1p.begin(), s1p.end()); reverse(s2p.begin(), s2p.end()); for (int i = 0; i < s1p.length(); i++) { if (i < s2p.length()) { c = c + s1p[i] - '0' + s2p[i] - '0'; res1 += (c % 10 + '0'); c = c / 10; } else { if (c == 1) { //若进位为1 需要考虑进位 c = c + s1p[i] - '0'; res1 += (c % 10 + '0'); c = c / 10; } else res1 += s1p[i]; } } if (c) { //处理正数最高位进位 res1 += '1'; } reverse(res1.begin(), res1.end()); //翻转正数序列 回到正常位置 cout << res1 << "." << res2 << endl; } }