#r #plot #3d #plotly #data-visualization
Вопрос:
Я работаю с языком программирования R.
Предположим, у меня есть следующая функция:
# function: defined the first way
my_function_a <- function(x) {
final_value = sin(x[1]) cos(x[2]) x[3]
}
#function : defined the second way
my_function_b <- function(input_1, input_2, input_3) {
final_value = sin(input_1) cos(input_2) input_3
}
Цель: Я хочу оценить эту функцию в разных точках, чтобы я мог построить трехмерный график.
Первая попытка:
Я попробовал очень простой подход для оценки этой функции в ряде фиксированных точек (с использованием сетки).:
library(plotly)
library(dplyr)
#create grid and evaluate function
input_1 <- seq(0,100,1)
input_2 <- seq(0,100,1)
input_3 <- seq(0,100,1)
my_grid <- data.frame(input_1, input_2, input_3)
my_grid$final_value = sin(input_1) cos(input_2) input_3
А затем я попытался построить эту функцию:
#plot function
plot_ly() %>%
add_trace(data = my_grid, x=my_grid$input_1, y=my_grid$input_2, z=my_grid$input_3, type='mesh3d') %>%
add_surface(
z = my_grid %>% as.matrix(),
surfacecolor = my_grid,
cauto=F,
cmax=max(my_grid$final_value),
cmin=min(my_grid$final_value)
)
Сюжет этой функции выглядит обманчиво «простым».:
Затем я понял, что это происходит потому, что я оценивал эту функцию только в «равномерно расположенных» точках, например:
head(my_grid)
input_1 input_2 input_3 final_value
1 0 0 0 1.000000
2 1 1 1 2.381773
3 2 2 2 2.493151
4 3 3 3 2.151128
5 4 4 4 2.589554
6 5 5 5 4.324738
Например, в приведенном выше фрейме данных вы не найдете комбинации таких точек, как (input_1 = 5, input_2 = 2, input_3 =11)
Вторая попытка
Затем я попытался добавить некоторую «случайность», чтобы решить, в каких точках оценивать функцию:
#create grid and evaluate function
input_1 <- rnorm(100,100,20)
input_2 <- rnorm(100,100,20)
input_3 <- rnorm(100,100,20)
my_grid <- data.frame(input_1, input_2, input_3)
my_grid$final_value = sin(input_1) cos(input_2) input_3
#create plot
plot_ly() %>%
add_trace(data = my_grid, x=my_grid$input_1, y=my_grid$input_2, z=my_grid$input_3, type='mesh3d') %>%
add_surface(
z = my_grid %>% as.matrix(),
surfacecolor = my_grid,
cauto=F,
cmax=max(my_grid$final_value),
cmin=min(my_grid$final_value)
)
Теперь график, по-видимому, содержит более высокий уровень сложности, как видно из данных, используемых для создания графика:
head(my_grid)
input_1 input_2 input_3 final_value
1 82.09936 65.48251 103.26060 102.78460
2 81.94343 118.69431 76.51834 77.55103
3 76.90372 115.58958 123.96159 124.16298
4 128.52814 85.52632 69.02835 68.53927
5 96.89466 121.53117 124.39381 124.32069
6 97.59012 126.80997 87.54789 87.76038
Вопрос: Есть ли какие-либо «лучшие» способы заполнить эту сетку точками, чтобы вы могли построить «более красивый и реалистичный» сюжет? Например, можно ли создать сетку таким образом, чтобы
#iterate input_1 from 1-100 AND fix input_2 and input_3 as constant
input_1 = 1, input_2 = 1, input_3 = 1 ; input_1 = 2, input_2 = 1, input_3 = 1 ; etc; input_1 = 100, input_2 = 1, input_3 = 1
#iterate input_2 from 1-100 AND fix input_1 and input_3 as constant
input_1 = 1, input_2 = 2, input_3 = 1; input_1 = 1, input_2 = 3, input_3 = 1 , etc
Можно ли оценить «my_function_a» или «my_function_b», используя такую сетку?
Спасибо
Ответ №1:
Если я правильно понимаю, проблема вызвана my_grid
неполным заполнением.
head(my_grid)
input_1 input_2 input_3 final_value 1 0 0 0 1.000000 2 1 1 1 2.381773 3 2 2 2 2.493151 4 3 3 3 2.151128 5 4 4 4 2.589554 6 5 5 5 4.324738
Все три входные переменные выдвигаются одновременно, что создает линию в трехмерном пространстве.
Возможно, вы имели в виду использовать expand.grid()
для создания трехмерной сетки:
n <- 3
my_grid <- expand.grid(i1 = 1:n, i2 = 1:n, i3 = 1:n)
my_grid$final_value = with(my_grid, sin(i1) cos(i2) i3)
head(my_grid)
i1 i2 i3 final_value 1 1 1 1 2.3817733 2 2 1 1 2.4495997 3 3 1 1 1.6814223 4 1 2 1 1.4253241 5 2 2 1 1.4931506 6 3 2 1 0.7249732
Итак, сюжет
library(plotly)
plot_ly() %>%
add_trace(data = my_grid, x=my_grid$i1, y=my_grid$i2, z=my_grid$i3, type='mesh3d') %>%
add_surface(
z = my_grid %>% as.matrix(),
surfacecolor = my_grid,
cauto=F,
cmax=max(my_grid$final_value),
cmin=min(my_grid$final_value)
)
становится
Комментарии:
1. Я внес небольшое изменение в код построения графиков: plot_ly() %>% add_trace(данные = my_grid, x=my_grid$i1, y=my_grid$i2, z=my_grid$final_value, тип=’mesh3d’) %>>% add_surface( z = my_grid %>>>% as.matrix(), цвет поверхности = my_grid, cauto=F, cmax=макс(my_grid$final_value), cmin=мин(my_grid$окончательное значение) )
2. Я также нашел способ изменить приращения пояса: n <- 3 my_grid
3. @noob Рад, что вы нашли решение самостоятельно!
seq(from, to, by)
это тоже было бы моим предложением.