2013-04-19 15 views
6

Mam wiele dużych ramek danych w R, który miałem zamiar przechowywać za pomocą redis. Jestem całkowicie nowy w Redis, ale czytałem o tym dzisiaj i używam pakietu R rredis.Przechowywanie dużych ramek danych w redis przez R

Grałem z małymi danymi oraz zapisałem i wyszukałem małe ramki danych przy użyciu funkcji redisSet() i redisGet(). Jednak gdy przyszło do zapisywania moich większych dataframes (z których największa wynosi 4,3 miliona wierszy i 365MB gdy zapisany jako plik .RData) używając kodu redisSet('bigDF', bigDF) pojawia się następujący komunikat o błędzie:

Error in doTryCatch(return(expr), name, parentenv, handler) : 
    ERR Protocol error: invalid bulk length 
In addition: Warning messages: 
1: In writeBin(v, con) : problem writing to connection 
2: In writeBin(.raw("\r\n"), con) : problem writing to connection 

Przypuszczalnie dlatego, że dataframe jest zbyt duży, aby go zapisać. Wiem, że redisSet zapisuje ramkę danych jako ciąg znaków, co nie jest chyba najlepszym sposobem na zrobienie tego z dużymi ramkami danych. Czy ktoś wie o najlepszy sposób to zrobić?

EDIT: Mam odtworzył błąd mój tworząc bardzo dużą atrapę dataframe:

bigDF <- data.frame(
'lots' = rep('lots',40000000), 
'of' = rep('of',40000000), 
'data' = rep('data',40000000), 
'here'=rep('here',40000000) 
) 

Running redisSet('bigDF',bigDF) daje mi błąd:

Error in .redisError("Invalid agrument") : Invalid agrument 

po raz pierwszy, a następnie uruchomić go ponownie natychmiast potem I pojawia się błąd

Error in doTryCatch(return(expr), name, parentenv, handler) : 
    ERR Protocol error: invalid bulk length 
In addition: Warning messages: 
1: In writeBin(v, con) : problem writing to connection 
2: In writeBin(.raw("\r\n"), con) : problem writing to connection 

Dzięki

+0

Podziel się rzeczywistym kodem, którego używasz w sformatowanym bloku kodu. Ułatwi to osobie z doświadczeniem diagnozowanie i sugerowanie poprawek. –

Odpowiedz

7

W skrócie: nie można. Redis can store a maximum of 512 Mb of data in a String value a odcinkach ramka danych demo jest większa niż:

> length(serialize(bigDF, connection = NULL))/1024/1024 
[1] 610.352 

tło techniczne:

serialize nazywa się funkcją .cerealize pakietu poprzez redisSet i rredis:::.redisCmd:

> rredis:::.cerealize 
function (value) 
{ 
    if (!is.raw(value)) 
     serialize(value, ascii = FALSE, connection = NULL) 
    else value 
} 
<environment: namespace:rredis> 

Offtopic: dlaczego przechowywałbyś tak duży zbiór danych w Redis? Redis jest dla małych par klucz-wartość. Z drugiej strony odniosłem sukces, przechowując duże zbiory danych w CouchDB i MongoDB (z GridFS), dodając tam skompresowany RData jako załącznik.

+0

Dziękuję daroczig, więc tylko po to, aby wyjaśnić, że masz długość zapytania (serializować (... podaje rozmiar wartości ciągu w Mb? Przypuszczam, że mógłbym podzielić ramkę danych w 2 i zapisać ją osobno, ale biorąc pod uwagę twój ostatni komentarz, zakładam, że W odniesieniu do twojego pytania dopiero zacząłem używać redis, więc nie zdawałem sobie sprawy z jego ograniczeń w przechowywaniu dużych zbiorów danych, słyszałem, że był to dobry sposób na szybkie przechowywanie i pobieranie danych, dlatego właśnie Spójrz na CouchDB i MongoDB – user1165199

+1

Optymalne przechowywanie zestawów danych R naprawdę zależy od twoich potrzeb Redis jest cholernie szybki, ponieważ ma przechowywać wszystko w pamięci, dlatego powinieneś raczej przechowywać tyle danych, które pasują do twojej fizycznej pamięci.Z drugiej strony, jeśli tylko uzyskasz dostęp do tych danych na localhost, nie ma potrzeby stosowania backendu DB: utwórz dysk RAM i napisz "RData" w migi i przeładuj go w dowolnym momencie. Powinieneś także znaleźć optymalną metodę i stosunek kompresji (CPU vs IO). Jeśli korzystasz z wielu komputerów, wybierz swój DB na potrzeby, takie jak replikacja, sharding itp. – daroczig

+1

@daroczig, powyższy post pomija inne potrzeby, dlaczego chciałbyś przechowywać większe przedmioty w Redis, słowo kluczowe: wymiana danych. Można wygenerować większe elementy danych w C# i przechowywać w Redis w celu łatwego dostępu w R lub odwrotnie. Oczywiście, jeśli ktoś chciałby przechowywać dane generowane przez R i uzyskać do nich dostęp później, to najlepszym rozwiązaniem jest przechowywanie na dysku, w połączeniu z plikami mapowanymi w pamięci. Ale używanie Redis ma sens w wymianie danych, gdy lokalizacje pomiędzy źródłem a celem danych nie są współużytkowane, a Redis jest jedynym punktem wymiany. –

Powiązane problemy