我有一个如下所示的列表。现在我正在尝试将列表的每个data.frame中的所有rownames设置为NULL
,以便每个data.frame以1开头的rowname开头。但不知何故,它没有正确执行。
我的la la声明有些不对劲,但我无法弄清楚是什么。
代码
20function <- function (return.query) {
by.areaSize <- split(return.query, return.query$areaSize, drop = FALSE)
lapply(by.areaSize, FUN = function(x) rownames(x) <- NULL)
return(by.areaSize)
}
列表我正在申请lapply
summary(x.split)
Length Class Mode
0 28 data.frame list
10 28 data.frame list
20 28 data.frame list
30 28 data.frame list
40 28 data.frame list
50 28 data.frame list
60 28 data.frame list
70 28 data.frame list
80 28 data.frame list
90 28 data.frame list
100 28 data.frame list
110 28 data.frame list
120 28 data.frame list
130 28 data.frame list
140 28 data.frame list
150 28 data.frame list
160 28 data.frame list
170 28 data.frame list
180 28 data.frame list
190 28 data.frame list
200 28 data.frame list
210 28 data.frame list
220 28 data.frame list
230 28 data.frame list
250 28 data.frame list
260 28 data.frame list
270 28 data.frame list
280 28 data.frame list
300 28 data.frame list
330 28 data.frame list
仍然在我的lapply之后,每个data.frame中的rownames不会按预期以1开头。但是分别来自split function
的索引号。
答案 0 :(得分:4)
只需使用for
循环;这里不需要lapply()
:
list.of.dfs <- list(`0`=data.frame(a=1:3,b=letters[1:3],row.names=rnorm(3)),`10`=data.frame(x=4:6,y=letters[4:6],row.names=rnorm(3)));
list.of.dfs;
## $`0`
## a b
## 0.0498607222485908 1 a
## 0.97522800355155 2 b
## 0.128524519534542 3 c
##
## $`10`
## x y
## -0.869665657970296 4 d
## 1.45087559347205 5 e
## 0.70259805976925 6 f
##
summary(list.of.dfs);
## Length Class Mode
## 0 2 data.frame list
## 10 2 data.frame list
for (i in seq_along(list.of.dfs)) rownames(list.of.dfs[[i]]) <- NULL;
list.of.dfs;
## $`0`
## a b
## 1 1 a
## 2 2 b
## 3 3 c
##
## $`10`
## x y
## 1 4 d
## 2 5 e
## 3 6 f
##
让我试着解释一下代码中发生了什么。首先,理解R范围规则很重要。每次调用任何函数都会导致为该特定函数求值创建评估环境,并且在该函数评估期间分配的所有局部变量都存储在该环境中。功能参数也存储在该环境中。 lapply()
调用的lambda与任何其他函数没有区别。在您的情况下,这意味着lambda的x
参数成为原始列表by.areaSize
的每个元素的lambda,IOW的每个评估的新局部变量。对x
变量进行更改不会影响原始列表by.areaSize
,因为by.areaSize
是一个单独的变量,它是外部函数评估环境的本地变量(指您的函数20function()
)。
如果您确实想使用lapply()
来完成此任务,可以采用两种方法。首先,您可以迭代原始列表的索引(或名称),而不是其元素,并使用超级对齐运算符<<-
索引分配原始列表,该运算符搜索闭包环境链,直到找到LHS变量名称的匹配(或者,如果找不到,将在全局环境中创建一个新的此类变量)。这类似于我上面用for
循环所做的,除了我没有必要使用超级赋值运算符,因为我没有内部函数范围需要担心。以下是它的外观:
lapply(seq_along(by.areaSize),function(x) rownames(by.areaSize[[x]]) <<- NULL);
或者,您可以使用lapply()
调用的返回值覆盖整个原始列表,这样您就可以有效地重建&#34;重建&#34;包含从lambda返回的任何值的列表。在您的情况下,您可能希望修改x
的行名称,然后返回x
本身。目前,您的lambda实际上返回了本地赋值操作的返回值,这是RHS的值,在您的情况下为NULL。显然,这不是你想要的。以下是如何执行此操作:
by.areaSize <- lapply(by.areaSize,function(x) { rownames(x) <- NULL; x; });