2012-09-04 73 views
0

我試圖將一個大的(〜700Mb).csv文件讀入R.R是否支持8位變量?

該文件包含一個小於256的整數數組,其中包含一個標題行和2個標題列。

我用:

trainSet <- read.csv(trainFileName) 

這最終barfs有:

Loading Data... 
R(2760) malloc: *** mmap(size=151552) failed (error code=12) 
*** error: can't allocate region 
*** set a breakpoint in malloc_error_break to debug 
R(2760) malloc: *** mmap(size=151552) failed (error code=12) 
*** error: can't allocate region 
*** set a breakpoint in malloc_error_break to debug 
Error: cannot allocate vector of size 145 Kb 
Execution halted 

綜觀內存使用,它在6GB的機器上有關的3Gb使用與在零頁面文件使用conks出事故發生的時間,所以可能有另一種解決方法。

如果我使用:

trainSet <- read.csv(trainFileName, header=TRUE, nrows=100) 
classes = sapply(train,class); 

我可以看到,所有的列被加載爲「整數」我認爲這是32位。

很明顯,使用3Gb加載700Mb .csv文件的一部分遠沒有效率。我想知道是否有辦法告訴R使用8位數字作爲列?這是我在過去在Matlab中完成的工作,然而,我似乎無法在R中找到任何提及的8位類型的地方。

它存在嗎?我怎麼會告訴它read.csv使用它?

在此先感謝您的幫助。

+1

可能的解決方案:A)得到更多的內存b)將數據存入數據庫,併爲使用'RMySQL'需要讀取數據塊。 c)快速啓動一個大內存的EC2實例並在那裏運行。 – Maiasaura

+0

@Maiasaura:或只是注意文檔中的警告。 ;-) –

回答

2

狹義答案是附加包ff允許您使用更緊湊的表示形式。

缺點是不同的表示方式會阻止您將數據傳遞到標準函數。

因此,您可能需要重新考慮您的方法:可能對數據進行二次採樣,或獲取更多RAM。

+0

會檢查ff,謝謝。獲得更多的內存真的有幫助,因爲它現在在頁面文件開始使用前已經完成了嗎? – Stephan

+0

是的,更多的RAM通常是最簡單和最有效的硬件修補程序。 –

+0

使用ff包中的read.csv.ffdf。有關包ff的其他基本數據操作,可以使用包ffbase。在開始做任何真實的統計之前,看看你能從那裏得到多少。 – jwijffels

2

問:你能告訴R來使用8位數字

答:沒有。(編輯:見德克的評論是低於他比我聰明。)

問:請問更多的內存的幫助?

答:也許吧。假設一個64位操作系統和一個64位R實例是起點,那麼「是」,否則「否」。

隱含的問題A:700GB的.csv數據集在被read.csv讀入時會不會有700 MB?

答:也許吧。如果它確實是所有整數,它可能會更小或更大。每個整數需要4個字節,如果大多數整數的範圍是-9到10,那麼當它們每個以4個字節存儲時,它們實際上可能會「擴大」。目前,每個值只使用1-3個字節,因此您希望大小增加50%。您希望在讀取功能中使用colClasses="integer"。否則,如果有任何數據輸入毛刺,它們可能被存儲爲因子或8字節「數字」。

隱含問題B:如果您將數據導入工作空間,您將能夠使用它嗎? A:只有可能。

答:只有也許。由於R分配的方式與您的最大對象相比至少需要三倍的內存,即使它是副本的名稱也是如此。

+0

看看軟件包'bit'以及'ff',我想你在這裏指出一個不是完全正確,除非你只考慮基地址R. –

+0

如果我正確讀取他們的摘要頁面,那麼這些包都不支持8位整數的內存操作。 「ff」提供基於磁盤的操作,「位」提供邏輯(1位)操作。 –

+0

這不是我從之前與Jens的討論中所記得的,但我可能錯了...... –

2

並不想成爲表露無疑,但解決這一問題的方式記錄在?read.csv

These functions can use a surprising amount of memory when reading 
large files. There is extensive discussion in the ‘R Data 
Import/Export’ manual, supplementing the notes here. 

Less memory will be used if ‘colClasses’ is specified as one of 
the six atomic vector classes. This can be particularly so when 
reading a column that takes many distinct numeric values, as 
storing each distinct value as a character string can take up to 
14 times as much memory as storing it as an integer. 

Using ‘nrows’, even as a mild over-estimate, will help memory 
usage. 

這個例子需要一段時間,因爲我跑/ O,甚至與我的SSD,但有沒有內存問題:

R> # In one R session 
R> x <- matrix(sample(256,2e8,TRUE),ncol=2) 
R> write.csv(x,"700mb.csv",row.names=FALSE) 

R> # In a new R session 
R> x <- read.csv("700mb.csv", colClasses=c("integer","integer"), 
+ header=TRUE, nrows=1e8) 
R> gc() 
      used (Mb) gc trigger (Mb) max used (Mb) 
Ncells 173632 9.3  350000 18.7 350000 18.7 
Vcells 100276451 765.1 221142070 1687.2 200277306 1528.0 
R> # Max memory used ~1.5Gb 
R> print(object.size(x), units="Mb") 
762.9 Mb 
+0

是的 - 我已經嘗試將colClasses指定爲整數,它似乎沒有改變任何東西。當我有3Gb未使用的RAM時,仍然需要弄清楚爲什麼我內存不足,但現在我有很多探索的途徑。 – Stephan

+0

@Stephan:請注意,我沒有*只是*指定'colClasses'。由於'?scan'('read.table'和'read.csv'使用'scan')中的註釋部分的這一部分指定'nrows',如果沒有指定項目的數目,按兩個冪分配內存,因此可以根據需要使用多達三倍的內存。「 –

+0

aha。這使得現在很有意義 - 當然可以解釋爲什麼它有很多可用的內存不足。在我說服自己完成FF後,我會更加痛苦,而不是我可以應付的。再次感謝。 – Stephan