2012-10-11 7 views
21

Eventuali duplicati:
This R reshaping should be simple, butÈ possibile utilizzare il dcast senza una funzione di aggregazione?

dcast da reshape2 opere senza una formula dove non ci sono duplicati. Prendete questi dati esempio:

df <- structure(list(id = c("A", "B", "C", "A", "B", "C"), cat = c("SS", 
"SS", "SS", "SV", "SV", "SV"), val = c(220L, 222L, 223L, 224L, 
225L, 2206L)), .Names = c("id", "cat", "val"), class = "data.frame", row.names = c(NA, 
-6L)) 

mi piacerebbe dcast questi dati e solo i valori tabulati, senza applicare alcuna funzione al value.var incluso quello predefinito length.

In questo caso, funziona correttamente.

> dcast(df, id~cat, value.var="val") 
    id SS SV 
1 A 220 224 
2 B 222 225 
3 C 223 2206 

Ma quando ci sono variabili duplicati, le fun default length. C'è un modo per evitarlo?

df2 <- structure(list(id = c("A", "B", "C", "A", "B", "C", "C"), cat = c("SS", 
"SS", "SS", "SV", "SV", "SV", "SV"), val = c(220L, 222L, 223L, 
224L, 225L, 220L, 1L)), .Names = c("id", "cat", "val"), class = "data.frame", row.names = c(NA, 
-7L)) 

> dcast(df2, id~cat, value.var="val") 
Aggregation function missing: defaulting to length 
    id SS SV 
1 A 1 1 
2 B 1 1 
3 C 1 2 

Idealmente quello che sto cercando è quello di aggiungere un fun = NA, come nel non cercare di aggregare il value.var. Il risultato mi piacerebbe quando dcasting DF2:

id SS SV 
1 A 220 224 
2 B 222 225 
3 C 223 220 
4. C NA 1 
+0

Cosa ti piacerebbe fare quando v'è la duplicazione? – Dason

+0

Aggiungilo semplicemente come un'altra riga con un 'NA' per qualsiasi valore mancante. – Maiasaura

+0

@Dason È kosher rispondere alla mia stessa domanda ora che ho trovato una soluzione? O dovrei semplicemente cancellare la q? – Maiasaura

risposta

19

Non credo ci sia un modo per farlo direttamente, ma possiamo aggiungere in una colonna aggiuntiva che ci aiuterà a uscire

df2 <- structure(list(id = c("A", "B", "C", "A", "B", "C", "C"), cat = c("SS", 
"SS", "SS", "SV", "SV", "SV", "SV"), val = c(220L, 222L, 223L, 
224L, 225L, 220L, 1L)), .Names = c("id", "cat", "val"), class = "data.frame", row.names = c(NA, 
-7L)) 

library(reshape2) 
library(plyr) 
# Add a variable for how many times the id*cat combination has occured 
tmp <- ddply(df2, .(id, cat), transform, newid = paste(id, seq_along(cat))) 
# Aggregate using this newid and toss in the id so we don't lose it 
out <- dcast(tmp, id + newid ~ cat, value.var = "val") 
# Remove newid if we want 
out <- out[,-which(colnames(out) == "newid")] 
> out 
# id SS SV 
#1 A 220 224 
#2 B 222 225 
#3 C 223 220 
#4 C NA 1 
+0

Grazie, sono arrivato alla stessa conclusione. – Maiasaura

9

Ho trovato la stessa soluzione mentre Dason rispondeva al mio.

Mi sono reso conto che dcast semplicemente non sa come gestire i duplicati. Il modo in cui ho capito come ingannarlo è stato aggiungere un altro identificatore univoco in modo da non confonderlo con i duplicati.

In questo esempio:

df <- ddply(df2, .(cat), function(x){ x$id2 = 1:nrow(x); x}) 
> dcast(df, id+id2~cat, value.var="val")[,-2] 
    id SS SV 
1 A 220 224 
2 B 222 225 
3 C 223 220 
4 C NA 1 
+0

che è stato così utile per un caso simile per me. Grazie :) – sarah

+0

Hai salvato la mia giornata !! –