标题:一个oj的题,测试数据都对,就是提交错误
只看楼主
花脸
Rank: 8Rank: 8
等 级:蝙蝠侠
威 望:9
帖 子:788
专家分:907
注 册:2017-1-4
结帖率:95.37%
已结贴  问题点数:20 回复次数:12 
一个oj的题,测试数据都对,就是提交错误
A+B Problem IV
时间限制:1000 ms  |  内存限制:65535 KB
难度:3
描述
acmj最近发现在使用计算器计算高精度的大数加法时很不方便,于是他想着能不能写个程序把这个问题给解决了。
输入
包含多组测试数据
每组数据包含两个正数A,B(可能为小数且位数不大于400)
输出
每组输出数据占一行,输出A+B的结果,结果需要是最简的形式。
样例输入
1.9 0.1
0.1 0.9
1.23 2.1
3 4.0
样例输出
2
1
3.33
7


#include <iostream>
using namespace std;

bool flag;//标记是否小数部分向整数部分有进位

//计算整数部分的加法
string add_Int(string s1,string s2)
{
    if(s1.length()<s2.length())
    {
        string t=s1;
        s1=s2;
        s2=t;
    }
    for(int i=s1.length()-1,j=s2.length()-1;i>=0;i--,j--)
    {
        s1[i]=char(s1[i]+(j>=0?s2[j]-'0':0));
        
        if(s1[i]-'0'>=10)
        {
            s1[i]=char((s1[i]-'0')%10+'0');
            if(i)
                s1[i-1]++;
            else
                s1="1"+s1;
        }
    }
    return s1;
}
//计算小数部分的加法
string add_Dec(string s1,string s2)
{
    //如果小数的位数不相同
    if(s1.length()!=s2.length())
    {
        if(s1.length()<s2.length())
        {
            string t=s1;
            s1=s2;
            s2=t;
        }
        for(int i=s2.length()-1,j=s2.length()-1;i>=0;i--,j--)
        {
            s1[i]=char(s1[i]+(j>=0?s2[j]-'0':0));
            
            if(s1[i]-'0'>=10)
            {
                s1[i]=char((s1[i]-'0')%10+'0');
                if(i)
                    s1[i-1]++;
                else
                    flag=true;
            }
        }
    }
    //小数部分位数不同
    if(s1.length()==s2.length())
    {
        for(int i=s1.length()-1,j=s2.length()-1;i>=0;i--,j--)
        {
            s1[i]=char(s1[i]+(j>=0?s2[j]-'0':0));
            
            if(s1[i]-'0'>=10)
            {
                s1[i]=char((s1[i]-'0')%10+'0');
                if(i)
                    s1[i-1]++;
                else
                    flag=true;
            }
        }
    }
    return s1;
}
 
int main()
{
    string s1,s2;
    while(cin>>s1>>s2)
    {
        string s1_Int,s1_Dec,s2_Int,s2_Dec;
        //s1的整数部分,s1的小数部分 ,s2的整数部分,s2的小数部分
        
        int s1_find=s1.find('.');//找到小数点的位置,把整数和小数分开来计算
        if(s1_find!=-1)//如果存在小数点
        {
            for(int i=0;i<s1.find('.');++i)
                s1_Int+=s1[i];
            for(int i=s1.find('.')+1;i<s1.length();++i)
                s1_Dec+=s1[i];
        }
        if(s1_find==-1)//如果不存在小数点
        {
            s1_Int+=s1;
            s1_Dec+="0";
        }
        
        int s2_find=s2.find('.');//s2的小数点的位置
        if(s2_find!=-1)//如果存在小数点
        {
            for(int i=0;i<s2.find('.');++i)
                s2_Int+=s2[i];
            for(int i=s2.find('.')+1;i<s2.length();++i)
                s2_Dec+=s2[i];
        }
        if(s2_find==-1)//如果不存在小数点
        {
            s2_Int+=s2;
            s2_Dec+="0";
        }
        
        flag=false;//默认为false如果有小数部分进位,则值为true
        string t_Dec=add_Dec(s1_Dec,s2_Dec);//先做小数部分的加法
     
        string t_Int_Carry;//小数加法时向正数有进位
        string t_Int;//小数加法向正数没有进位
   
        if(flag)// 如果小数部分向整数部分有进位
            t_Int_Carry=add_Int(add_Int(s1_Int,s2_Int),"1");
        else//小数部分向整数部分没有进位
            t_Int=add_Int(s1_Int,s2_Int);
        
        if(t_Dec=="0")//如果小数部分为零
            if(flag)//小数部通过向整数部分进位 产生的0
                cout<<t_Int_Carry<<endl;
            else//两个数本来都为整数
                cout<<t_Int<<endl;
        else//小数部分不为零
            cout<<t_Int<<"."<<t_Dec<<endl;
    }
    return 0;
}
搜索更多相关主题的帖子: 小数 整数 string int length 
2018-05-23 22:58
lin5161678
Rank: 12Rank: 12Rank: 12
等 级:贵宾
威 望:45
帖 子:1136
专家分:3729
注 册:2011-12-3
得分:10 
简单解析一下
你可以把两个小数 同时乘以 10000.....
转换成两个整数相加
结果在除以 10000.....
转换回去
计算过程 统一成一套
分析这么多不同情况

