【问题标题】:Change leaf color in plot.dendrogram like with plot.phylo of package ape像包猿的 plot.phylo 一样更改 plot.dendrogram 中的叶子颜色
【发布时间】:2013-04-17 14:25:35
【问题描述】:

我正在尝试以与使用包“ape”绘制树时相同的“样式”绘制凝聚聚类(带有 Agnes 的 UPGMA)的结果。我在下图中包含了一个简单的示例

关键问题是我希望能够根据叶子标签中的 a 模式为树状图的叶子着色。我尝试了两种方法:要么使用 hc2Newick,要么使用 Joris Meys 在对 Change Dendrogram leaves 的回答中提出的代码。两者都没有给出令人满意的输出。可能是我也不完全理解树状图的构建方式。可以在 https://www.dropbox.com/s/gke9qnvwptltkky/abundance.agnes.ave 上找到 abundance.agnes.ave 对象(从运行 agnes 中存储)的 ASCII 保存。

当我使用第一个选项时(使用 bioconductor 的 ctc 包中的 hc2Newick),我在使用此代码时得到下图:

write(hc2Newick(as.hclust(abundance.agnes.ave)),file="all_samples_euclidean.tre")
eucltree<-read.tree(file="all_samples_euclidean.tre")
eucltree.laz<-ladderize(eucltree,FALSE)
tiplabs<-eucltree$tip.label
numbertiplabs<-length(tiplabs)
colourtips<-rep("green",numbertiplabs)
colourtips[grep("II",tiplabs)]<-"red"
plot(eucltree.laz,tip.color=colourtips,adj=1,cex=0.6,use.edge.length=F)
add.scale.bar()

这显然不理想,情节的“对齐”不是我想要的。我想这与分支长度计算有关,但是我不知道如何解决这个问题。当然,与 colLab 函数的结果相比,它看起来更像是我想要报告的树状图样式。此外,在上面的代码中使用 use.edge.length=T 确实会产生一个未正确“对齐”的集群:

使用 Joris Meys 的 colLab 函数和以下代码的第二种方法给出了下图

clusDendro<-as.dendrogram(as.hclust(abundance.agnes.ave))
labelColors<-c("red","green")
clusMember<-rep(1,length(rownames(abundance.x)))
clusMember[grep("II",rownames(abundance.x))]<-2
names(clusMember)<-rownames(abundance.x)

colLab <- function(n)
{
  if(is.leaf(n)) {
    a <- attributes(n)
    # clusMember - a vector designating leaf grouping
    # labelColors - a vector of colors for the above grouping
    labCol <- labelColors[clusMember[which(names(clusMember) == a$label)]]
    attr(n, "nodePar") <- c(a$nodePar, lab.col = labCol)
  }
  n
}

clusDendro<-dendrapply(clusDendro, colLab)
plot(clusDendro,horiz=T,axes=F)

这个情节越来越接近我想要的,但是我不知道为什么叶子上会出现空心圆圈以及如何去除它们。

非常感谢任何帮助。

亲切的问候,

调频

【问题讨论】:

    标签: r dendrogram ape col dendextend


    【解决方案1】:

    这个功能现在可以在一个名为“dendextend”的新包中使用,专为这类事情而构建。

    您可以在以下 URL 的“使用”部分的演示文稿和小插曲中看到许多示例:https://github.com/talgalili/dendextend

    刚刚在以下 SO 问题中回答了一个几乎完全正确的问题:

    https://stackoverflow.com/a/18832457/256662

    【讨论】:

    • 感谢您的更新,我会尽快调查您的软件包的使用情况。我实际上只是在寻找制作“缠结图”的可能性,如您的小插图所示!
    • 我很高兴调频。此外,如果您将使用包创建一些东西 - 请考虑通过电子邮件向我发送有关您的工作的信息(我的联系方式在包 github 主页中)。我渴望展示使用此代码的真实案例研究示例,因此我很乐意宣传您的工作。祝你好运,塔尔·加利利
    【解决方案2】:

    我在很久以前编写了该代码,并且似乎在机制中发生了一些变化。

    我使用的plot.dendrogram 函数有一个参数nodePar。自从我上次使用该函数以来,行为发生了变化,虽然这通常用于内部节点,但它显然也会对外部节点产生影响。根据帮助文件,pch 现在的默认值是1:2

    因此,您需要在colLab 函数中添加到外部节点的属性中专门指定pch=NA。尝试像这样调整它:

    colLab <- function(n)
    {
      if(is.leaf(n)) {
        a <- attributes(n)
        # clusMember - a vector designating leaf grouping
        # labelColors - a vector of colors for the above grouping
        labCol <- labelColors[clusMember[which(names(clusMember) == a$label)]]
    
        attr(n, "nodePar") <- 
            if(is.list(a$nodePar)) c(a$nodePar, lab.col = labCol,pch=NA) else
                                   list(lab.col = labCol,pch=NA)
      }
      n
    }
    

    在我的机器上,这解决了问题。

    或者,您可以查看ape 包中函数plot.phylo 的参数use.edge.length。您将其设置为FALSE,但根据您的解释,我相信您希望将其设置为默认值TRUE

    编辑:为了使函数更通用,添加labelColorsclusMember 作为函数的参数可能是个好主意。我的 quick-n-dirty 解决方案不是干净代码的最佳示例...

    也忘了我所说的使用边长。猿包将其解释为真正的树状图,并将use.edge.length 放入TRUE 会将边长转换为进化时间。因此,树状图的“奇怪”轮廓。

    还要注意,如果树叶没有nodePar 属性,使用c() 函数添加额外的参数会导致不良效果:如果添加例如lab.cex=0.6c() 函数将创建一个向量而不是一个列表,并且只要参数列表中有一个字符值,就将lab.cex 的值转换为字符。在这种情况下,这将是颜色的名称,这解释了您在评论中谈到的错误。

    【讨论】:

    • 乔里斯,感谢您的回复。在我的机器上,这也解决了这个问题。关于您对use.edge.length 的评论,我已经编辑了我的原始帖子,表明我使用它得到了不受欢迎的结果。我不得不承认我对细节仍然有些模糊。例如,如果我将lab.cex 添加到节点的属性(例如)attr(n, "nodePar") &lt;- c(a$nodePar, lab.col = labCol, pch=NA, lab.cex=0.6)。我收到一条我不理解的错误消息:Error in dLeaf * lab.cex : non-numeric argument to binary operator
    猜你喜欢
    • 2015-12-02
    • 1970-01-01
    • 1970-01-01
    • 2023-02-05
    • 2012-05-03
    • 2014-05-22
    • 1970-01-01
    • 2017-06-11
    • 1970-01-01
    相关资源
    最近更新 更多