【问题标题】:Remove highly correlated variables删除高度相关的变量
【发布时间】:2013-08-18 23:56:07
【问题描述】:

我有一个巨大的数据框 5600 X 6592,我想删除任何相互关联超过 0.99 的变量我知道如何一步一步地做到这一点,即形成一个相关矩阵,四舍五入值,删除相似的并使用索引再次获取我的“减少”数据。

cor(mydata)
mydata <- round(mydata,2)
mydata <- mydata[,!duplicated (mydata)]
## then do the indexing...

我想知道这是否可以通过简短的命令或一些高级功能来完成。我正在学习如何使用 R 语言中的强大工具,从而避免如此冗长的不必要命令

我在想类似的东西

mydata <- mydata[, which(apply(mydata, 2, function(x) !duplicated(round(cor(x),2))))]

对不起,我知道上面的命令不起作用,但我希望我能做到。

适用于问题的播放数据:

mydata <- structure(list(V1 = c(1L, 2L, 5L, 4L, 366L, 65L, 43L, 456L, 876L, 
78L, 687L, 378L, 378L, 34L, 53L, 43L), V2 = c(2L, 2L, 5L, 4L, 
366L, 65L, 43L, 456L, 876L, 78L, 687L, 378L, 378L, 34L, 53L, 
41L), V3 = c(10L, 20L, 10L, 20L, 10L, 20L, 1L, 0L, 1L, 2010L, 
20L, 10L, 10L, 10L, 10L, 10L), V4 = c(2L, 10L, 31L, 2L, 2L, 5L, 
2L, 5L, 1L, 52L, 1L, 2L, 52L, 6L, 2L, 1L), V5 = c(4L, 10L, 31L, 
2L, 2L, 5L, 2L, 5L, 1L, 52L, 1L, 2L, 52L, 6L, 2L, 3L)), .Names = c("V1", 
"V2", "V3", "V4", "V5"), class = "data.frame", row.names = c(NA, 
-16L))

非常感谢

【问题讨论】:

    标签: r function subset correlation


    【解决方案1】:

    我确信有很多方法可以做到这一点,当然还有比这更好的方法,但这应该可行。我基本上只是将上面的三角形设置为零,然后删除任何值超过 0.99 的行。

    tmp <- cor(data)
    tmp[upper.tri(tmp)] <- 0
    diag(tmp) <- 0
    
    # Above two commands can be replaced with 
    # tmp[!lower.tri(tmp)] <- 0
    
     
    data.new <- 
      data[, !apply(tmp, 2, function(x) any(abs(x) > 0.99, na.rm = TRUE))]
    head(data.new)
    
       V2 V3 V5
    1   2 10  4
    2   2 20 10
    3   5 10 31
    4   4 20  2
    5 366 10  2
    6  65 20  5
    

    【讨论】:

    • 感谢大卫,它完成了工作,虽然我不知道上面的三角形是什么!我找到了 R 帮助页面,但我无法真正理解它的作用! :)
    • @Error404 upper.tri 只是用“TRUE”填充矩阵的那一部分(其余为零,也就是 FALSE),所以 tmp[upper.tri(tmp)] 只选择 tmp 的上三角部分。
    • 如果你这样做可能会更清楚data[, apply(tmp,2,function(x) all(x&lt;=0.99))] 不要使用双重否定:-)
    • 对命令进行了有趣的简化 :) 我将使用上面的三角形。谢谢朋友
    • 嗨,当我在我的数据集上使用 norm.num[, apply(tmp,2,function(x) any(x > 0.99))] 时,任何人都可以提供帮助,我收到错误消息说 Error in [.data.frame(norm.num, , !apply(tmp, 2, function(x) any(abs(x) > : undefined columns selected
    【解决方案2】:

    这是我的 R 代码,对你有帮助

    library('caret')
    
    df1 = read.csv("stack.csv")
    
    print (df1)
    
         GA     PN     PC   MBP    GR    AP
    1 0.033  6.652  6.681 0.194 0.874 3.177
    2 0.034  9.039  6.224 0.194 1.137 3.400
    3 0.035 10.936 10.304 1.015 0.911 4.900
    4 0.022 10.110  9.603 1.374 0.848 4.566
    5 0.035  2.963 17.156 0.599 0.823 9.406
    6 0.033 10.872 10.244 1.015 0.574 4.871
    7 0.035 21.694 22.389 1.015 0.859 9.259
    8 0.035 10.936 10.304 1.015 0.911 4.500
    
    
    df2 = cor(df1)
    hc = findCorrelation(df2, cutoff=0.3) # putt any value as a "cutoff" 
    hc = sort(hc)
    reduced_Data = df1[,-c(hc)]
    print (reduced_Data)
    
         GA     PN    GR    AP
    1 0.033  6.652 0.874 3.177
    2 0.034  9.039 1.137 3.400
    3 0.035 10.936 0.911 4.900
    4 0.022 10.110 0.848 4.566
    5 0.035  2.963 0.823 9.406
    6 0.033 10.872 0.574 4.871
    7 0.035 21.694 0.859 9.259
    8 0.035 10.936 0.911 4.500
    

    并将减少的数据写入新的 csv 只需使用:

    write.csv(reduced_Data, file = "outfile.csv", row.names = FALSE)
    

    【讨论】:

    • 你在哪里定义了 findCorrelation?
    • @AnkitDhingra - findCorrelation 是一个内置在 caret 包中的函数,jax 在他的第一行加载。
    • @JAX,你真是个天才!谢谢
    【解决方案3】:

    @大卫 通过提供

    abs(x) > 0.99 
    

    而不仅仅是

    x > 0.99
    

    data.new &lt;- data[,!apply(tmp,2,function(x) any(abs(x) &gt; 0.99))]

    干杯..!!!

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2020-03-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-05-24
      • 2018-03-13
      • 2020-10-20
      • 2012-12-26
      相关资源
      最近更新 更多