2016-11-08 98 views
1

如何合併密鑰位於一個數據集的列和R中的另一行的數據集?合併密鑰位於一個數據集的列和另一個數據集的行的數據集R

實施例的數據:

group = c("a", "b", "c", "c") 
id1 = c(1, 0, 0, 0) 
id2 = c(0, 1, 0, 1) 
id3 = c(0, 0, 1, 0) 
df1 = data.frame(group,id1, id2, id3) 
df1 

id = c("id1", "id2", "id3") 
iv1 = c(2, 3, 3) 
iv2 = c(3, 2, 3) 
df2 = data.frame(id, iv1, iv2) 
df2 

我喜歡由IDS這些兩個數據集合並。其結果

df1$iv1 = ifelse(df1$id1 == 1, 2, 3) 
df1$iv2 = ifelse(df1$id2 == 1, 2, 3) 

:我可以通過ifelse做

group id1 id2 id3 iv1 iv2 
1  a 1 0 0 2 3 
2  b 0 1 0 3 2 
3  c 0 0 1 3 3 
4  c 0 1 0 3 2 

的ifelse方法是乏味如果說,我有1000個變量進行合併。有沒有更有效的方式來合併這些數據集?

+0

df1中的ID列是互斥的嗎?你是否有這樣一種情況,即你有一行id1 = 1和id2 = 1的行?如果是這樣,預期產出是多少? – User7598

回答

4

我們可以使用第一個列順序匹配第二個行順序的事實。

df1[c("iv1", "iv2")] <- df2[max.col(df1[-1]),-1] 
# group id1 id2 id3 iv1 iv2 
# 1  a 1 0 0 2 3 
# 2  b 0 1 0 3 2 
# 3  c 0 0 1 3 3 
# 4  c 0 1 0 3 2 
0

Pierre Lafortune已經給出了很好的答案。我仍然會發布我的解決方案:

ids <- colnames(df1[, 2:4]) 
ids <- apply(df1[, 2:4], 1, function(x) return(ids[as.logical(x)])) 

df1$id <- ids 
new_df <- merge(df1, df2, by="id", all.x = TRUE, sort=FALSE) 

> new_df 
    id group id1 id2 id3 iv1 iv2 
1 id1  a 1 0 0 2 3 
2 id2  b 0 1 0 3 2 
3 id2  c 0 1 0 3 2 
4 id3  c 0 0 1 3 3 
0

Pierre和Istrel的答案都很好。對於這個和更復雜的操作,你也可以使用Hadley Wickham的流行tidyr包:

install.packages('tidyr', repos='http://cran.rstudio.org') 
library(tidyr) 

g1 <- gather(df1, idx, id_val, -group) # colnames are in 'idx'; 12 rows total 
g1 <- g1[g1$id_val==1, ]    # drop rows with id_val == 0 
g2 <- merge(g1, df2, by.x='idx', by.y='id') 
g3 <- spread(g2, idx, id_val)   # pivot the 'idx' column back out 
g3 
# group iv1 iv2 id1 id2 id3 
# 1  a 2 3 1 NA NA 
# 2  b 3 2 NA 1 NA 
# 3  c 3 2 NA 1 NA 
# 4  c 3 3 NA NA 1 
g3[is.na(g3)] <- 0 
g3 
# group iv1 iv2 id1 id2 id3 
# 1  a 2 3 1 0 0 
# 2  b 3 2 0 1 0 
# 3  c 3 2 0 1 0 
# 4  c 3 3 0 0 1 
相關問題