是否可以生成带有随机数的 gganimate 图?
Is it possible to generate a gganimate plot with random numbers?
我希望生成一个 gganimate
对象,它在特定范围内显示 n 个随机点。另一个限制是它应该绘制 2^n
点,即 2, 4, 8, 16, 32, 64...
点。我这样做是为了计算 pi
的小数,但我希望绘制此动画,以便我可以展示它如何以更好的方式改进给定更多随机数的结果。
这是我目前拥有的:
results <- c()
for(i in c(1:20)) {
r <- 1
limit <- 2^i
points <- data.frame(
x = runif(limit, -r, r),
y = runif(limit, -r, r))
points$d <- sqrt(points$x^2 + points$y^2)
points$type <- ifelse(points$d < r, "c", "s")
picalc <- 4 * length(points$type[points$type=="c"]) / limit
error <- pi - picalc
label <- paste0('Pi calc : ', round(picalc, 6), '\nError : ', round(error, 6))
iter <- data.frame(n = limit, picalc = picalc, error = error, label = label)
results <- rbind(results, iter)
}
# GGANIMATE
library(ggplot2)
library(gganimate)
p <- ggplot(results, aes(x = runif(n, -1, 1), y = runif(n, -1, 1))) +
geom_point(lwd = 2, alpha = 0.3) +
theme_minimal() +
geom_text(aes(x = 0, y = 0, label = label), size = 5) +
labs(caption = 'Number of random points : {frame_time}') +
transition_time(n)
animate(p, nframes = nrow(results), fps = 5)
有什么建议吗?
我会这样 "show how it improves the results given more random numbers in a nicer way."
library(ggplot2)
library(gganimate)
p <- ggplot(results, aes(x = n, y = error)) +
geom_point(lwd = 2, alpha = 0.3) +
theme_minimal() +
geom_text(aes(x = 0, y = 0, label = label), size = 5, hjust = 0) +
scale_x_log10(breaks = c(2^(1:4), 4^(2:10)), minor_breaks = NULL) +
labs(caption = 'Number of random points : {2^frame}') +
transition_manual(n) +
shadow_trail(exclude_layer = 2)
animate(p, nframes = nrow(results), fps = 5)
要显示问题中描述的那种图片,您需要用它们所属的框架标记这些点。 (此外,正如目前所写,每次迭代都会重新随机分配点。最好先设置所有点,然后坚持使用这些点,以增加 window 大小,以计算结果。)
为了快速做到这一点,我将采用最后一个 points
帧(当 i
处于循环结束时它存在),并为它应该添加的帧添加一个数字属于。然后我可以使用 transition_manual
绘制每一帧的点,并使用 shadow_trail
.
保留过去的帧
注意,如果你 运行 它有 100 万点,ggplot 会比我等待的慢,所以我做了一个删减版本,最多 2^15 = 32k。
# Note, I only ran the orig loop for 2^(1:15), lest it get too slow
points2 <- points %>%
mutate(row = row_number(),
count = 2^ceiling(log2(row)))
point_plot <- ggplot(points2,
aes(x = x, y = y, color = type, group = count)) +
geom_point(alpha = 0.6, size = 0.1) +
theme_minimal() +
labs(caption = 'Number of random points : {2^(frame-1)}') +
transition_manual(count) +
shadow_trail()
animate(point_plot, nframes = 15, fps = 2)
我希望生成一个 gganimate
对象,它在特定范围内显示 n 个随机点。另一个限制是它应该绘制 2^n
点,即 2, 4, 8, 16, 32, 64...
点。我这样做是为了计算 pi
的小数,但我希望绘制此动画,以便我可以展示它如何以更好的方式改进给定更多随机数的结果。
这是我目前拥有的:
results <- c()
for(i in c(1:20)) {
r <- 1
limit <- 2^i
points <- data.frame(
x = runif(limit, -r, r),
y = runif(limit, -r, r))
points$d <- sqrt(points$x^2 + points$y^2)
points$type <- ifelse(points$d < r, "c", "s")
picalc <- 4 * length(points$type[points$type=="c"]) / limit
error <- pi - picalc
label <- paste0('Pi calc : ', round(picalc, 6), '\nError : ', round(error, 6))
iter <- data.frame(n = limit, picalc = picalc, error = error, label = label)
results <- rbind(results, iter)
}
# GGANIMATE
library(ggplot2)
library(gganimate)
p <- ggplot(results, aes(x = runif(n, -1, 1), y = runif(n, -1, 1))) +
geom_point(lwd = 2, alpha = 0.3) +
theme_minimal() +
geom_text(aes(x = 0, y = 0, label = label), size = 5) +
labs(caption = 'Number of random points : {frame_time}') +
transition_time(n)
animate(p, nframes = nrow(results), fps = 5)
有什么建议吗?
我会这样 "show how it improves the results given more random numbers in a nicer way."
library(ggplot2)
library(gganimate)
p <- ggplot(results, aes(x = n, y = error)) +
geom_point(lwd = 2, alpha = 0.3) +
theme_minimal() +
geom_text(aes(x = 0, y = 0, label = label), size = 5, hjust = 0) +
scale_x_log10(breaks = c(2^(1:4), 4^(2:10)), minor_breaks = NULL) +
labs(caption = 'Number of random points : {2^frame}') +
transition_manual(n) +
shadow_trail(exclude_layer = 2)
animate(p, nframes = nrow(results), fps = 5)
要显示问题中描述的那种图片,您需要用它们所属的框架标记这些点。 (此外,正如目前所写,每次迭代都会重新随机分配点。最好先设置所有点,然后坚持使用这些点,以增加 window 大小,以计算结果。)
为了快速做到这一点,我将采用最后一个 points
帧(当 i
处于循环结束时它存在),并为它应该添加的帧添加一个数字属于。然后我可以使用 transition_manual
绘制每一帧的点,并使用 shadow_trail
.
注意,如果你 运行 它有 100 万点,ggplot 会比我等待的慢,所以我做了一个删减版本,最多 2^15 = 32k。
# Note, I only ran the orig loop for 2^(1:15), lest it get too slow
points2 <- points %>%
mutate(row = row_number(),
count = 2^ceiling(log2(row)))
point_plot <- ggplot(points2,
aes(x = x, y = y, color = type, group = count)) +
geom_point(alpha = 0.6, size = 0.1) +
theme_minimal() +
labs(caption = 'Number of random points : {2^(frame-1)}') +
transition_manual(count) +
shadow_trail()
animate(point_plot, nframes = 15, fps = 2)