Вопрос или проблема
У меня есть функция plot_fun
, где аргументы facet
и fill
иногда пустые. В моем реальном сценарии на самом деле есть гораздо больше аргументов. Я интересуюсь, какой хороший способ заставить ggplot
пропустить аргументы, если они пустые? Сейчас я написал много if
операторов. Это правильный подход или есть более хороший и чистый вариант?
plot_fun <- function(data, x, y, facet = c(), fill = c()){
ggplot(data, aes(x = .data[[x]], y = .data[[y]], color = .data[[fill]])) +
geom_line() +
facet_wrap(~.data[[facet]])
}
x <- "Sepal.Width"
y <- "Sepal.Length"
plot_fun(iris, x, y, facet = "Species", fill = "Species")
plot_fun(iris, x, y, facet = c(), fill = c()) # не работает
Да, вы можете использовать if
операторы:
library(ggplot2)
ggplot(data, if (length(fill) == 1L && is.character(fill)) {
aes(x = .data[[x]], y = .data[[y]], color = .data[[fill]])
} else {
aes(x = .data[[x]], y = .data[[y]])
}) +
geom_line() +
if (length(facet) == 1L && is.character(facet)) {
facet_wrap(~.data[[facet]])
} else {
list()
}
}
Ответ или решение
Чтобы создать графики с помощью ggplot2
внутри функции с динамическими аргументами, действительно существует более элегантный способ, чем множество условных операторов. Вы можете использовать конструкции в ggplot2
, которые позволяют гибко добавлять слои графика и эстетические параметры в зависимости от наличия аргументов.
Вот пример функции plot_fun
, которая корректно обрабатывает пустые аргументы facet
и fill
, используя механизм if
для добавления эстетики и фасетирования только в том случае, если аргументы не пустые:
library(ggplot2)
plot_fun <- function(data, x, y, facet = NULL, fill = NULL) {
# Инициализация базового ggplot
p <- ggplot(data, aes(x = .data[[x]], y = .data[[y]]))
# Добавление заливки, если задан аргумент fill
if (!is.null(fill) && fill != "") {
p <- p + aes(color = .data[[fill]])
}
# Добавление геометрического объекта
p <- p + geom_line()
# Добавление фасета, если задан аргумент facet
if (!is.null(facet) && facet != "") {
p <- p + facet_wrap(~ .data[[facet]])
}
return(p)
}
# Примеры использования функции
x <- "Sepal.Width"
y <- "Sepal.Length"
# С графиком с фасетом и заливкой
plot_fun(iris, x, y, facet = "Species", fill = "Species")
# С графиком без фасета и заливки
plot_fun(iris, x, y, facet = NULL, fill = NULL)
Объяснение кода:
- Анастроение параметров: Параметры
facet
иfill
инициализированы какNULL
по умолчанию, что позволяет легко проверять их наличие. - Базовый график: Сначала мы создаем основной график без дополнительных эстетик.
- Добавление эстетики: Если параметр
fill
задан и не является пустой строкой, мы добавляем его к эстетическим параметрам графика. - Добавление геометрического объекта: Добавляется линия (
geom_line()
). - Добавление фасета: Если параметр
facet
задан, он добавляется к графику.
Таким образом, вы избегаете множества условных операторов и делаете код более читабельным и простым в поддержке.