Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/arduino/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
R-是否有一种矢量化方法/预制函数可以快速生成两个矢量之间的唯一集?_R_Performance_Unique_Vectorization_Combinations - Fatal编程技术网

R-是否有一种矢量化方法/预制函数可以快速生成两个矢量之间的唯一集?

R-是否有一种矢量化方法/预制函数可以快速生成两个矢量之间的唯一集?,r,performance,unique,vectorization,combinations,R,Performance,Unique,Vectorization,Combinations,所以,我想要的是一个数据帧,其中两个随机向量的组合在行上表示。我不想要像这样的重复组合;1,2;2,1. 只有一个。以及不重复的组合;1,1 现在我得到了这个简单的for循环,但它并不理想 unique_combos <- function(v1, v2) { df <- data.frame(matrix(ncol=2)) counter = 0 for (name1 in v1) { for (name2 in v2) {

所以,我想要的是一个数据帧,其中两个随机向量的组合在行上表示。我不想要像这样的重复组合;1,2;2,1. 只有一个。以及不重复的组合;1,1

现在我得到了这个简单的for循环,但它并不理想

unique_combos <- function(v1, v2) {
    df <- data.frame(matrix(ncol=2))
    counter = 0
    for (name1 in v1) {
        for (name2 in v2) {
            if (name1 != name2){
                counter = counter + 1
                df[counter,] <- c(name1, name2)
            }
        }
    }
    return(df)
}

# example usage;
> v1 <- c(1,2,3,4)
> v2 <- c(3,4,5,6)
> unique_combos(v1, v2)
   X1 X2
1   1  3
2   1  4
3   1  5
4   1  6
5   2  3
6   2  4
7   2  5
8   2  6
9   3  4
10  3  5
11  3  6
12  4  3
13  4  5
14  4  6
> 

unique_组合根本不需要循环。
您可以使用
expand.grid
并在一条指令中包含data.frame和repeats。然后使用逻辑索引只保留不同的行

unique_combos2 <- function(v1, v2) {
  e <- expand.grid(v1, v2)
  e <- e[e[[1]] < e[[2]], ]
  e[order(e[[1]]), ]
}


u1 <- unique_combos(v1, v2)
u2 <- unique_combos2(v1, v2)

这里的速度差可能不会有任何实际影响,除非向量很大,但是因为你把“性能”作为标签,这里有一个稍微快一点的方法

library(data.table)
CJ(v1, v2)[V1 != V2]
基准:

注: 默认情况下,
CJ
将按
v1
订购,而在
unique_combos2
中按
v1
订购需要花费大量时间,因此我删除了该部分,因为不清楚您是否需要它

unique_combos2 <- function(v1, v2) {
  e <- expand.grid(v1, v2)
  e <- e[e[[1]] != e[[2]], ]
  e
}
unique_combos3 <- function(v1, v2) CJ(v1, v2)[V1 != V2]

w1 <- sample(200)
w2 <- sample(200)
mb2 <- microbenchmark(
  u2 = unique_combos2(w1, w2),
  u3 = unique_combos3(w1, w2)
)

# Unit: milliseconds
#  expr      min       lq      mean   median       uq        max neval cld
#    u2 5.513842 5.942765 10.969386 6.692507 8.158763 368.180211   100   b
#    u3 1.140513 1.443076  1.898202 1.711384 2.139075   8.397942   100  a 

这里有一个
tidyverse
方法,主要使用
purr
工具。(编辑以澄清问题)。此方法执行以下操作:

  • 获取向量乘积集的列表,过滤它们相等的情况
  • 将列表元素转换为已排序的整数向量,并丢弃所有重复的
    unique
  • 转换回列列表结构,
    简化
    将列转换为向量,并放回数据帧中
  • 非常开放,看看是否有人能想出一种方法来浓缩一些步骤

    v1%
    唯一%>%
    转置(.names=c(“x”,“y”))%>%
    简化所有%>%
    作为_tible()
    #>#A tibble:13 x 2
    #>xy
    #>     
    #>  1     1     3
    #>  2     2     3
    #>  3     3     4
    #>  4     1     4
    #>  5     2     4
    #>  6     1     5
    #>  7     2     5
    #>  8     3     5
    #>  9     4     5
    #> 10     1     6
    #> 11     2     6
    #> 12     3     6
    #> 13     4     6
    

    由(v0.2.0)于2018-10-05创建。

    我编辑了我的帖子,组合不对!参见3-4-3组合。我想避免这种行为,只使用1而不是两者。@CasperPetersBerghopper现在是Frank使用
    的想法。我编辑了我的帖子,组合不对!参见3-4-3组合。我想避免这种行为,只需要1而不是两者。不,我不需要v1的精确顺序,我只需要combinations@Caspar我想用
    @Frank谢谢!现在一切都像我希望的那样工作:)。我不明白为什么这样做有效,你能解释一下为什么使用
    解决方案使用
    哦,好的,Ryan。另一个选择是
    unique(CJ(v1,v2)[v1>v2,c(“v1”,“v2”):=(v2,v1)])
    @Caspar它通过选择一个约定来工作(至少在后一个公式中),这样就可以保留成对的v1v2。嗨,我编辑了我的帖子,谢谢你指出仍然存在的组合(我的错误)。我不一定需要订购,我只需要独特的组合。澄清;是的,我只想要其中一个组合,不管是哪一个。编辑以解决此澄清!
    library(data.table)
    CJ(v1, v2)[V1 != V2]
    
    unique_combos2 <- function(v1, v2) {
      e <- expand.grid(v1, v2)
      e <- e[e[[1]] != e[[2]], ]
      e
    }
    unique_combos3 <- function(v1, v2) CJ(v1, v2)[V1 != V2]
    
    w1 <- sample(200)
    w2 <- sample(200)
    mb2 <- microbenchmark(
      u2 = unique_combos2(w1, w2),
      u3 = unique_combos3(w1, w2)
    )
    
    # Unit: milliseconds
    #  expr      min       lq      mean   median       uq        max neval cld
    #    u2 5.513842 5.942765 10.969386 6.692507 8.158763 368.180211   100   b
    #    u3 1.140513 1.443076  1.898202 1.711384 2.139075   8.397942   100  a 
    
    unique(CJ(v1, v2)[V1 > V2, c("V1", "V2") := .(V2, V1)])