2017-04-22 53 views
-1

正如我從answer瞭解到的,有一種方法可以通過宏LDBL_MANT_DIG使用float.h來擴展精度。我的目標是提高double值的浮點精度,以便我可以存儲更精確的數字,例如0.000000000566666而不是0.000000。請問,有人可以舉一個簡短的例子來使用這個宏,以便我可以擴展存儲在緩衝區中的精度嗎?如何使用float.h宏來增強浮點精度

+3

你不能增加float的精度。標題爲您提供宏來檢查您的系統及其硬件提供了哪種精度,但就是這樣。 – dasblinkenlight

+1

如果用'「%f」'打印,則只能得到6位小數。改爲使用'%e'或'%g',或者添加精度控制,或兩者兼而有之。 –

回答

0

您引用的答案只是提到宏等於您可以存儲的精度位數。它不能以任何方式提高精度。但這個宏是爲了「長雙打」,而不是雙打。

long double x = 3.14L; 

公告的「L」爲它指定一個長雙字面號碼後:如果您需要比double類型更精確,您可以使用long double型。

0

浮點類型在硬件中實現。精度在整個行業中得到了標準化,並融入到了CPU的電路中。除了諸如GMP之類的擴展精度軟件庫外,無法將其增加到long double以外。

好消息是浮點數不會陷入前導零。 0.000000000566666不會舍入爲零。只有六位數字,你甚至只需要一個單精度的float來表示它。

沒有與math.h(不float.h)的問題,其中POSIX標準不能提供π和Ëlong double精度。有幾個解決方法:GNU定義了例如M_PIlM_El,或者您也可以使用預處理器將l粘貼到另一個庫中的字面常量(給出long double類型)並希望獲得空閒數字。

2

您的評論關於想存儲更準確的數字,所以你不會得到只是0.000000表明問題不在於存儲,但在打印數字的方式。請看下面的代碼:

#include <stdio.h> 

int main(void) 
{ 
    float f = 0.000000000566666F; 
    double d = 0.000000000566666; 
    long double l = 0.000000000566666L; 

    printf("%f %16.16f %13.6e\n", f, f, f); 
    printf("%f %16.16f %13.6e\n", d, d, d); 
    printf("%lf %16.16lf %13.6le\n", d, d, d); 
    printf("%Lf %16.16Lf %13.6Le\n", l, l, l); 
    return 0; 
} 

運行時,它產生:

0.000000 0.0000000005666660 5.666660e-10 
0.000000 0.0000000005666660 5.666660e-10 
0.000000 0.0000000005666660 5.666660e-10 
0.000000 0.0000000005666660 5.666660e-10 

正如你所看到的,使用默認"%f"格式打印6位小數,它把該值作爲0.0。然而,隨着更精確的格式顯示,該值被正確存儲,並且可以顯示更多小數位,或格式爲%e,或者格式爲%g,但代碼不顯示正在使用 - 輸出會與本例中的%e格式相同。

%f轉換規範,而不是%lf%Lf,說'打印double'。請注意,當float值傳遞到printf()時,它們會自動轉換爲double(就像短於int的數字類型被提升爲int一樣)。因此,%f可用於floatdouble類型,實際上%lf格式(其定義在C99中 - 其他所有內容均在C90中定義)可用於格式化floatdouble值。 %Lf格式需要long double

只需使用<float.h>中的任何宏,就沒有辦法在floatdouble中存儲更多精度。這些更多地描述了浮點類型的特徵以及它們表現的方式。