zoukankan      html  css  js  c++  java
  • poj3358 Period of an Infinite Binary Expansion

    WA的代码:

    #include<iostream>
    #include<string.h>
    #include<stdio.h>
    #define LL long long
    #define maxn 1000+5//最多的小数位数
    using namespace std;
    double a[maxn];
    const double eps=1e-10;
    double abs(double n)
    {
        return n>0 ? n:-n;
    }
    int find(int cnt)//关键
    {//判断第cnt个数是否在前面出现过
        for (int i=1;i<cnt;i++)
        {
            if (abs(a[i]-a[cnt])<eps) return i;
        }
        return 0;
    }
    int main()
    {
        LL n,m;
        int cas=0;
        while(~scanf("%I64d/%I64d",&n,&m))
        {
            cas++;
            double ans=(n+0.0)/(m+0.0);
            ans=ans-(int)ans;
            int cnt=1;a[1]=ans;
            int ch;
            while ( (ch=find(cnt))==0 )
            {
                ans=ans*2;
                ans=ans-(int)ans;//应该判余数
                cnt++;
                a[cnt]=ans;
            }
            printf("Case #%d: %d,%d
    ",cas,ch,cnt-ch);
    
        }
        return 0;
    }

    我们主要来说说是怎么WA的

    一句话总结,正确的算法,有限的存储精度。

    思路描述:

    1、原理:重复乘2,取首位。

    然后我就就想简化判断,只要出现重复的小数部分,那一定是又开始了一个新的循环。

    2、结果悲剧了,错误有二:

    i.  double型的好像不能直接判断a==b,会有判断误差,反正像是0.2==0.2这样的都判断不出

    ii.  后来我就想通过eps约束,(abs(a-b)< eps ), 一直W,后来才想到,比如1/199213,这样的数据,它本身的小数部分就有10^6位,计算机是不可能存储下来的,double本来就是模糊存储。  再者,eps不可能兼顾所有的数据  (以后少用)。

    下面是AC的代码

  • 相关阅读:
    洛谷 P1981 表达式求值
    1696:逆波兰表达式
    C# winform选择文件、选择文件夹、打开文件
    建立二叉树的二叉链表存储结构(严6.70)
    二叉树的深度
    Sequence
    c++优先队列(priority_queue)用法详解
    二叉树的操作
    [清华集训2015]灯泡(浙江大学ZOJ 3203 Light Bulb)
    Go 和 Colly笔记
  • 原文地址:https://www.cnblogs.com/little-w/p/3294276.html
Copyright © 2011-2022 走看看