https://zh.
2018-05-24 00:55
lin5161678
Rank: 12Rank: 12Rank: 12
等 级:贵宾
威 望:45
帖 子:1136
专家分:3729
注 册:2011-12-3
得分:0 
比如输入
10.888888888888888888888888888888 和 00.000011111111111111111111111112
你可以把这两个数字处理为
10888888888888888888888888888888
00000011111111111111111111111112
相加结果
10888900000000000000000000000000
小数点摆回去 去掉无效0
10.8889
完毕


https://zh.
2018-05-24 01:02
花脸
Rank: 8Rank: 8
等 级:蝙蝠侠
威 望:9
帖 子:788
专家分:907
注 册:2017-1-4
得分:0 
回复 3楼 lin5161678
小数点位置不同不好对齐。
2018-05-24 12:35
lin5161678
Rank: 12Rank: 12Rank: 12
等 级:贵宾
威 望:45
帖 子:1136
专家分:3729
注 册:2011-12-3
得分:0 
回复 4楼 花脸
短的数字后面补0而已
很好操作的

https://zh.
2018-05-24 13:39
wmf2014
Rank: 19Rank: 19Rank: 19Rank: 19Rank: 19Rank: 19
等 级:贵宾
威 望:216
帖 子:2039
专家分:11273
注 册:2014-12-6
得分:10 
输入:9.9 0.11
输出:.01
显然结果错误,对你的代码做如下修改后可得到正确结果,但仍然不能AC,应该是有其他逻辑错误,自己好好找吧。
        if(t_Dec=="0")//如果小数部分为零
        {
            if(flag)//小数部通过向整数部分进位 产生的0
                cout<<t_Int_Carry<<endl;
            else//两个数本来都为整数
                cout<<t_Int<<endl;
        }
        else//小数部分不为零
        {
            if(flag)
                cout<<t_Int_Carry<<"."<<t_Dec<<endl;
            else
                cout<<t_Int<<"."<<t_Dec<<endl;
        }

现在不能AC的主要原因是不能输出最简形式,如:9.999999 0.000001 你的代码输出是:10.000000,根据题意应该是10

[此贴子已经被作者于2018-5-24 17:08编辑过]


能编个毛线衣吗?
2018-05-24 16:01
花脸
Rank: 8Rank: 8
等 级:蝙蝠侠
威 望:9
帖 子:788
专家分:907
注 册:2017-1-4
得分:0 
回复 5楼 lin5161678
好的,我试试。
2018-05-24 23:07
花脸
Rank: 8Rank: 8
等 级:蝙蝠侠
威 望:9
帖 子:788
专家分:907
注 册:2017-1-4
得分:0 
回复 6楼 wmf2014
好的 谢谢。
2018-05-24 23:07
花脸
Rank: 8Rank: 8
等 级:蝙蝠侠
威 望:9
帖 子:788
专家分:907
注 册:2017-1-4
得分:0 
回复 6楼 wmf2014
我加了如下代码,能解决您说的9.999999 0.000001 你的代码输出是:10.000000,根据题意应该是10这个问题。
//计算小数部分的加法
string add_Dec(string s1,string s2)
{
    //如果小数的位数不相同
    if(s1.length()!=s2.length())
    {
        if(s1.length()<s2.length())
        {
            string t=s1;
            s1=s2;
            s2=t;
        }
        for(int i=s2.length()-1,j=s2.length()-1;i>=0;i--,j--)
        {
            s1[i]=char(s1[i]+(j>=0?s2[j]-'0':0));
            
            if(s1[i]-'0'>=10)
            {
                s1[i]=char((s1[i]-'0')%10+'0');
                if(i)
                    s1[i-1]++;
                else
                    flag=true;
            }
        }
    }
    //小数部分位数不同
    if(s1.length()==s2.length())
    {
        for(int i=s1.length()-1,j=s2.length()-1;i>=0;i--,j--)
        {
            s1[i]=char(s1[i]+(j>=0?s2[j]-'0':0));
            
            if(s1[i]-'0'>=10)
            {
                s1[i]=char((s1[i]-'0')%10+'0');
                if(i)
                    s1[i-1]++;
                else
                    flag=true;
            }
        }
        bool flag1=true;
        for(int i=s1.length()-1;i>=0;--i)
            if(s1[i]!='0')
            {
                flag1=false;
                break;
            }
        if(flag1)
        {
            s1.clear();
            s1+="0";
        }

    }
   
    return s1;
}
2018-05-24 23:50
wmf2014
Rank: 19Rank: 19Rank: 19Rank: 19Rank: 19Rank: 19
等 级:贵宾
威 望:216
帖 子:2039
专家分:11273
注 册:2014-12-6
得分:0 
我这个代码也不能过,
不能AC的提示为“输出结果不对,看看是不是忘了输出必要的换行或者大小写错误?如果不是,那很可能你的程序逻辑有问题,或者有特殊的数据没有考虑。
我反复分析和测试了,没有格式错误和逻辑错误啊,看你能帮忙分析下原因不,也请各位ACM大佬帮忙分析下,题目位置:http://acm.nyist.
程序代码:
#include <iostream>
#include <string>
using namespace std;

string align(string ,int ,int );

int  main()
{
    int i,j,k;
    string a,b;
    while(cin>>a>>b)
    {
        for(j=0;j<a.length() && a[j]!='.';j++);
        k=a.length() -j;
        for(i=0;i<b.length() && b[i]!='.';i++);
        if(i>j)
            j=i;   
        if(b.length() -i>k)
            k=b.length() -i;   //分别得到整数最大位数j和小数最大位数k
        a=align(a,j,k);
        b=align(b,j,k);        //按位对齐
        for(i=a.length ()-1,j=0;i>=0;i--)
        {
            if(a[i]!='.')
            {//加法运算
                a[i]=a[i]+b[i]+j-'0';
                j=0;
                if(a[i]>'9')
                {
                    j=1;
                    a[i]-=10;
                }
            }
        }
        if(j)
            a='1'+a;  //补进位
        for(i=0;a[i]=='0';i++);                   //消前导0
        for(b="",j=a.length ()-1;a[j]=='0';j--);  //消尾数0
        if(a[j]=='.')j--;                         //整数处理
        for(;i<=j;i++)
            b+=a[i];
        cout<<b<<endl;
    }
    return 0;
}

string align(string s,int ni,int nf)
{//数据位对齐
    int i,j,k;
    for(j=0;j<s.length()&&s[j]!='.';j++);
    if(j==s.length())
        s+=".0";
    k=s.length()-j;
    for(i=0;i<ni-j;i++)
        s='0'+s;
    for(i=0;i<nf-k;i++)
        s+='0'; 
    return s;
}

能编个毛线衣吗?
2018-05-28 12:50



参与讨论请移步原网站贴子:https://bbs.bccn.net/thread-487219-1-1.html




关于我们 | 广告合作 | 编程中国 | 清除Cookies | TOP | 手机版

编程中国 版权所有,并保留所有权利。
Powered by Discuz, Processed in 0.375504 second(s), 7 queries.
Copyright©2004-2024, BCCN.NET, All Rights Reserved