as.matrix()在R中使用列表的行为

smdncfj3  于 2023-10-13  发布在  其他
关注(0)|答案(1)|浏览(83)

因此在R中,由于data.frame是默认格式,dif类型并没有受到严格的控制,偶尔一个向量会以列表的形式出现在矩阵乘法中:

set.seed(123)
U = matrix(runif(20),5,4)
L = list(1,2,3,4)

L.mat = matrix(L)
L.asmat = as.matrix(L)
L.unlst = unlist(L)
L.unlst.mat = matrix(unlist(L))

print(L);                     class(L);          dim(L)
print(L.mat);             class(L.mat);      dim(L.mat)
print(L.asmat);         class(L.asmat);    dim(L.asmat)
print(L.unlst);         class(L.unlst);    dim(L.unlst)
print(L.unlst.mat); class(L.unlst.mat); dim(L.unlst.mat)

U %*% L
U %*% L.mat
U %*% L.asmat
U %*% L.unlst
U %*% L.unlst.mat

str(L)
str(L.mat)
str(L.asmat)
str(L.unlst)
str(L.unlst.mat)

这看起来很奇怪。基于类和维度,L.asmat和L.unlst.mat看起来是相同的,但前者是具有维度属性的列表对象,后者是具有维度属性的向量对象。它们在控制台中的显示也相同。
什么时候才能付诸实践?类似于:

V.df = data.frame(a=c(1,2,3,4), b = c(2,3,4,5), c = c(3,4,5,6))
V.sel1 = c("a")
V.sel2 = c("a", "b")
V.sub1 = V.df[,V.sel1] # the dreaded drop = TRUE 
V.sub2 = V.df[,V.sel2]
V.lst1 = lapply(V.sub1, function(x) x^2)
V.lst2 = lapply(V.sub2, function(x) x^2)

U %*% V.lst1
U %*% V.lst2

U %*% as.matrix(V.lst1); as.matrix(V.lst1) # not obvious what's going on by inspection
U %*% as.matrix(V.lst2); as.matrix(V.lst2) # obviously wrong
# not obvious what's going on by inspection
class(as.matrix(V.lst1)) 
class(as.matrix(unlist(V.lst1)))
# need to check str for the true attributes
str(as.matrix(V.lst1))
str(as.matrix(V.lst2))

所以我的主要观点是:

vec = c(1,2,3,4)
U %*% vec
U %*% as.list(vec)
U %*% as.matrix(vec)
U %*% as.matrix(as.list(vec))
U %*% as.list(as.matrix(vec))
U %*% as.list(as.matrix(as.list(vec)))
U %*% as.matrix(as.list(as.matrix(vec)))
vec.lml = as.list(as.matrix(as.list(vec))); vec.lml; str(vec.lml)
vec.mlm = as.matrix(as.list(as.matrix(vec))); vec.mlm; str(vec.mlm)
identical(vec.lml, vec.mlm)
[1] TRUE

我只是觉得as.list强制转换优于as.matrix强制转换很奇怪。如果由我来决定,我会将.matrix(list)定义为matrix(unlist(x)),以允许从vector进行往返,这是基本的R数据类型。或者至少,当在控制台中打印L.asmat时,我会这样做:

[,1]
[1,] numeric,1   
[2,] numeric,1
[3,] numeric,1 
[4,] numeric,1

不是:

[,1]
[1,] 1   
[2,] 4   
[3,] 9   
[4,] 16

来揭示矩阵中每个元素的类别。或者,也许我没有意识到这一点,但是难道不应该有一种方法来获得对象的类,并赋予维度属性,这使得对象成为矩阵吗?我可以得到“list”,但只能从类(c(L.asmat))中得到。
最后,不确定这是一个问题,一个咆哮,还是一个功能请求,但也许有人可以解释为什么.matrix(L)被定义为等同于matrix(L),当它打破了向量的往返强制时。

nxowjjhe

nxowjjhe1#

为什么不这样呢?%*%需要对矩阵进行操作,或者需要可以提升为矩阵的向量。看看这个(案例2):

str(matrix(list(1,2,3,4)))
List of 4
 $ : num 1
 $ : num 2
 $ : num 3
 $ : num 4
 - attr(*, "dim")= int [1:2] 4 1

与此相比(情况3)

str(unlist(list(1,2,3,4)))
 num [1:4] 1 2 3 4

案例2只是生成一个列表,所以%*%将抛出一个错误。情况3产生一个向量,所以矩阵乘法工作正常。有关更多信息,我建议阅读R数据结构指南。数据科学的R有a good one

相关问题