這道題題意如下:給出一個循環小數,將它化成分數並化簡為最簡分數,然後輸出該分數。由於不知道這些循環小數從哪開始是循環節,於是就規定,輸出當該小數所化成的分數分母最小時,該小數所化成的分數。(原題地址:http://poj.org/problem?id=1930)
要想解決這道題,首先應該了解如何將循環小數化為分數:
一,純循環小數化分數:循環節的數字除以循環節的位數個9組成的整數。例如:
0.3333……=3/9=1/3;
0.285714285714……=285714/999999=2/7.
二,混循環小數:(例如:0.24333333……)不循環部分和循環節構成的的數減去不循環部分的差,再除以循環節位數個9添上不循環部分的位數個0。例如:
0.24333333…………=(243-24)/900=73/300
0.9545454…………=(954-9)/990=945/990=21/22
這便是循環小數化成分數的方法,知道這個後,解決這道題也好辦了。
代碼如下:
1 /*
2 Name:poj1930
3 Copyright:
4 Author: yuyang
5 Date: 29/10/16 11:58
6 Description:
7 */
8
9 #include<cstdio>
10 #include<stdlib.h>
11 #include<algorithm>
12 #include<cstring>
13 #include<string>
14 #include<iostream>
15 using namespace std;
16 string str;
17
18 //判斷兩數的最大公因數
19 int gcd(int x,int y){
20 int ret;
21 if(y==0){
22 ret=x;
23 }else if(x<y){
24 ret=gcd(y,x);
25 }else{
26 ret=gcd(y,x%y);
27 }
28 return ret;
29 }
30
31 //將所得到的分數化簡,得到當分數為最簡分數時分子和分母的值
32 pair<int,int> jh(int x,int y){
33 int li=gcd(x,y);
34 if(li==1){
35 return make_pair(x,y);
36 }else{
37 return jh(x/li,y/li);
38 }
39 }
40
41 int main(){
42 while(cin>>str&&str.size()!=1){
43 int fmmin=99999999;
44 int fzmin;
45 int yjr=0;int start,end,fxhj;
46 //判斷小數部分是從第幾位開始,從第幾位結束(開頭的0算一位,小數點算一位),start為起始位數,end為結束位數
47 for(int i=0;i<str.size();i++){
48 if(yjr==0&&str[i]=='.'){
49 start=i+1;
50 yjr=1;
51 }
52 if(yjr==1&&str[i+1]=='.'){
53 end=i;
54 }
55 }
56 end-=2;
57 for(int i=start;i<=end;i++){//求出當從第i位開始為循環節時,該小數對應的分數值,並判斷在此情況下分母是否取最小值
58 int fz=0,fm=0;//fz為分子值,fm為分母值
59 /*
60 一,純循環小數化分數:循環節的數字除以循環節的位數個9組成的整數。例如:
61 0.3333……=3/9=1/3;
62 0.285714285714……=285714/999999=2/7.
63 二,混循環小數:(例如:0.24333333……)不循環部分和循環節構成的的數減去不循環部分的差,再除以循環節位數個9添上不循環部分的位數個0。例如:
64 0.24333333…………=(243-24)/900=73/300
65 0.9545454…………=(954-9)/990=945/990=21/22
66 */
67 for(int j=i;j<=end;j++){
68 fz=fz*10+(str[j]-'0');
69 fm=fm*10+9;
70 }
71 int plus=0;
72 if(i>start){
73 for(int j=start;j<i;j++){
74 plus=plus*10+(str[j]-'0');
75 fm=fm*10;
76 }
77 int qian=plus;
78 for(int j=i;j<=end;j++){
79 qian=qian*10;
80 }
81 qian=fz+qian;
82 fz=qian-plus;
83 }
84 //判斷分母是否取最小值
85 if(jh(fz,fm).second<fmmin){
86 fmmin=jh(fz,fm).second;
87 fzmin=jh(fz,fm).first;
88 }
89 }
90 printf("%d/%d\n",fzmin,fmmin);
91 }
92 return 0;
93 }
我將這個代碼提交到poj後通過了:
