使用dataframe时触发is.finite(x)错误:默认方法未支持'list'类型
R代码报错:
Error in is.finite(x) : default method not implemented for type 'list' 解决方法 错误原因
- 构建
dat数据框时,z = histo将整个dataframe赋值给了列z,导致dat$z是list类型,ggplot无法处理这种非数值类型的变量。 geom_histogram(aes(histo))直接传入了dataframe对象,而ggplot的aes()需要的是数据框中的数值列名,不是整个dataframe。
修正后的代码
方式一:分图层指定数据源(推荐)
library(ggplot2) dev.new() set.seed(1684) x = seq(15, 33, by = 0.9) f <- function(x) { out <- ifelse( x < 15 | 33 < x, 0, ifelse( 15 <= x & x <= 24, (2*(x-15))/((33-15)*(24-15)), ifelse( 24 < x & x <= 33, (2*(33-x))/((33-15)*(33-24)), NA_real_ ))) if (any((is.na(out) | is.nan(out)) & (!is.na(x) & !is.nan(x)))) { warning("f(x) undefined for some input values") } out } x_accept <- numeric(0) while (length(x_accept) != 105) { x1 = runif(1, min = 15, max = 33) num = runif(1, min = 0, max = 1) if (num < (f(x1)/2/(33-15))) { x_accept = c(x_accept, x1) } } # 分别定义两个数据框,图层各自调用 line_dat <- data.frame(x = x, y = f(x)) histo_dat <- data.frame(x = x_accept) ggplot() + geom_line(data = line_dat, aes(x, y), color = "red") + geom_histogram(data = histo_dat, aes(x), alpha = .5, binwidth = 1)
方式二:合并数据后统一调用(需处理长度差异)
如果一定要合并数据,需注意x和x_accept长度不一致,可通过重复或填充NA对齐,不过这种方式不如分图层直观:
library(ggplot2) dev.new() set.seed(1684) x = seq(15, 33, by = 0.9) f <- function(x) { out <- ifelse( x < 15 | 33 < x, 0, ifelse( 15 <= x & x <= 24, (2*(x-15))/((33-15)*(24-15)), ifelse( 24 < x & x <= 33, (2*(33-x))/((33-15)*(33-24)), NA_real_ ))) if (any((is.na(out) | is.nan(out)) & (!is.na(x) & !is.nan(x)))) { warning("f(x) undefined for some input values") } out } x_accept <- numeric(0) while (length(x_accept) != 105) { x1 = runif(1, min = 15, max = 33) num = runif(1, min = 0, max = 1) if (num < (f(x1)/2/(33-15))) { x_accept = c(x_accept, x1) } } # 对齐长度后合并数据框 max_len <- max(length(x), length(x_accept)) dat <- data.frame( x_line = rep(x, length.out = max_len), y = rep(f(x), length.out = max_len), x_histo = rep(x_accept, length.out = max_len) ) ggplot(dat) + geom_line(aes(x_line, y), color = "red") + geom_histogram(aes(x_histo), alpha = .5, binwidth = 1)
关键注意点
- ggplot的图层可以通过
data参数单独指定数据源,无需强行合并所有数据到一个数据框。 - 所有
aes()中的变量必须是数据框内的数值型列,不能直接传入dataframe或list对象。
内容的提问来源于stack exchange,提问作者user20357700
相关产品推荐
相关产品推荐

