apply()报错:'MARGIN' does not match dim(X) 求助
极大似然分类器报错排查:'MARGIN' does not match dim(X)
错误信息
Error in apply(as.array(na.omit(image_probabilities)), MARGIN = c(1, 2), : 'MARGIN' does not match dim(X) Called from: apply(as.array(na.omit(image_probabilities)), MARGIN = c(1, 2), function(pixel) { which.max(pixel) })
错误原因
- 列表转数组方式错误:
image_probabilities是存储多张二维概率图像的列表,直接用as.array()转换会生成维度混乱的数组;若列表元素维度一致,本应得到行×列×类别数的三维数组,但na.omit会破坏这个结构。 na.omit误用:na.omit()处理列表时会移除含NA的列表元素(即整个类别),导致后续转数组时维度与预期不符;即使原列表无NA,该操作也会将列表转成非预期的数组结构,使得apply的MARGIN=c(1,2)与数组维度不匹配(比如转成一维数组时,dim长度为1,无法匹配二维MARGIN)。- 未验证概率图像维度一致性:若
gaussian_class_likelihood返回的各类别概率图像维度不同,转数组时会直接变成一维数组,触发维度不匹配错误。
解决方法
步骤1:修正或移除na.omit
如果需要处理像素级NA,应在单张概率图像内部修正,而非移除整个类别:
# 循环内处理单张概率图像的NA(示例用0填充,可按需调整) image_probabilities[[i]] <- gaussian_class_likelihood(image_data, params) image_probabilities[[i]][is.na(image_probabilities[[i]])] <- 0
若无需处理NA,直接删除na.omit。
步骤2:正确堆叠列表为三维数组
将多张二维概率图像按**第三维(类别维度)**堆叠成三维数组,确保每个像素位置对应所有类别的概率值:
- 方法一(推荐,需安装
abind包):
library(abind) prob_array <- abind(image_probabilities, along = 3)
- 方法二(手动构造,需确保所有概率图像维度一致):
img_dim <- dim(image_data) prob_array <- array(unlist(image_probabilities), dim = c(img_dim[1], img_dim[2], num_classes))
步骤3:添加维度一致性检查
在循环中验证每张概率图像的维度,避免因维度不一致导致的数组错误:
for (i in 1:num_classes){ params <- gaussian_parameters_estimation(split_classes[[i]]) prob_img <- gaussian_class_likelihood(image_data, params) if (!all(dim(prob_img) == dim(image_data))) { stop(paste("类别", i, "的概率图像维度与输入图像不匹配")) } image_probabilities[[i]] <- prob_img }
修正后的完整代码
maximum_likelihood_classifier <- function(image_data, df_samples, classes) { num_classes <- length(classes) image_probabilities <- vector("list", num_classes) img_dim <- dim(image_data) split_classes <- split_classes(df_samples, classes) for (i in 1:num_classes){ params <- gaussian_parameters_estimation(split_classes[[i]]) prob_img <- gaussian_class_likelihood(image_data, params) # 验证维度一致性 if (!all(dim(prob_img) == img_dim)) { stop(paste("类别", i, "的概率图像维度与输入图像不匹配")) } # 处理像素级NA(可选) prob_img[is.na(prob_img)] <- 0 image_probabilities[[i]] <- prob_img } # 堆叠为三维数组 library(abind) prob_array <- abind(image_probabilities, along = 3) # 获取每个像素的最大概率类别 classified_image <- apply(prob_array, MARGIN = c(1, 2), function(pixel) { which.max(pixel) }) return(classified_image) }
内容的提问来源于stack exchange,提问作者Vinícius D'Lucas
相关产品推荐
相关产品推荐

