L_ply: как передать атрибут имени списка в функцию?
Скажем, у меня есть список R, подобный этому:
> summary(data.list)
Length Class Mode
aug9104AP 18 data.frame list
Aug17-10_acon_7pt_dil_series_01 18 data.frame list
Aug17-10_Picro_7pt_dil_series_01 18 data.frame list
Aug17-10_PTZ_7pt_dil_series_01 18 data.frame list
Aug17-10_Verat_7pt_dil_series_01 18 data.frame list
Я хочу обработать каждый data.frame в списке с помощью l_ply
, но мне также нужно имя (например, aug9104AP), которое будет передано в функцию обработки вместе с data.frame. Что-то вроде:
l_ply(data.list,function(df,...) {
cli.name<- arg_to_access_current_list_item_name
#make plots with df, use cli.name in plot titles
#save results in a file called cli.name
}, arg_to_access_current_list_item_name
)
Что должно быть arg_to_access_current_list_item_name
?
Ответы
Ответ 1
Если вы передаете их один за другим, вы можете использовать deparse (substitute (arg)), например:
test <- function(x){
y <- deparse(substitute(x))
print(y)
print(x)
}
var <- c("one","two","three")
test(var)
[1] "var"
[1] "one" "two" "three"
для l_ply, вам придется прибегнуть к добавлению атрибута в список, например:
for(i in 1:length(data.list)){
attr(data.list[[i]],"name") <- names(data.list)[i]
}
Затем вы можете использовать attr:
cli <- attr(x,"name")
Приветствия
Ответ 2
Проще всего начинать с имен, а затем использовать их для извлечения интересующего вас фрагмента:
l_ply(names(data.list),function(name,...) {
df <- data.list[[name]]
)
Вы также можете использовать m_ply
для передачи как имени, так и данных:
m_ply(cbind(names(data.list), data.list), function(name, df, ...) {
...
}
Ответ 3
Joris ответ - самый чистый способ сделать это. Я бы добавил функцию для извлечения атрибута:
for(ename in names(data.list)) {
attr(data.list[[ename]], "ename") <- ename
}
ename <- function(x) attr(x, "ename") # states for element name
Итак, вы используете его как:
l_ply(data.list, function(df, ...) {
cli.name<- ename(df)
# make plots, save results using cli.name
})
Обычно я использую этот метод:
l_ply(names(data.list), function(cli.name, df=data.list[[cli.name]], ...) {
# make plots, save results using cli.name
})
Итерации по именам и извлечение data.frame
из исходного списка, используя их.
Только для уведомления есть взлома. Я не рекомендую, чтобы это вызывало проблемы с кадрами, и это трудно контролировать.
Используя факт, что llply
фактически представляет собой цикл for
, вы можете извлечь фактический шаг изнутри функции. Это можно сделать с помощью get
с правильной средой.
l_ply(data.list, function(df, ...) {
cli.name<- names(data.list)[get("i",parent.frame())]
# make plots, save results using cli.name
})