2009-12-06 64 views
2

我真的很努力將一些數值浮點數據從一個文件加載到C程序中......該文件具有浮點數,精度爲3個小數點,每個小數點都在一個單獨的行...我想加載這些值到一個浮點數組,然後在其中執行一些計算...但是我試圖將它加載到一個浮點數組中,但它沒有正確存儲值...即像123.45被存儲爲123.44999或其他...但我不想要這個。從文件中加載數據C

我試圖將它存儲在一個字符串數組中,然後可能會將它們轉換爲縮放整數。但我不能讓它加載到一個字符串數組。誰能告訴我我哪裏出錯了。我所做的就是這樣的。

unsigned char **data 
............ 
data = malloc(sizeof(unsigned char *) * fileSize); 
............ 
while (!feof(fp)) 
{ 
if (fscanf (fp, "%s", &data[j]) == 1) // if converted, increment counter 
++j; 
} 
........... 

我是新手,所以我不太擅長指針。並在我加載到一個字符串數組後,我如何將它轉換成縮放整數?

+3

你正在分配文件大小乘以ptr的大小,而不是你想要的。 – 2009-12-06 10:30:18

+0

@Mitch:我認爲這是他的意圖,因爲他希望每個數字都有一個單獨的字符串,並且數據保存指向字符串的指針。但是,在代碼中還有一些其他問題... – 2009-12-06 11:50:51

回答

1

不使用float,使用double。

也可以使用

double d;

read(d);

(int)(d * 100)得到int。

+0

小心!你不想截斷結果乘以100,因爲那樣你會失去精度。 Try(int)(d * 100 + 0.5) 否則123.45,存儲爲123.44999將最終爲12344 – 2009-12-06 11:56:41

+0

使用double似乎適用於我。 – sfactor 2009-12-06 12:13:25

+0

@Tony感謝您指出:) – 2009-12-06 13:03:59

0

不幸的是,您所碰到的是一些數字無法用浮點數據類型準確表示的事實。如果您手動將124.45分配給C中的浮點數(即float f = 123.45),則會出現完全相同的問題。

真的需要精確度嗎?你有什麼數據計劃?

3

你可能沒有太多的選擇,當涉及到浮點數喜歡123.45被顯示爲123.44999

浮點表示的「不準確」的SO,here's one example已經討論過很多次了。

我建議你回去把輸入視爲浮點數,但是讀到精度問題。

+0

+1用於糾正潛在的有缺陷的浮點假設 – 2009-12-06 10:39:49

+2

123.45如果僅顯示爲2dp,則不會顯示爲123.44999。換句話說,123.45 == 123.44999到2dp,只要你不會犯第一位數字打印出來的結果的錯誤,你應該沒問題。 – 2009-12-06 11:53:51

0

我建議你使用ifstream來讀入字符串,然後將其轉換爲double。

string number; 
ifstream yourfile("yourfile", ios::in); 

if(yourfile) 
    while(yourfile >> number){ 
    double yourFloat=strtod(number.c_str()); 
    } 
+0

他沒有使用C++ – 2009-12-06 11:04:26

0

這個精度對您的應用程序有多重要?浮點數通常可能會稍微不準確,因爲它們將數字存儲在基數2(二進制)表示中,該表示無法正確表示一些基數爲10的數字。

你有幾個選擇,取決於這個精度對你的應用程序有多重要。

  1. 住在一起。也許這個錯誤對您的應用程序來說不是問題
  2. 使用Double。它有兩倍的空間 來表示數字,並且將更精確地爲 。在某些情況下,它仍然可能不準確 。
  3. 使用定點數學。如果您只需要n位小數,那麼可能需要查看這種方法(因爲它消除了不準確性的根源)。
  4. 將float保留爲字符串或將其存儲爲二進制編碼的Decimal。您需要爲您需要的任何數學運算編寫函數,並且性能將是這4個選項中最差的。但是,您將能夠使用任意精度的十進制數字,而不必擔心精度的任何損失。

選項3或4需要使用外部庫或滾動自己的實現。如果1或2足夠好,那麼我不會爲這些選項而煩惱。

+0

是的,使用double工作 – sfactor 2009-12-06 12:14:07