匹配R中的两个数据帧

时间:2014-02-07 14:19:16

标签: r match

我对使用匹配功能获得的输出有疑问。我有两个数据帧,它们的行数和行数不同。我希望从前两个获得两个新的数据帧,其中没有行/ rownames。一种方法是将一个数据框的rownames与另一个数据框的rownames相匹配

到目前为止,这是我的代码:

 x_1 <- c("A1", "A1", "B10", "B10", "B10", "B10", "C100", "C100", "C100", "C100")

 y_1 <- round(seq(1, 24, length = 10), 2)

 A <- data.frame(x_1, y_1)



 x_2 <- c("A1", "B10", "C100", "D1", "D200", "G210")

 y_2 <- round(seq(1, 24, length = 6), 2)

 B <-  data.frame( x_2, y_2 )

现在,由于A和B在rownames中不同,我希望制作A和B的新版本,但删除了所有不同的rownames。

 m_1 <- names(table(A$x_1))
 m_2 <- names(table(B$x_2))

 comb_names <- union(m_1[!(m_1 %in% m_2)], m_2[!(m_2 %in% m_1)])

 A_1 <- A[!A$x_1 %in% c(comb_names), ]
 B_1 <- B[!B$x_2 %in% c(comb_names), ]
 newB_1 <- B_1[match(A_1$x_1, B_1$x_2), ]

newB_1是B_1的数据框,已与A_1

中的rownames匹配

我的问题是,当我输入代码names(table(newB_1$x_2))时,我仍然会获得B_1中应该使用此代码B_1 <- B[!B$x_2 %in% c(comb_names), ]删除的所有原始rownames。但是,当我输入newB_1时,它会给我正确的输出。

names(table(newB_1$x_2))
"A1"   "B10"  "C100" "D1"   "D200" "G210"

newB_1
x_2  y_2
A1  1.0
A1  1.0
B10  5.6
B10  5.6
B10  5.6
B10  5.6
C100 10.2
C100 10.2
C100 10.2
C100 10.2

事实上,同样的事情适用于names(table(B_1$x_2)),这表明B_1 <- B[!B$x_2 %in% c(comb_names), ]不会删除上面给出的comb_names中包含的名称。

table(B_1$x_2)

A1  B10 C100   D1 D200 G210 
1    1    1    0    0    0 

最后一个问题是如何完全删除数据帧A和B不常见的rownames,以便最终得到两个具有相同rownames的数据帧?即我不希望名称D1,D200和G210出现在新的数据帧中。

我希望上述内容有道理,但我很乐意澄清任何含糊之处。我想知道如何修改我的代码以获得所需的输出,但也欢迎其他可以复制结果的替代代码。

1 个答案:

答案 0 :(得分:2)

我可能会误解,但这不是你想要的(即每个data.frame只有第一列的值出现在另一列的第一列)?

A[A$x_1 %in% B$x_2,]
#     x_1   y_1
# 1    A1  1.00
# 2    A1  3.56
# 3   B10  6.11
# 4   B10  8.67
# 5   B10 11.22
# 6   B10 13.78
# 7  C100 16.33
# 8  C100 18.89
# 9  C100 21.44
# 10 C100 24.00
B[B$x_2 %in% A$x_1,]
#    x_2  y_2
# 1   A1  1.0
# 2  B10  5.6
# 3 C100 10.2

此外,如果要连接它们,可以使用以下两种方法之一:

cbind(A, y_2=B[match(A$x_1, B$x_2), "y_2"])
merge(A, B, by=1)  # 

第一个比第二个快,但两者产生相同的输出。 match方法要快得多,但有一个限制,即B表必须在您加入的内容上是唯一的(这里就是这种情况)。

#     x_1   y_1  y_2
# 1    A1  1.00  1.0
# 2    A1  3.56  1.0
# 3   B10  6.11  5.6
# 4   B10  8.67  5.6
# 5   B10 11.22  5.6
# 6   B10 13.78  5.6
# 7  C100 16.33 10.2
# 8  C100 18.89 10.2
# 9  C100 21.44 10.2
# 10 C100 24.00 10.2    

最后,这会复制newB_1

B[match(A$x_1, B$x_2), ]
#      x_2  y_2
# 1     A1  1.0
# 1.1   A1  1.0
# 2    B10  5.6
# 2.1  B10  5.6
# 2.2  B10  5.6
# 2.3  B10  5.6
# 3   C100 10.2
# 3.1 C100 10.2
# 3.2 C100 10.2
# 3.3 C100 10.2