R:检查完整设计的功能

时间:2013-03-02 11:23:23

标签: r function

我想创建一个从1到10个向量并返回Yes或No的函数,这意味着我的所有向量都代表“完整的设计”。

这是我称之为“完整设计”的一个例子:

  

a< -c(1,1,1,1,2,2,2,2,3,3,3)

     

b< - c(1,2,1,2,1,2,1,2,1,2,1,2)

     

c< - c(1,1,2,2,1,1,2,2,1,1,2,2)

这是一个完整的设计,因为: 对于所有向量的所有级别,所有其他向量的所有级别(在相同位置)具有相同的次数。

以下是“不完整设计”的两个例子: (在以下两个示例中,a和b匹配,但c与b不匹配)

示例1:

  

a< -c(1,1,1,1,2,2,2,2,3,3,3)

     

b< - c(1,2,1,2,1,2,1,2,1,2,1,2)

     

c < - c(1,2,3,1,2,3,1,2,3,1,2,3)

示例2:

  

a&lt; -c(1,1,1,1,2,2,2,2,3,3,3)

     

b&lt; - c(1,2,1,2,1,2,1,2,1,2,1,2)

     

c&lt; - c(1,2,3,4,5,1,2,3,4,5,1,2)

希望我很清楚。整个想法是我有一个数据集,这个数据集由因子a,b,c,d,e等解释...我想要一个函数告诉我,我正在测试一个完整的或一个在运行aov()之前设计不完整。

非常感谢!

要在我想要创建的函数中询问的问题是: 当等于给定的水平时(例如,假设为2)。我们看一下b [which(a == 2)]并检查b的所有等级是否包含在b [which(a == 2)]中,并检查b的所有等级[哪个(a == 2)]重复次数相同。

2 个答案:

答案 0 :(得分:4)

使用plyr的id()函数有一种非常简单的方法:

library(plyr)
a <- c(1,1,1,1,2,2,2,2,3,3,3,3)
b <- c(1,2,1,2,1,2,1,2,1,2,1,2)
c <- c(1,1,2,2,1,1,2,2,1,1,2,2)

ids <- id(data.frame(a, b, c))
attr(ids, "n") == length(unique(ids))
# [1] TRUE

d <- c(1,1,2,2,1,1,2,2,1,1,2,3)
ids <- id(data.frame(a, b, d))
attr(ids, "n") == length(unique(ids))
# [1] FALSE

id()的工作原理是为输入中的每一行分配唯一的ID,以便有可能存在所有可能的组合。输出包含一个属性n,它给出了可能的总组合数。

答案 1 :(得分:2)

如果我理解正确,您可能会以某种方式使用interaction作为决定您的数据是否完整的第一步。

查看您的示例,似乎每个向量中的所有唯一级别应始终存在一个唯一组合(不是2,而不是0)。所以,对于你展示的第一套:

> all(table(interaction(a, b, c)) == 1)
[1] TRUE

而且,对于其他两个例子,如果你做了同样的事情,你会得到FALSE作为结果。


另一种选择是假设我们可以将变量a视为分组变量,并将所有向量放入data.frame,如下所示:

df1 <- data.frame(a = c(1,1,1,1,2,2,2,2,3,3,3,3),
                  b = c(1,2,1,2,1,2,1,2,1,2,1,2),
                  c = c(1,1,2,2,1,1,2,2,1,1,2,2))

完成后,我们可以split data.frame如下:

DF1 <- split(df1[-1], df1[1])

然后,我们可以写一个小函数来检查分裂的每个部分是否相等。我们会稍微欺骗并使用merge,但必须有更强大的方法来执行此操作。我们的想法是,如果我们在相同的输入上使用merge,那么它应该只是一个data.frame,它与所有输入data.frame相同。

这是一个(不那么强大 - 没有经过广泛测试的)功能,可以作为起点。

myFun <- function(myList) {
  all.equal(Reduce(function(x, y) 
    merge(x, y, all = TRUE, sort = FALSE), myList),
            myList[[1]], check.attributes = FALSE)
}

应用于DF1,它会向我们TRUE,但请尝试以下操作:

df2 <- data.frame(a = c(1,1,1,1,2,2,2,2,3,3,3,3),
                  b = c(1,2,1,2,1,2,1,2,1,2,1,2),
                  c = c(1,2,3,1,2,3,1,2,3,1,2,3))
df3 <- data.frame(a = c(1,1,1,1,2,2,2,2,3,3,3,3),
                  b = c(1,2,1,2,1,2,1,2,1,2,1,2),
                  c = c(1,2,3,4,5,1,2,3,4,5,1,2))

DF1 <- split(df1[-1], df1[1])
DF2 <- split(df2[-1], df2[1])
DF3 <- split(df3[-1], df3[1])

myFun(DF1)
# [1] TRUE
myFun(DF2)
# [1] "Component 1: Numeric: lengths (6, 4) differ" "Component 2: Numeric: lengths (6, 4) differ"
myFun(DF3)
# [1] "Component 1: Numeric: lengths (10, 4) differ" "Component 2: Numeric: lengths (10, 4) differ"