如何遍历因子水平所有组合运行函数并将结果存入对称矩阵?
批量计算地理空间变量对的Bhattacharyya亲和度并构建对称矩阵
数据集
首先我们有包含变量及地理坐标的数据集:
set.seed(123) # example dataset: d <- data.frame(var=as.factor(rep(LETTERS[1:5],each=6)),x=runif(30),y=runif(30)) head(d) # var x y # 1 A 0.2875775 0.96302423 # 2 A 0.7883051 0.90229905 # 3 A 0.4089769 0.69070528 # 4 A 0.8830174 0.79546742 # 5 A 0.9404673 0.02461368 # 6 A 0.0455565 0.47779597
单对变量的Bhattacharyya亲和度计算示例
使用adehabitatHR包的kerneloverlap()函数可以计算两个变量的Bhattacharyya亲和度(BA),示例代码如下:
library(dplyr) library(adehabitatHR) a <- d %>% filter(var %in% c("A","B")) %>% dplyr::select(x,y) b <- d %>% filter(var %in% c("A","B")) %>% dplyr::select(var) sp_df <- SpatialPointsDataFrame(a, b) kerneloverlap(sp_df, method='BA')[1,2] # [1] 0.7217199
问题背景
kerneloverlap()仅支持一次处理两个变量,尝试循环批量计算时曾出现错误:Error in kernelUD(xy, same4all = TRUE, ...) : At least 5 relocations are required to fit an home range——虽每个变量有6个观测值,但将var改为字符向量后错误消失,却无法正确填充对称矩阵。后续使用combn()生成所有变量对并成功计算BA值,但不知道如何将值对应到对称矩阵的正确位置。
解决方案:用combn()批量计算并填充对称矩阵
我们可以利用combn()生成所有变量对,在循环中计算BA值,并将其填入对称矩阵的对应位置,同时设置对角线值为1(变量自身的亲和度为1):
library(dplyr) library(adehabitatHR) # 初始化对称矩阵,行名列名为变量水平 vars <- levels(d$var) distmat <- matrix(nrow = length(vars), ncol = length(vars), dimnames = list(vars, vars)) # 对角线设为1(自身与自身的亲和度为1) diag(distmat) <- 1 # 生成所有变量对组合 combos <- combn(vars, 2) # 循环计算每对的BA值并填充矩阵 for (i in 1:ncol(combos)) { # 获取当前变量对 var1 <- combos[1, i] var2 <- combos[2, i] # 提取对应坐标和变量,自动处理因子水平问题 subset_data <- d %>% filter(var %in% c(var1, var2)) %>% select(x, y, var) # 创建SpatialPointsDataFrame对象 sp_df <- SpatialPointsDataFrame(subset_data %>% select(x, y), subset_data %>% select(var)) # 计算BA值 ba_value <- kerneloverlap(sp_df, method='BA')[1,2] # 填充对称矩阵的两个对称位置 distmat[var1, var2] <- ba_value distmat[var2, var1] <- ba_value } # 查看最终的对称矩阵 distmat
运行后,distmat就是包含所有变量对Bhattacharyya亲和度的对称矩阵,对角线为1,其余位置为对应变量对的BA值。
内容的提问来源于stack exchange,提问作者eazyezy
相关产品推荐
相关产品推荐

