我有一个包含51608个变量(列)的9个样本(行)的数据集,每当我尝试缩放它时,我都会收到错误:
这很好用
pca = prcomp(pca_data)
然而,
pca = prcomp(pca_data, scale = T)
给出
> Error in prcomp.default(pca_data, center = T, scale = T) :
cannot rescale a constant/zero column to unit variance
显然,发布一个可重复的例子有点困难。有什么想法可以达成协议吗?
寻找恒定列:
sapply(1:ncol(pca_data), function(x){
length = unique(pca_data[, x]) %>% length
}) %>% table
输出:
.
2 3 4 5 6 7 8 9
3892 4189 2124 1783 1622 2078 5179 30741
所以没有恒定的列。与NA'相同 -
is.na(pca_data) %>% sum
>[1] 0
这很好用:
pca_data = scale(pca_data)
但之后两人仍然给出完全相同的错误:
pca = prcomp(pca_data)
pca = prcomp(pca_data, center = F, scale = F)
那么为什么我无法在这些数据上获得缩放的pca?好的,让我们100%确定它不是恒定的。
pca_data = pca_data + rnorm(nrow(pca_data) * ncol(pca_data))
相同的错误。 Numierc数据?
sapply( 1:nrow(pca_data), function(row){
sapply(1:ncol(pca_data), function(column){
!is.numeric(pca_data[row, column])
})
} ) %>% sum
仍然是同样的错误。我没有想法。
编辑:更多,至少要解决它。
稍后,仍然很难聚集这些数据,例如:
Error in hclust(d, method = "ward.D") :
NaN dissimilarity value in intermediate results.
在特定截止值下修剪值,例如< 1到零无效。最终工作的是修剪列中包含多于x个零的所有列。为#zeros< = 6工作,但是7+给出了错误。不知道这是否意味着这一般是一个问题,或者是否恰好碰到了一个有问题的专栏。仍然会很高兴听到有人有任何想法,因为只要没有变量全是零(或以其他方式不变),这应该可以正常工作。
答案 0 :(得分:16)
我认为你没有正确地寻找零方差列。让我们尝试一些虚拟数据。首先,一个可接受的矩阵:10x100:
mat <- matrix(rnorm(1000, 0), nrow = 10)
一个零方差列。我们称之为oopsmat
。
const <- rep(0.1,100)
oopsmat <- cbind(const, mat)
oopsmat
的前几个元素如下所示:
const
[1,] 0.1 0.75048899 0.5997527 -0.151815650 0.01002536 0.6736613 -0.225324647 -0.64374844 -0.7879052
[2,] 0.1 0.09143491 -0.8732389 -1.844355560 0.23682805 0.4353462 -0.148243210 0.61859245 0.5691021
[3,] 0.1 -0.80649512 1.3929716 -1.438738923 -0.09881381 0.2504555 -0.857300053 -0.98528008 0.9816383
[4,] 0.1 0.49174471 -0.8110623 -0.941413109 -0.70916436 1.3332522 0.003040624 0.29067871 -0.3752594
[5,] 0.1 1.20068447 -0.9811222 0.928731706 -1.97469637 -1.1374734 0.661594937 2.96029102 0.6040814
让我们在oopsmat
上尝试按比例缩放和取消缩放的PCA:
PCs <- prcomp(oopsmat) #works
PCs <- prcomp(oopsmat, scale. = T) #not forgetting the dot
#Error in prcomp.default(oopsmat, scale. = T) :
#cannot rescale a constant/zero column to unit variance
因为如果它是无穷大,你不能除以标准偏差。要识别零方差列,我们可以使用which
如下获取变量名称。
which(apply(oopsmat, 2, var)==0)
#const
#1
要从数据集中删除零方差列,您可以使用相同的apply
表达式,设置方差不等于零。
oopsmat[ , apply(oopsmat, 2, var) != 0]
希望有助于使事情更清楚!
答案 1 :(得分:2)
错误是因为其中一列具有常量值。
计算所有数值列的标准偏差,以找到零方差变量。
如果标准偏差为零,则可以删除变量并计算pca
答案 2 :(得分:1)
除了Joe的答案,只需检查数据框中列的类是否为数字即可。
如果有整数,则方差为0,导致缩放失败。
如果
class(my_df$some_column)
例如,是一个整数64,然后执行以下操作
my_df$some_column <- as.numeric(my_df$some_column)
希望这对某人有帮助。