首页
学习
活动
专区
圈层
工具
发布

svd估算R
EN

Stack Overflow用户
提问于 2016-02-27 18:57:15
回答 2查看 1.7K关注 0票数 4

我试图使用bcv包中的SVD计算,但是所有的计算值都是相同的(按列)。

这是缺少数据http://pastebin.com/YS9qaUPs的数据集。

代码语言:javascript
复制
#load data
dataMiss = read.csv('dataMiss.csv')
#impute data
SVDimputation = round(impute.svd(dataMiss)$x, 2)
#find index of missing values
bool = apply(X = dataMiss, 2, is.na)
#put in a new data frame only the imputed value
SVDImpNA = mapply(function(x,y) x[y], as.data.frame(SVDimputation), as.data.frame(bool))
View(SVDImpNA)

head(SVDImpNA)
        V1   V2   V3
[1,] -0.01 0.01 0.01
[2,] -0.01 0.01 0.01
[3,] -0.01 0.01 0.01
[4,] -0.01 0.01 0.01
[5,] -0.01 0.01 0.01
[6,] -0.01 0.01 0.01

我哪里错了?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2016-04-21 05:15:23

impute.svd算法的工作原理如下:

  1. 用相应的列方法替换所有缺失的值。
  2. 计算得到的矩阵的秩-k逼近.
  3. 用步骤2中计算的秩-k近似中的对应值替换被计算位置中的值。
  4. 重复步骤2和3,直到收敛为止。

在示例代码中,您正在设置k=min(n,p) (默认值)。然后,在第2步中,秩-k逼近与求积矩阵完全相等.该算法经过0次迭代后收敛。也就是说,该算法将所有被估算的条目设置为列均值(如果存在数值错误,则设置与此非常接近的项)。

如果您想做一些其他事情,而不是用列来计算缺少的值,那么您需要为k使用一个较小的值。下面的代码在示例数据中演示了这一点:

代码语言:javascript
复制
> library("bcv")
> dataMiss = read.csv('dataMiss.csv')

k=3

代码语言:javascript
复制
> SVDimputation = impute.svd(dataMiss, k = 3,  maxiter=10000)$x
> table(round(SVDimputation[is.na(dataMiss)], 2))

-0.01  0.01 
531  1062 

k=2

代码语言:javascript
复制
> SVDimputation = impute.svd(dataMiss, k = 2,  maxiter=10000)$x
> table(round(SVDimputation[is.na(dataMiss)], 2))

-11.31  -6.94  -2.59  -2.52  -2.19  -2.02  -1.67  -1.63 
    25     23     61      2     54     23      5     44 
 -1.61   -1.2  -0.83   -0.8  -0.78  -0.43  -0.31  -0.15 
    14     10     13     19     39      1     14     19 
 -0.14  -0.02      0   0.01   0.02   0.03   0.06   0.17 
    83     96     94     77     30     96     82     28 
  0.46   0.53   0.55   0.56   0.83   0.91   1.26   1.53 
     1    209     83     23     28    111     16      8 
  1.77   5.63   9.99  14.34 
   112     12     33      5 

注意,对于您的数据,默认的最大迭代次数(100)太低了(我收到了警告消息)。为了解决这个问题,我设置了maxiter=10000

票数 5
EN

Stack Overflow用户

发布于 2016-02-28 00:18:51

您所描述的问题很可能是因为impute.svd最初将所有NA值设置为等于该列的均值,然后在收敛时不更改这些值。

这取决于您首先使用SVD估算的原因,但如果您是灵活的,则解决此问题的一个好方法可能是将SVD调用的级别切换到例如1。目前,k被自动设置为min(n,p),其中n= nrow,和p= not,对于您的数据来说,这意味着k= 3。例如,如果您将其设置为1(正如在impute.svd函数文档中所设置的那样),那么这个问题就不会发生:

代码语言:javascript
复制
library(bcv) 
dataMiss = read.csv("dataMiss.csv") 
SVDimputation = round(impute.svd(dataMiss, k = 1)$x, 2)

head(SVDimputation) 
      [,1]  [,2]  [,3]
[1,]  0.96 -0.23  0.52
[2,]  0.02 -0.23 -1.92
[3,] -1.87 -0.23  0.52
[4,] -0.92 -0.23  0.52
[5,]  0.49 -0.46  0.52
[6,] -1.87 -0.23  0.52
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/35674036

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档