2016-07-20 3 views
3

Ich habe einen breiten Datenrahmen, den ich sammeln oder in einen großen Datenrahmen verschmelzen muss. Der Teil, an dem ich festhalte, ist, dass ich Gruppen von Spalten habe, die verbunden/gruppiert bleiben müssen.Sammeln Sie mehrere Gruppen von Spalten in R

Ich habe 2 Benutzer für jede Formularübergabe und 3 Spalten mit Daten für jeden Benutzer. Ich möchte diese 6 Spalten nehmen und sie im Wesentlichen in Gruppen von 3 stapeln, so dass jeder Benutzer eine separate Beobachtung ist.

Dies ist ein Beispiel von mehr oder weniger, was wie meine Daten aussehen:

wide <- data.frame(
    form.ID  = c(1, 2), 
    entry.date = c("2016-07-01", "2016-06-15"), 
    user.1  = c("Joe", "Sam"), 
    user.1.ID = c("A1", "A2"), 
    user.1.data = c("foo", "lorem"), 
    user.2  = c("Jane", "Sue"), 
    user.2.ID = c("B1", "B2"), 
    user.2.data = c("bar", "ipsum") 
) 

wide 
# form.ID entry.date user.1 user.1.ID user.1.data user.2 user.2.ID user.2.data 
# 1  1 2016-07-01 Joe  A1   foo Jane  B1   bar 
# 2  2 2016-06-15 Sam  A2  lorem Sue  B2  ipsum 

Dies ist das gewünschte Endzustand:

# form.ID entry.date user user.ID user.data 
# 1  1 2016-07-01 Joe  A1   foo 
# 1  1 2016-07-01 Jane  B1   bar 
# 2  2 2016-06-15 Sam  A2  lorem  
# 2  2 2016-06-15 Sue  B2  ipsum 

ich diese Frage gefunden, aber ich kann nicht die gegebenen Antworten in meinem Fall zu arbeiten:

Gather multiple sets of columns

ich habe versucht:

Ich dachte, eine Sequenz von gather() -Funktionen wie die obige zu verwenden, aber ich erhalte doppelte Daten.

Ich habe versucht:

tall.not.quite <- gather(wide, user.n, user.name, -form.ID, -date) 
tall.not.quite 
    form.ID entry.date  user.n user.name 
1  1 2016-07-01  user.1  Joe 
2  2 2016-06-15  user.1  Sam 
3  1 2016-07-01 user.1.ID  A1 
4  2 2016-06-15 user.1.ID  A2 
5  1 2016-07-01 user.1.data  foo 
6  2 2016-06-15 user.1.data  ipsum 
7  1 2016-07-01  user.2  Jane 
8  2 2016-06-15  user.2  Sue 
9  1 2016-07-01 user.2.ID  B1 
10  2 2016-06-15 user.2.ID  B2 
11  1 2016-07-01 user.2.data  bar 
12  2 2016-06-15 user.2.data  lorem 

Denken ich dann Ausbreitung nutzen konnte(), um die user.n.ID und user.n.data Felder zu ziehen, aber ich kann das auch nicht an die Arbeit. Ich lande dort, wo ich angefangen habe.

Ich bin ziemlich gut und stecken. Dieser R Newby würde wirklich jede Hilfe schätzen.

Danke!

+1

Base-R können Sie auch nach einiger Umbenennung sie erreichen: 'Namen (breit) [3: 8] <- c ("name.1", "Id.1", "data.1",“ name.2 "," id.2 "," data.2 "); umformen (wide, idvar = c ("form.ID", "entry.date"), direction = "long", variierend = 3: 8) '- nicht wirklich eine Antwort wert, da du in der dplyr-Welt arbeitest. – thelatemail

+0

Ich wollte den Umfang der Antworten nicht mit der Struktur der Frage einschränken. Ich finde deine Antwort leichter zu verstehen. – aaron

Antwort

5

Wir können melt von data.table verwenden, die mehrere measure Spalten nehmen kann.

library(data.table) 
melt(setDT(wide), measure = patterns("\\d+$", "user.*ID$", "data$"), 
    value.name = c("user", "user.ID", "user.data"))[, 
    variable:= NULL][order(form.ID)] 
#  form.ID entry.date user user.ID user.data 
# 1:  1 2016-07-01 Joe  A1  foo 
# 2:  1 2016-07-01 Jane  B1  bar 
# 3:  2 2016-06-15 Sam  A2  lorem 
# 4:  2 2016-06-15 Sue  B2  ipsum 
+1

Ihre Lösung funktioniert perfekt. Du hast mir gerade viele (mehr) Stunden Kopfkratzen erspart. Vielen Dank! – aaron

+1

@aaron Bitte denken Sie daran, die Lösung zu akzeptieren, indem Sie auf das Häkchen neben der Abstimmung klicken. – akrun

+0

Ich wollte diese Frage noch nicht abschließen. Während Ihre Lösung an meinen Dummy-Daten arbeitete, erhalte ich Fehler in meinem realen Datensatz. Ich bin neu im data.table-Paket, also wollte ich versuchen, es zuerst zu untersuchen, bevor ich mit einer Folgefrage zurückkomme. Mach dir keine Sorgen, ich werde nicht verschwinden. :) – aaron

Verwandte Themen