ai2738浮点数相加(Tuesday)

本文介绍了一个解决实数加法问题的C语言程序实现,该程序能够处理两个具有特定格式的小数,并输出它们的精确和。通过字符串操作和数组处理来完成加法运算。

2738:实数加法

总时间限制: 1000ms

内存限制: 65536kB

描述

求两个实数相加的和。

题目中输入输出里出现的浮点数都有如下的形式:
P1P2...Pi.Q1Q2...Qj。对于整数部分,P1P2...Pi是一个非负整数且当整数部分不为0时,P1不等于0;对于小数部分,Qj不等于0。

输入

2行,每行是一个加数。每个加数的长度不超过100。

输出

一行,即相应的和。输出保证一定是一个小数部分不为0的实数。

样例输入

0.111111111111111111111111111111
0.111111111111111111111111111111

样例输出

0.222222222222222222222222222222

已accept的代码

#include<stdio.h>
#include<string.h>
#define MAX_LEN 100+10
int main(){
	int ft1[MAX_LEN],ft2[MAX_LEN],n1[MAX_LEN],n2[MAX_LEN],i=0,j=0,k,ilen1,ilen2,flen1,flen2;
    char line1[MAX_LEN],line2[MAX_LEN],num1[MAX_LEN],num2[MAX_LEN],flt1[MAX_LEN],flt2[MAX_LEN];
    memset(ft1,0,sizeof(ft1));
    memset(ft2,0,sizeof(ft2));
    memset(n1,0,sizeof(n1));
    memset(n2,0,sizeof(n2));
    memset(flt1,0,sizeof(flt1));
    memset(flt2,0,sizeof(flt2));
    memset(num1,0,sizeof(num1));
    memset(num2,0,sizeof(num2));
	scanf("%s",line1);
    scanf("%s",line2);
	sscanf(line1,"%[^.].%s",num1,flt1);
	sscanf(line2,"%[^.].%s",num2,flt2);
    ilen1=strlen(num1);
    ilen2=strlen(num2);
    flen1=strlen(flt1);
    flen2=strlen(flt2);
    for(j=0,i=ilen1-1;i>=0;j++,i--){
    	n1[j]=num1[i]-'0';
    }
    for(j=0,i=ilen2-1;i>=0;j++,i--){
    	n2[j]=num2[i]-'0';
    }
    for(i=0;i<flen1;i++){
    	ft1[i]=flt1[i]-'0';
    }
    for(i=0;i<flen2;i++){
    	ft2[i]=flt2[i]-'0';
    }
    
    
    flen1=flen1>flen2?flen1:flen2;
    for(i=flen1-1;i>0;i--){
        ft1[i]+=ft2[i];
        ft1[i-1]+=ft1[i]/10;
        ft1[i]%=10;
    }
    ft1[0]+=ft2[0];
    n1[0]+=ft1[0]/10;
    ft1[0]%=10;
    	
    	
    ilen1=ilen1>ilen2?ilen1:ilen2;
    for(i=0;i<ilen1-1;i++){
        n1[i]+=n2[i];
        n1[i+1]+=n1[i]/10;
        n1[i]%=10;
        }
    n1[ilen1-1]+=n2[ilen1-1];
	
	for(i=flen1;ft1[i]==0;i--);
	flen1=i;
	for(i=ilen1;n1[i]==0&&i>0;i--);
	ilen1=i;
    for(i=ilen1;i>=0;i--){
    printf("%d",n1[i]);
    }
    printf(".");
    for(i=0;i<=flen1;i++){
    printf("%d",ft1[i]);
    }
}

debug:这次吸取了上次的教训,数组我直接无脑加十,总不会超时了吧,本以为会一遍过的,没想到卡了两个下午,都是在自己的电脑上可以,就是提交时Runtime error,先是测所有想得到的边界条件,后来怀疑是gets()对stdin的EOF识别不到位,前前后后不算小的改动,光是重写都有三遍,尝试用不同思路,不同函数,看着别的同学都写完下一个作业开始碎觉了,心累无爱,最后终于在一个同学的帮助下,发现只要删掉return 1;这一行就Accept了,我还试了试以前的一个版本果然删掉return后万事大吉,那感觉,太酸爽了。

### 浮点数相加的精度问题 在计算机科学中,浮点数表示法用于近似实数值。然而,由于二进制系统的固有限制,某些十进制分数无法精确表示为二进制浮点数。这导致了浮点数运算中的舍入误差。 #### 例子展示 考虑两个简单的浮点数相加操作: ```python >>> a = 2.01 >>> b = 3.02 >>> result = a + b >>> print(result) 5.029999999999999 ``` 上述代码展示了当 `a` `b` 进行相加时产生的微小偏差[^2]。 为了处理这种情况并获得更准确的结果,有几种方法可供选择。 ### 解决方案一:使用 `decimal.Decimal` Python 提供了一个名为 `Decimal` 的类来执行高精度算术运算。通过这种方式可以避免大多数常见的浮点数陷阱。 ```python from decimal import Decimal, getcontext getcontext().prec = 6 # 设置精度位数 result_decimal = Decimal('2.01') + Decimal('3.02') print(float(result_decimal)) # 转换回浮点数显示 ``` 这种方法能够提供更高的准确性,特别是在金融应用其他需要严格控制四舍五入行为的情况下[^3]。 ### 解决方案二:调整算法逻辑 另一种策略是在可能的情况下重新设计程序逻辑,使得大部分计算可以在整数范围内完成,最后再将结果转换成所需的浮点形式。例如,在累加多个相同的分量之前先做乘法运算。 ```python # 计算 1/3 + 1/3 + 1/3 total_parts = (1 + 1 + 1) * 1.0 / 3.0 print(total_parts) # 输出 1.0 ``` 此技巧有助于减少累积错误的影响,并提高最终输出的质量[^1]。 ### 总结 虽然浮点数运算是现代编程不可或缺的一部分,但在涉及金钱交易或其他敏感数据的应用场合下务必小心谨慎对待其潜在缺陷。利用内置库函数如 `Decimal` 或者巧妙改变原有算法结构都是有效应对措施之一。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值