代码之家  ›  专栏  ›  技术社区  ›  Yorgos

在R数据帧中生成交互变量

  •  18
  • Yorgos  · 技术社区  · 16 年前

    是否有一种方法(而不是for循环)在r数据帧中生成新的变量,这将是现有变量之间所有可能的双向交互? 例如,假设一个数据帧有三个数值变量v1、v2、v3,我想生成以下新变量:

    Inter.V1V2 (= V1 * V2) 
    Inter.V1V3 (= V1 * V3)
    Inter.V2V3 (= V2 * V3)
    

    循环示例:

    x <- read.table(textConnection('
       V1 V2 V3 V4
    1  9   25   18
    2  5   20   10
    3  4   30   12
    4  4   34   16'
    ), header=TRUE)
    
    dim.init <- dim(x)[2]
    for (i in 1: (dim.init - 1) ) {
            for (j in (i + 1) : (dim.init) ) {
                    x[dim(x)[2] + 1]    <- x[i] * x[j]
                    names(x)[dim(x)[2]] <- paste("Inter.V",i,"V",j,sep="")
    
            }
    }
    
    3 回复  |  直到 9 年前
        1
  •  31
  •   Ian Fellows    16 年前

    如果您有以下因素,以下是一条适用于您的单行线:

    > model.matrix(~(V1+V2+V3+V4)^2,x)
      (Intercept) V1 V2 V3 V4 V1:V2 V1:V3 V1:V4 V2:V3 V2:V4 V3:V4
    1           1  1  9 25 18     9    25    18   225   162   450
    2           1  2  5 20 10    10    40    20   100    50   200
    3           1  3  4 30 12    12    90    36   120    48   360
    4           1  4  4 34 16    16   136    64   136    64   544
    attr(,"assign")
     [1]  0  1  2  3  4  5  6  7  8  9 10
    
        2
  •  12
  •   Shane    16 年前

    给你,用 combn apply :

    > x2 <- t(apply(x, 1, combn, 2, prod))
    

    列名称的设置可以用两个 paste 命令:

    > colnames(x2) <- paste("Inter.V", combn(1:4, 2, paste, collapse="V"), sep="")
    

    最后,如果你想把所有的变量放在一起, cbind 他们:

    > x <- cbind(x, x2)
    >   V1 V2 V3 V4 Inter.V1V2 Inter.V1V3 Inter.V1V4 Inter.V2V3 Inter.V2V4 Inter.V3V4
    1  1  9 25 18          9         25         18        225        162        450
    2  2  5 20 10         10         40         20        100         50        200
    3  3  4 30 12         12         90         36        120         48        360
    4  4  4 34 16         16        136         64        136         64        544
    
        3
  •  0
  •   Rodrigo Remedio    9 年前

    我认为这个问题应该与 poly/polym 函数:它不仅在变量之间产生交互作用,而且在选定的程度之前产生它的力量。和 orthogonal iteractions 可能非常有用。

    直接解决问题的方法是:

    > polym(x$V1, x$V2, x$V3, x$V4, degree = 2, raw = T)
         1.0.0.0 2.0.0.0 0.1.0.0 1.1.0.0 0.2.0.0 0.0.1.0 1.0.1.0 0.1.1.0 0.0.2.0 0.0.0.1 1.0.0.1 0.1.0.1 0.0.1.1 0.0.0.2
    [1,]       1       1       9       9      81      25      25     225     625      18      18     162     450     324
    [2,]       2       4       5      10      25      20      40     100     400      10      20      50     200     100
    [3,]       3       9       4      12      16      30      90     120     900      12      36      48     360     144
    [4,]       4      16       4      16      16      34     136     136    1156      16      64      64     544     256
    attr(,"degree")
     [1] 1 2 1 2 2 1 2 2 2 1 2 2 2 2
    

    第4、7、8、11、12、13列提出了问题中的要求。其他列有其他类型的交互。如果你想得到正交的相互作用,只要设置 raw = FALSE .