Я наткнулся на функцию ниже в разделе Parlist главы Expressions в Advanced R < / а>:
make_function <- function(args, body, env = parent.frame()) {
args <- as.pairlist(args)
eval(call("function", args, body), env)
}
Функция позволяет пользователю создавать функцию из ее составных частей: списка формальных аргументов, тела и окружения. Например.
add <- make_function(alist(a = 1, b = 2), quote(a + b))
add
function (a = 1, b = 2)
a + b
class(add)
[1] "function"
Мне было интересно, можно ли изменить функцию, чтобы позволить пользователю вводить строку для аргумента body
? Я пробовал parse(text = 'a + b')
, но это возвращает {{X2 }} вместо call
, как в quote(a + b)
:
class(quote(a + b))
[1] "call"
class(parse(text = 'x^m'))
[1] "expression"
Есть ли способ построить объект call
из строки?
1 ответ
Как правило, вам следует избегать синтаксического анализа произвольной строки, введенной пользователями. Обычно этого можно избежать, разработав соответствующее программное обеспечение.
В любом случае, просто извлеките язык из выражения:
make_function(alist(a = 1, b = 2), parse(text = 'a^b')[[1]])
Изменить:
Просто чтобы показать, как вы можете проверить белый список (без регулярного выражения):
whitelist <- c("+", "*", "-", "/", "^", "**", "%%", "%/%", "sin", "cos", "tan", "abs") #etc.
expr <- parse(text = "cos(x)^sin(x)*abs(x)")
foo <- function(e) if (length(e) > 1) lapply(as.list(e), foo) else return(e)
funs <- unlist(foo(expr[[1]]))
funs <- funs[vapply(funs, function(x) {x <- eval(x); is.function(x) | is.primitive(x)}, FUN.VALUE = TRUE)]
all(vapply(funs, function(x) as.character(x) %in% whitelist, FUN.VALUE = TRUE))
Анализ и оценка произвольного кода в публичном блестящем приложении представляет собой угрозу безопасности. Эта проверка гарантирует, что можно использовать только предопределенный набор функций. Если вы не избегаете меньших рисков, вы можете вместо этого просто использовать черный список (запрещающие функции, такие как system
, system2
, shell
и т. Д.).
Похожие вопросы
Новые вопросы
r
R - это бесплатный язык программирования с открытым исходным кодом и программная среда для статистических вычислений, биоинформатики, визуализации и общих вычислений. Пожалуйста, предоставьте минимальные и воспроизводимые примеры вместе с желаемым результатом. Используйте dput () для данных и укажите все небазовые пакеты с вызовами library (). Не вставляйте изображения для данных или кода, вместо этого используйте блоки кода с отступом. По вопросам, связанным со статистикой, используйте https://stats.stackexchange.com.