R中的唯一对,忽略顺序

时间:2015-02-02 18:50:08

标签: r

说我有这样的数据框:

dat<-data.frame(c("a", "b", "c"), c("b", "a", "d"), stringsAsFactors=F)
colnames(dat)<-c("V1", "V2")
dat
#    V1  V2
# 1   a   b
# 2   b   a
# 3   c   d

我想要做的是,每行成对,生成所有唯一对,忽略顺序。所以我的输出就像是

unique_pairs(dat$V1, dat$V2)

# Output
#   V1  V2
# 1  a   b
# 2  c   d

最有效的方法是什么?

2 个答案:

答案 0 :(得分:3)

一个选项(由@bgoldst回答)是用apply分别对每一行进行排序。但是,对于使用pminpmax的单个调用,而不是使用对sort的多次调用的行,我们可以在列上运行的大型数据帧中获得更好的性能:< / p>

# Make a larger data frame by sampling
set.seed(144)
dat.large <- dat[sample(nrow(dat), 10000, replace=T),]

# Row-wise and column-wise computations
rowwise <- function(dat) unique(t(apply(dat, 1, sort)))
colwise <- function(dat) unique(cbind(pmin(dat[,1], dat[,2]), pmax(dat[,1], dat[,2])))
all.equal(unname(rowwise(dat.large)), unname(colwise(dat.large)))
# [1] TRUE

# Compare performance
library(microbenchmark)
microbenchmark(rowwise(dat.large), colwise(dat.large))
# Unit: milliseconds
#                expr       min        lq      mean    median        uq      max neval
#  rowwise(dat.large) 465.45604 523.49464 564.91541 559.14461 595.58961 805.7982   100
#  colwise(dat.large)  33.69199  42.91692  50.87839  47.70415  53.06705 122.4459   100

正如您所看到的,对于10000行输入,列式运算速度提高了大约10倍,显示了在R中计算时矢量化的强大功能。显然,从500 ms到50 ms的加速可能不是什么大问题,但是如果您正在处理大型数据集,那么矢量化方法可能更可取。

答案 1 :(得分:2)

您可以使用apply()对每一行进行排序,然后强制回data.frame(因为apply()将返回一个矩阵),然后通过unique()运行:

dat <- data.frame(c('a','b','c'), c('b','a','d'), stringsAsFactors=F );
colnames(dat) <- c('V1','V2');
x <- unique(as.data.frame(t(apply(dat, 1, sort ))));
rownames(x) <- 1:nrow(x);
x;

输出:

  V1 V2
1  a  b
2  c  d