USACOFractions to Decimals

来源:http://ace.delos.com/usacoprob2?a=ecro6SKAJN4&S=fracdec

这题主要是处理循环节的问题。

先考虑竖式除法:

1.设被除数为A,除数为B,试除一次有:B/A=C……D

2.令B不变,被除数变成D*10,再进行试除

3.明显竖式除法是递推定义的,而出现循环节则表示被除数重复出现了,由此算法已经很明显了,不再多说。

唉,明明很简单的东西,我竟然写了一大堆废话T_T

/*
ID:ay27272
PROG:fracdec
LANG:C++
*/

#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;

#define NN 100005
int a[NN]={0};
int b[NN]={0};

int work(int x)      //求出x的位数
{
    int xx=0;
    while (x>0)
    {
        xx++;
        x/=10;
    }
    if (xx==0) return 1;
    else return xx;
}

int main()
{
    freopen("fracdec.in","r",stdin);
    freopen("fracdec.out","w",stdout);
    int n,m;
    cin>>n>>m;

    int dd=n/m,d=n%m;   //dd为整数部分,d为小数部分
    int temp,h=-1,sum;
    memset(a,255,sizeof(a));     //初值为-1
    a[d]=0;

    for (sum=1;true;sum++)
    {
        b[sum]=d*10/m;       //记录结果值
        temp=d*10-b[sum]*m;
        d=temp;
        if (temp==0) break;
        if (a[temp]!=-1) { h=a[temp]+1; break; }
        a[temp]=sum;     //记录试除后的余数,temp*10作为下一次的被除数
    }

    int ss=work(dd)+1;     //输出注意条件每76个字符换行
    cout<<dd<<".";
    for (int i=1;i<=sum;i++)
    {
        if (ss==76) { cout<<endl; ss=0; }
        if (h==i) { cout<<"("; ss++; }
        if (ss==76) { cout<<endl; ss=0; }
        cout<<b[i];
        ss++;
    }
    if (ss==76) cout<<endl;
    if (h!=-1) cout<<")";
    cout<<endl;

    return 0;
}
原文地址:https://www.cnblogs.com/ay27/p/2800770.html