Time Limit: 1000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Total Submission(s): 1646 Accepted Submission(s): 613 Problem Description Ray 在數(shù)學課上聽老師說,任何小數(shù)都能表示成分數(shù)的形式,他開始了化了起來,很快他就完成了,但他又想到一個問題,如何把一個循環(huán)小數(shù)化成分數(shù)呢? 請你寫一個程序不但可以將普通小數(shù)化成最簡分數(shù),也可以把循環(huán)小數(shù)化成最簡分數(shù)。 Input 第一行是一個整數(shù)N,表示有多少組數(shù)據(jù)。 每組數(shù)據(jù)只有一個純小數(shù),也就是整數(shù)部分為0。小數(shù)的位數(shù)不超過9位,循環(huán)部分用()括起來。 Output 對每一個對應的小數(shù)化成最簡分數(shù)后輸出,占一行。 首先我們要明確,無限小數(shù)可按照小數(shù)部分是否循環(huán)分成兩類:無限循環(huán)小數(shù)和無限不循環(huán)小數(shù)。無限不循環(huán)小數(shù)不能化分數(shù),這在中學將會得到詳盡的解釋;無限循環(huán)小數(shù)是可以化成分數(shù)的。那么,無限循環(huán)小數(shù)又是如何化分數(shù)的呢?由于它的小數(shù)部分位數(shù)是無限的,顯然不可能寫成十分之幾、百分之幾、千分之幾……的數(shù)。其實,循環(huán)小數(shù)化分數(shù)難就難在無限的小數(shù)位數(shù)。所以我就從這里入手,想辦法“剪掉”無限循環(huán)小數(shù)的“大尾巴”。策略就是用擴倍的方法,把無限循環(huán)小數(shù)擴大十倍、一百倍或一千倍……使擴大后的無限循環(huán)小數(shù)與原無限循環(huán)小數(shù)的“大尾巴”完全相同,然后這兩個數(shù)相減,“大尾巴”不就剪掉了嗎!我們來看兩個例子: ⑴ 把0.4747……和0.33……化成分數(shù)。 想1: 0.4747……×100=47.4747…… 0.4747……×100-0.4747……=47.4747……-0.4747…… (100-1)×0.4747……=47 即99×0.4747…… =47 那么 0.4747……=47/99 想2: 0.33……×10=3.33…… 0.33……×10-0.33……=3.33…-0.33…… (10-1) ×0.33……=3 即9×0.33……=3 那么0.33……=3/9=1/3 由此可見, 純循環(huán)小數(shù)化分數(shù),它的小數(shù)部分可以寫成這樣的分數(shù):純循環(huán)小數(shù)的循環(huán)節(jié)最少位數(shù)是幾,分母就是由幾個9組成的數(shù);分子是純循環(huán)小數(shù)中一個循環(huán)節(jié)組成的數(shù)。 ⑵把0.4777……和0.325656……化成分數(shù)。 想1:0.4777……×10=4.777……① 0.4777……×100=47.77……② 用②-①即得: 0.4777……×90=47-4 所以, 0.4777……=43/90 想2:0.325656……×100=32.5656……① 0.325656……×10000=3256.56……② 用②-①即得: 0.325656……×9900=3256.5656……-32.5656…… 0.325656……×9900=3256-32 所以, 0.325656……=3224/9900 將純循環(huán)小數(shù)改寫成分數(shù),分子是一個循環(huán)節(jié)的數(shù)字組成的數(shù);分母各位數(shù)字都是9,9的個數(shù)與循環(huán)節(jié)中的數(shù)字的個數(shù)相同. 將混循環(huán)小數(shù)改寫成分數(shù),分子是不循環(huán)部分與第一個循環(huán)節(jié)連成的數(shù)字組成的數(shù),減去不循環(huán)部分數(shù)字組成的數(shù)之差;分母的頭幾位數(shù)字是9,末幾位數(shù)字是0,9的個數(shù)跟循環(huán)節(jié)的數(shù)位相同,0的個數(shù)跟不循環(huán)部分的數(shù)位相同. #include#includestring.h>int gcd(int a,int b){ return b==0?a:gcd(b,a%b);}int main(){ char str[20]; int n; scanf('%d',&n); getchar(); while(n--){ scanf('%s',str); int i,flag=1; int a1=1,b1=0,a2=1,b2=0; for(i=2;str[i]!='\0';i++){ if(str[i]=='(') flag=0; if(str[i]>='0' && str[i]<>'9'){ if(flag){ a1*=10; b1=b1*10+str[i]-'0'; } a2*=10; b2=b2*10+str[i]-'0'; } } //printf('a1=%d b1=%d a2=%d b2=%d\n',a1,b1,a2,b2);if(flag) printf('%d/%d\n',b1/gcd(a1,b1),a1/gcd(a1,b1)); else{ int tmp=gcd((a2-a1),(b2-b1)); printf('%d/%d\n',(b2-b1)/tmp,(a2-a1)/tmp); } } return0;}
|