简单算法题:分数小数化


题目:输入正整数a,b,c输出a/b的小数形式,精确到小数点后c位。a,b<=1e+6,c<=100.输入包含多组数据,结束标记为a=b=c=0;

样例输入:

1 6 4

0 0 0

样例输出:

0.1667

--------------------------------------------------------------------------------------------------------------------------

其实非常简单(不考虑数据很大的输入)

printf("%.*f",c,(double)a/b);

如果不知道“.*”这种东西,我的想法是这样的:

(1)把小数问题化为整数问题:比如本题样例1/6=0.166667;既然要保留4位,那我就乘以5位,使之变成16666.66667

(2)利用强制类型转换判断是否进位:随后(int)强制类型转化变成16666,取余取最后一位,作为四舍五入的依据,判断语句如果ans%10>=5则ans=ans+10;相当于进位

如果ans%10<5,则ans=ans。

(3)还原结果为小数:ans=(int)ans/10;ans=(int)ans/pow(10,4);打印的时候一定要用%f,另外对于被强制转化为整数的浮点数,打印一定要用%d而不能是%f,否则结果为0?

这里没有把两步写为一步,即ans=(int)ans/pow(10,5)是因为,16676/100000=0.16676,不是我们想要的0.1667,所以需要先变成1667,再还原变成0.1667

代码如下:

int a,b,c;
    FILE *fin;
    fin=fopen("in.txt","r");
    //printf("%.*f",3,12.4569);
    //double pi=13.5415;
    //printf("pi=%f,取整pi=%d",pi,(int)pi);
    while(fscanf(fin,"%d %d %d",&a,&b,&c)==3){
        if(a==b && a==c && a==0)break;
        if(a<0 || a>1e+6 || b<=0 || b>1e+6 || c<=0 || c>100)break;
        double ans=(double)a/b;
        ans*=pow(10,c+1);
        int tmp=(int)ans%10;
        //printf("ans=%f (int)ans=%d tmp=%d\n",ans,(int)ans%10,tmp);
        if(tmp>=5){
            ans+=10;
            ans=(int)ans/10;
            ans/=pow(10,c);
            printf("%.*f\n",c,ans);
        }else{
            ans=(int)ans/10;
            ans/=pow(10,c);
            printf("%.*f\n",c,ans);
        }
    }