程式設計之美 浮點數的精確表示

2021-07-11 05:09:29 字數 1450 閱讀 5448

問題描述:

如何將浮點數(小數)轉換為分數的形式,這樣可以更精確的表達出浮點數的值。

問題分析:

小數可以分為兩種,有限小數和無限迴圈小數。

有限小數的處理相對簡單:

只要把它乘以10的n次方,轉換為整數,再和10的n次方都除以它們的最大公約數即可。

例如:0.25  把它乘以 10的2次方 變成25, 25/100 分子分母除以最大公約數25變成1/4即可。

無限迴圈小數的處理要複雜一些:

書中使用了乙個有趣的計算方法,它把無限迴圈小數分為一小數部分和乙個迴圈部分 例如: x=0.a1a2...am(b1b2...bn)

這裡a是小數部分,b是迴圈部分。

1)  x先乘以10的m次方,把小數部分變為整數   x*10^m ==> a1a2...am + 0

.b1b2...bn(b1b2...bn)

x = (a1a2...am + 0.b1b2...bn(b1b2...bn))/(10^m)

2)  假設 y = 0.b1b2...bn(b1b2...bn),那麼y可以轉換為 y*10^n = b1b2...bn + 0.b1b2...bn(b1b2...bn)

y*10^n = b1b2...bn +

y   ==>   y = b1b2...bn/(10^n - 1)

3)  把y的部分代入x的等式中  x = (a1a2...am +

b1b2...bn/(10^n - 1))/(10^m)

x = (a1a2...am * (10^n - 1) + b1b2...bn) / ((10^n - 1)*10^m)

例如 0.3(3) = (3*9 + 3) / (9*10) = 30 / 90 = 1/3

例項程式:

程式中的缺陷,如果迴圈小數字數太多,會造成乘積超過int的範圍,造成計算錯誤。

#include using namespace std;

typedef struct _data

data_t;

unsigned long gcb(unsigned long a, unsigned long b)

r = b % a;

while(r != 0)

return a;

}void calc(data_t data)

temp = data._b;

while (temp != 0)

cout << "a->" << data._a << ":" << power_a << " b->" <> val;

return 0;

}

程式設計之美 2 6 精確表達浮點數

本題目內容如下 在計算機中,有時使用float或double來儲存小數是不能得到精確值的.如果你需要得到精確計算結果,最好是用分數形式來表示小數。有限小數或者無限迴圈小數都可以轉化為分數。eg 0.9 9 10 0.33 3 1 3 括號裡的數字表示的的是迴圈節 當然乙個小數可以用好幾種弄分數形式來...

程式設計之美 2 6 精確表達浮點數

題目 給乙個有限小數 或者 無限迴圈小數,用分母最小的方式用分數精確的表達這個數字。括號中表示迴圈部分,如 0.3 0.3 3 0.3 0 思路 我一看,傻眼了,想了兩下不想想了,就在網上找迴圈小數轉分數,結果居然是小學奧賽題!我鬱悶的很啊.拿 1.2 34 來舉例子吧 1.2 34 10 12.3...

程式設計之美 2 6 精確表達浮點數

1.簡述 簡單的說就是將有限迴圈小數和無限迴圈小數轉化為分數形式。比如 0.9 9 10 0.333 3 1 3,其中括號表示迴圈節。2.思路 書上的方法就是分情況討論。首先是有限迴圈小數,比如123.456,整數部分123不用說了,主要是小數部分0.456,直接轉化為456 1000,然後消去最大...