在保留每个数据帧中的顺序或行的同时查找

时间:2019-02-14 08:41:36

标签: r rbind

我需要合并2个数据帧,同时保留它们在每个数据帧中的出现顺序:

x = data.frame(a=1:3, b=2:4, c=3:5)
y = data.frame(a=c(10, 20, 30), b=c(20, 30, 40), c=c(30, 40, 50))

我想要的是:

> z 

a   b   c
1   2   3
10  20  30
2   3   4
20  30  40
3   4   5
30  40  50

但是rbind所做的是将第二个数据帧添加到第一个数据帧之下。

5 个答案:

答案 0 :(得分:4)

尝试这种单线模式

do.call("rbind", Map("rbind", split(x, 1:nrow(x)), split(y, 1:nrow(y))))

如果xy如问题中所示,则给出此data.frame:

      a  b  c
1.1   1  2  3
1.2  10 20 30
2.2   2  3  4
2.21 20 30 40
3.3   3  4  5
3.31 30 40 50

它将逐行拆分每个数据帧,然后将拆分拆分的相应组件。然后,它束缚了所有这些。请注意,即使列具有不同的类型,此单行代码也可以使用。例如,即使:

x <- data.frame(a = letters[1:3], b = 1:3, c = c(TRUE, FALSE, TRUE))
y <- data.frame(a = LETTERS[1:3], b = 11:13, c = c(FALSE, TRUE, FALSE))

答案 1 :(得分:3)

作为另一个基本的r版本:

x = data.frame(a=1:3, b=2:4, c=3:5)
y = data.frame(a=c(10, 20, 30), b=c(20, 30, 40), c=c(30, 40, 50))

mapply(FUN = function(i,j){rbind(i,j)}, x, y)
#>       a  b  c
#> [1,]  1  2  3
#> [2,] 10 20 30
#> [3,]  2  3  4
#> [4,] 20 30 40
#> [5,]  3  4  5
#> [6,] 30 40 50

reprex package(v0.2.1)于2019-02-14创建

答案 2 :(得分:2)

您可以在基础R中使用Paweł提供的行号提示:

x$rowid <- seq(1, nrow(x)*2, by = 2) # or simply 1:nrow(x)
y$rowid <- seq(2, nrow(y)*2, by = 2)
z <- rbind(x, y)
z[order(z$rowid),]

   a  b  c rowid
1  1  2  3     1
4 10 20 30     2
2  2  3  4     3
5 20 30 40     4
3  3  4  5     5
6 30 40 50     6

edit 也可以使用rbind()生成的行名:

z <- do.call(rbind, list(x = x, x = y))
z[order(rownames(z)), ]

      a  b  c
x.1   1  2  3
x.11 10 20 30
x.2   2  3  4
x.21 20 30 40
x.3   3  4  5
x.31 30 40 50

答案 3 :(得分:1)

您应在每个数据框中添加行号变量,并在绑定后按此变量排序。使用email,您可以按照以下步骤进行操作:

var res =  {"matchObject":"{\"data\":[{\"id\":\"jack1\",\"firstname\":\"jack\",\"lastname\":\"hudson\",\"dob\":\"1990-01-01T00:00:00.000Z\",\"email\":\"jack1@yahoo.com\",\"phone\":null,\"orgid\":\"001\"},{\"id\":\"jack2\",\"firstname\":\"Jack\",\"lastname\":\"Clinton\",\"dob\":\"1991-01-01T00:00:00.000Z\",\"email\":\"jack.clinton@yahoo.com\",\"phone\":\"+16464922600\",\"orgid\":\"002\"}]}"};
var parsedObj = JSON.parse(res.matchObject);

const extractData = (obj, type) => obj.reduce((acc, elt) => (
  elt[type] && acc.push({matchedRes: elt[type], id: elt.id, type: type})
, acc),[]);

const result = [...extractData(parsedObj.data, 'email'), ...extractData(parsedObj.data, 'phone')];

console.log(result);

答案 4 :(得分:0)

仅出于完整性考虑,也是一种data.table解决方案。

library(data.table)
dt.x <- data.table(x)
dt.y <- data.table(y)
dt.x[,Row.Num :=seq(1:.N)]
dt.y[,Row.Num :=seq(1:.N)]
rbindlist(list(dt.x,dt.y), idcol = TRUE)[order(Row.Num),]