yukicoder No.25 - 有限小数

Source

ニコニコミュニティ
問題文

問題概要

正整数 $N,M$ が与えられるので,$N/M$ を小数表示した時 $0$ でない最後の数字を求める問題.
有限小数で表せない場合はそれを指摘する.
(有限小数でも無限小数でもどちらでも表せる場合は,有限小数で表すこととする)

解法

まず,$N,M$ のそれぞれを ${\rm GCD}(N,M)$ で割って互いに素にしておく.
$M$ が $2,5$ 以外の素因数を持てば有限小数では表せない.
その後,$N$ が $10$ の倍数であるかぎり,$10$ で割っておく.
後は,$M$ が $10$ の冪になるように,足りない $2,5$ を分子分母にかけて,$N$ の下1桁が答え.
この時,オーバーフローしないように,$N$ は ${\rm mod}\ 10$ などで計算すれば良い.

C++によるスパゲッティなソースコード

#include<bits/stdc++.h>
using namespace std;

#define REP(i,a,b) for(i=a;i<b;i++)
#define rep(i,n) REP(i,0,n)

#define ll long long
#define ull unsigned ll

template<class T> T GCD(T a,T b){T r; while(a){r=b; b=a; a=r%a;} return b;}

int main(){
  int i, j, k;
  int p2 = 0, p5 = 0;
  ull N, M, g;

  scanf("%llu%llu",&N,&M);
  g = GCD(N,M);
  N /= g; M /= g;

  while(M%2==0) M/=2, p2++;
  while(M%5==0) M/=5, p5++;
  if(M>1){ puts("-1"); return 0; }

  while(N%10==0) N /= 10;
  N %= 10;
  while(p2>p5) p5++, N=(N*5)%10;
  while(p2<p5) p2++, N=(N*2)%10;

  printf("%d\n",(int)N);

  return 0;
}

Current time: 2017年07月23日15時46分14秒
Last modified: 2014年11月18日03時09分12秒 (by laycrs)
Tags: Competitive_Programming yukicoder
トップページに戻る

Logged in as: unknown user (not login)

ログイン: