You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

技术问询:如何在PCoA分析图中添加性状向量/箭头?

嘿,看你已经把PCoA性状分析的前期流程走得很顺畅了——从构建物种×性状矩阵、考虑性状权重拆分,到用lingoes法校正负特征值,这几步都踩得很准!接下来要绘制带性状向量的PCoA图,我给你分享两个常用工具(R和Python)的实现方法,都是生态领域里常用的套路:

在R中绘制带性状向量的PCoA图

R里的vegan包是生态分析的利器,能轻松搞定PCoA计算和性状向量拟合:

  • 首先,用cmdscale完成带lingoes校正的PCoA计算:
    # 假设你的距离矩阵已经构建好,命名为dist_mat
    pcoa_result <- cmdscale(dist_mat, k = 2, eig = TRUE, add = TRUE, x.ret = TRUE)
    # 参数说明:k=2指定保留前2个轴,add=TRUE就是启用lingoes校正
    
  • 接着用envfit函数拟合性状与PCoA轴的相关性:
    library(vegan)
    # trait_mat是你的物种×性状矩阵(行=物种,列=性状)
    trait_fit <- envfit(pcoa_result$points, trait_mat, permutations = 999)
    # permutations设置置换次数,用于计算显著性
    
  • 最后绘制PCoA图并添加性状向量:
    # 先绘制物种点
    plot(pcoa_result$points, pch = 16, col = "darkblue", 
         xlab = paste0("PCoA 1 (", round(pcoa_result$eig[1]/sum(pcoa_result$eig)*100, 1), "%)"),
         ylab = paste0("PCoA 2 (", round(pcoa_result$eig[2]/sum(pcoa_result$eig)*100, 1), "%)"),
         main = "PCoA with Trait Vectors")
    # 添加显著的性状向量(p<0.05)
    plot(trait_fit, p.max = 0.05, col = "red", lwd = 2)
    # 加个图例更清晰
    legend("topright", legend = c("Species", "Significant Traits"), 
           pch = c(16, NA), lty = c(NA, 1), col = c("darkblue", "red"))
    

注意:性状矩阵的物种顺序必须和PCoA分析中的物种顺序完全一致,否则相关性计算会出错!如果是分类性状,记得先转换成哑变量再输入envfit。

在Python中绘制带性状向量的PCoA图

Python可以用scikit-bio做PCoA,结合matplotlib手动绘制性状向量:

  • 第一步,用scikit-bio完成lingoes校正的PCoA:
    import skbio
    # dist_mat是你的距离矩阵(可以是skbio的DistanceMatrix对象,或者普通二维数组)
    pcoa = skbio.stats.ordination.pcoa(dist_mat, correction='lingoes')
    
  • 第二步,计算性状与PCoA轴的相关性(这里用皮尔逊相关):
    import pandas as pd
    import scipy.stats as stats
    import matplotlib.pyplot as plt
    
    # trait_mat是DataFrame格式,行=物种,列=性状;pcoa.samples是PCoA坐标表
    trait_correlations = {}
    for trait in trait_mat.columns:
        # 计算性状与PC1、PC2的相关性和p值
        corr_pc1, p_pc1 = stats.pearsonr(pcoa.samples['PC1'], trait_mat[trait])
        corr_pc2, p_pc2 = stats.pearsonr(pcoa.samples['PC2'], trait_mat[trait])
        trait_correlations[trait] = (corr_pc1, corr_pc2, p_pc1, p_pc2)
    
    # 转换成DataFrame方便筛选显著性状
    corr_df = pd.DataFrame.from_dict(trait_correlations, orient='index', 
                                     columns=['PC1_corr', 'PC2_corr', 'PC1_p', 'PC2_p'])
    # 筛选p<0.05的显著性状
    sig_traits = corr_df[(corr_df['PC1_p'] < 0.05) | (corr_df['PC2_p'] < 0.05)]
    
  • 第三步,绘制PCoA图并添加性状箭头:
    fig, ax = plt.subplots(figsize=(8, 6))
    # 绘制物种点
    ax.scatter(pcoa.samples['PC1'], pcoa.samples['PC2'], c='darkblue', alpha=0.7)
    # 计算轴的范围,用于缩放箭头长度
    x_range = pcoa.samples['PC1'].max() - pcoa.samples['PC1'].min()
    y_range = pcoa.samples['PC2'].max() - pcoa.samples['PC2'].min()
    
    # 添加性状箭头
    for trait, row in sig_traits.iterrows():
        # 箭头长度用相关性乘以轴范围的0.8倍,避免超出图范围
        ax.arrow(0, 0, row['PC1_corr'] * x_range * 0.8, row['PC2_corr'] * y_range * 0.8,
                 head_width=0.05*x_range, head_length=0.05*y_range, fc='red', ec='red', lw=2)
        # 标注性状名称
        ax.text(row['PC1_corr'] * x_range * 0.9, row['PC2_corr'] * y_range * 0.9, 
                trait, color='red', fontweight='bold')
    
    # 设置轴标签和标题
    ax.set_xlabel(f"PCoA 1 ({pcoa.proportion_explained['PC1']*100:.1f}%)")
    ax.set_ylabel(f"PCoA 2 ({pcoa.proportion_explained['PC2']*100:.1f}%)")
    ax.set_title("PCoA with Trait Vectors")
    plt.grid(alpha=0.3)
    plt.show()
    

小提示:如果是分类性状,需要先做one-hot编码(比如用pandas.get_dummies),再计算相关性,不然结果会不准确。

内容的提问来源于stack exchange,提问作者Vincent H.

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.19 10:37:59