检查两个向量是否包含 R 中的相同(无序)元素

Check whether two vectors contain the same (unordered) elements in R

我想检查两个向量是否包含相同的元素,即使它们的顺序不同。例如,函数(我们称它为 SameElements)应满足以下条件:

SameElements(c(1, 2, 3), c(1, 2, 3))  # TRUE
SameElements(c(1, 2, 3), c(3, 2, 1))  # TRUE
SameElements(c(1, 2, 1), c(1, 2))  # FALSE
SameElements(c(1, 1, 2, 3), c(3, 2, 1))  # FALSE

编辑 1:指定当向量包含相同元素但频率不同时函数应 return F。

编辑 2:清理问题以省略初始答案,因为这是我现在的实际答案。

我想你可以使用 setequal(a,b)

Updated update setequal 检查两个向量是否由相同的元素组成,但不检查这些元素在每个向量中是否有相同的出现。

代替更清洁的替代方案,这是已知的解决方案:

SameElements <- function(a, b) return(identical(sort(a), sort(b)))
SameElements(c(1, 2, 3), c(1, 3, 2))  # TRUE
SameElements(c(1, 2, 3), c(1, 1, 3, 2))  # FALSE

编辑:根据 nrussell 的建议 identical 而不是 all.equal(...) == T

您可能对 "compare" 软件包感兴趣。 This answer demonstrates the compare() function,但对于你的情况,你可能会用compareIgnoreOrder()做得很好(它几乎与你的问题的标题完全匹配)。

有几个参数可以添加为尝试比较元素时应允许的转换。在下面的示例中(为了节省一些输入),我要求函数允许所有转换 (allowAll = TRUE) 除了更改向量长度 (shorten = FALSE).

library(compare)
compare(A1, A2, allowAll = TRUE, shorten = FALSE)
# TRUE
compare(A1, A3, allowAll = TRUE, shorten = FALSE)
# TRUE
#   sorted
compare(A1, A4, allowAll = TRUE, shorten = FALSE)
# FALSE
#   sorted
compare(B1, B2, allowAll = TRUE, shorten = FALSE)
# FALSE
#   sorted
compare(B1, A4, allowAll = TRUE, shorten = FALSE)
# FALSE
#   sorted
compare(A3f, A1, allowAll = TRUE, shorten = FALSE)
# TRUE
#   coerced from <numeric> to <factor>
#   sorted

示例数据:

A1 <- c(1, 2, 3); A2 <- c(1, 2, 3)
A3 <- c(3, 2, 1); A4 <- c(1, 1, 2, 3)
B1 <- c(1, 2, 1); B2 <- c(1, 2)
A3f <- factor(A3)

这是我的解决方案:

SameElements <- function (a,b){
  l <- Map(table,list(a, b)) # Compute frequencies - returns ordered table
  Reduce(identical,l) # Check if frequencies are the same for all input vectors
}

SameElements(c(1, 2, 3), c(1, 2, 3))  # TRUE
SameElements(c(1, 2, 3), c(3, 2, 1))  # TRUE
SameElements(c(1, 2, 1), c(1, 2))  # FALSE
SameElements(c(1, 1, 2, 3), c(3, 2, 1))  # FALSE

如您所见,它适用于任意数量的输入向量,只要您将它们全部放在一个列表中即可。

一个班轮:

Reduce(identical,Map(table,listOfVectors))

基本上你的问题可以概括为这些步骤:

if not same unique values: return FALSE
else if same Frequencies: return TRUE
    else return True

在正确的 R 代码中:

SameElements = function(v1, v2)
{
  tab1 = table(v1) ; tab2 = table(v2)
  if( !all(names(tab1) == names(tab2)) ) return(FALSE) # Same unique values test
  return(all(tab1==tab2)) # Same frequencies test
}

一些例子:

v1 = c(1, 2, 3)
v2 = c(3, 2, 1)
SameElements(v1, v2) # TRUE as both uniqueness and frequencies test are verified

v1 = c(1,1, 2,3)
v2  =c(3,2,1)
S

ameElements(v1, v2) # FALSE 因为违反了频率测试

PS : i) 您可以将 !all() 替换为 any()
~~~ii) 为了加快代码速度,当两个向量不
时,你可以快速 return FALSE ~~~具有相同的长度,从而避免频率计算。