美文网首页
知识分享|多组学相关性热图实操

知识分享|多组学相关性热图实操

作者: 百易汇能 | 来源:发表于2023-05-21 09:51 被阅读0次

           本篇文章给大家带来热图的实操,大家一定要动手实践起来哦!学会了的知识才是自己的!赶紧跟着小易学习起来吧!以微生物组与代谢组联合分析作为示例,带大家复现几种相关性热图!

    1. 准备输入数据

    1) 物种丰度表(*_otu.tsv,格式如下:

    说明:第一列为物种名称,第一行为样本的名称,其他的为对应样本的物种丰度,表格用制表格分割。

    2)代谢物含量表(metabolites_*.tsv,格式如下:

    说明:第一列为代谢物id(或者名称),第一行为样本的名称,其他的为对应样本的代谢物的含量,表格用制表格分割。

    2. 脚本及运行

    2.1 相关性聚类热图

    用法:

    Rscript combine_heatmap.R genus_otu.tsv metabolites_differential.tsv prefix

    可视化示例图:

    library(psych)

    library(vegan)

    library(reshape2)

    library(ComplexHeatmap)

    library(circlize)

    options(bitmapType='cairo') #关闭服务器与界面的互动响应

    read_data <- function(data){

        data <- read.table(data, header=T, row.names=1, sep="\t", comment.char="", quote="", check.names=FALSE)

        #check.names=FALSE 保留原始表头

        data <- data[which(rowSums(data) >0),] #过滤所有丰度都为0得行    

        data <- t(data)

        return(data)

    }

    filter_pvalue_row <- function(data, pmax=0.05){#过滤P值均大于0.05的行

        r <- c()

        for(i in rownames(data)){

                if(min(data[i, ]) <= pmax){ #存在P值小于等于0.05的行

                      r <- c(r, i)

                      }else{  

                              print(i)       

                      }    

              }

              return(r)

    }

    filter_rvalue_row <- function(data, rmin=0.6){ #过滤R值均小于0.6的行

        r <- c()

        for(i in rownames(data)){

            if(max(abs(data[i, ])) >= rmin){ #存在R值大于等于0.6的行

                r <- c(r, i)

            }else{ 

               print(i)

            }

        }

        return(r)

    }

    mark_pvalue <- function(pvalue){#筛选标注哪些小于0.01小于0.05并标注

        if(!is.null(pvalue)){

            site1 <- pvalue<0.01

            pvalue[site1] <-"**"

            site2 <- pvalue >0.01& pvalue <0.05

            pvalue[site2] <-"*"

            pvalue[!site2&!site1]<-""

        }else{

            pvalue <- F

        }

        return(pvalue)

    }

    filter_pvalue <- function(pvalue, rvalue){

        indexs <- which(apply(pvalue,1, min, na.rm=TRUE) <0.05)

        pvalue <- pvalue[indexs,]

        rvalue <- rvalue[indexs,]

        r <-list(pvalue=pvalue, rvalue=rvalue)

        return(r)

    }

    size_picture <- function(data){

        rows <- nrow(data)      #计算行数

        #print(rows)

        columns <- length(data[1,])     #计算列数

        #print(columns)

        if(rows<=20) {

            widths <-20

            ratio <-1

        }elseif(rows<=50) {

            widths <-25

            ratio <-1.2

        }elseif(rows<=80){

            widths <-35

            ratio <-1.6

            }elseif(rows<=100){

            widths <-50

            ratio <-1.6

        }else{

            widths <-100

            ratio <-1.8

        }

        if(columns<=8) {

            heights <-8

        }elseif(columns<=12) {

            heights <-10

        }elseif(columns<=20) {

            heights <-15

        }else{

            heights <-20

        }

        r <-list(widths=widths, heights=heights, ratio=ratio)

    }

    correlation_analysis <- function(data1, data2, prefix){

        data1 <- read_data(data1)

        data2 <- read_data(data2)

        sample_id <- rownames(data1)

        data2 <- data2[sample_id, ] #匹配样本

        result <- corr.test(data1, data2, method="spearman", adjust="none") #计算相关性 pearson

        rvalue <- result$r

        pvalue <- result$p

        rowpid <- filter_pvalue_row(pvalue,0.05) #获取有P值小于0.05的行

        pvalue <- t(pvalue[rowpid,])

        colpid <- filter_pvalue_row(pvalue,0.05) #获取有P值小于0.05的列

        rvalue <- rvalue[rowpid, colpid]

        rowrid <- filter_rvalue_row(rvalue,0.6) #获取有R值小于0.6的行

        rvalue <- t(rvalue[rowrid,])

        colrid <- filter_rvalue_row(rvalue,0.6) #R值小于0.6的行

        rvalue <- rvalue[colrid, ]

        pvalue <- pvalue[colrid, rowrid]

        r <- filter_pvalue(pvalue, rvalue)

        rvalue <- r$rvalue

        pvalue <- r$pvalue

        result <- melt(rvalue, value.name="cor")

        result$pvalue <- as.vector(pvalue)

        write.table(result, file=paste(prefix,".correlation_pvalue.xls", sep=""), row.names=FALSE, sep="\t", quote=FALSE, na ="")

        data.1<-scale(data1)

        data.2<-scale(data2)

        rvalue<-t(rvalue)

        pvalue <- mark_pvalue(pvalue)

        pvalue<-t(pvalue)

        data.2<- data.2[,match(colnames(rvalue), colnames(data.2))]

        data.1<- t(data.1[,match(rownames(rvalue), colnames(data.1))])

        wh <- size_picture(t(data2))

        widths <- wh$widths

        heights <- wh$heights

        ratio <- wh$ratio

        col_fun = colorRamp2(c(-1,0,1), c("blue","white","red"))

        ha <- rowAnnotation(empty=anno_empty(border=FALSE),

            Microbiome=data.1, col=list(Microbiome=col_fun),

            show_legend=F, annotation_label="Microbiome", foo = anno_text(rownames(data.1)))

        p1 <- Heatmap(rvalue, name="Correlation", 

            cluster_columns=T, cluster_rows=T, show_row_names=F,

            show_heatmap_legend=TRUE, width=unit(widths*ratio,"cm"), height=unit(heights*0.55,"cm"),

            column_dend_height=unit(3,"cm"),

            cell_fun = function(j, i, x, y, width, height, fill) {

                grid.text(sprintf("%s",pvalue[i, j]), x, y, gp = gpar(fontsize =10))

            }, right_annotation=ha)

        p2 <- Heatmap(data.2, name="Metabolome", 

            column_title="Metabolome",column_title_side="bottom", cluster_columns=F, show_row_names=F, #show_row_names=T 添加样本名称 

            cluster_rows=F, width=unit(widths*ratio,"cm"), height=unit(heights*0.55,"cm"))

        lgd.list= Legend(col_fun=col_fun, title="Microbiome")

        ht = p1%v%p2

        pdf(paste(prefix,".combine_heatmap.pdf", sep=""), width=widths*1.2, height=heights)

        ptemp <- dev.cur()

        png(paste(prefix,".combine_heatmap.png", sep=""), width=widths*75, height=heights*60)

        dev.control("enable")

        draw(ht, annotation_legend_list=lgd.list, column_title="",  #不显示标题column_title="Metabolome"

            column_title_side="bottom", column_title_gp=gpar(fontface='bold',fontsize=20),        

            padding=unit(c(2,2,10,2),"mm"))

        decorate_annotation("Microbiome", {

            grid.text("Microbiome", gp=gpar(fontface='bold', fontsize=20) ,

            y=unit(1,"npc") + unit(2,"mm"), just ="bottom")}

        )

        dev.copy(which=ptemp)

        dev.off()

        dev.off()

    }

    2.2 相关性层次聚类热图

    用法:

    Rscript correlation_heatmap.R metabolites_differential.tsv genus_otu.tsv  prefix

    可视化示例图:

    library(psych)

    library(pheatmap)

    library(reshape2)

    options(bitmapType='cairo') #关闭服务器与界面的互动响应

    run_data <- function(data){

        data <- read.table(data, header=T, row.names=1, sep="\t", comment.char="",quote="", check.names=FALSE)

        #check.names=FALSE 保留原始表头

        data <- data[which(rowSums(data) > 0),] #过滤所有丰度都为0得行

        data <- t(data)

        return(data)

    }

    filter_pvalue_row <- function(data, pmax=0.05){

        #过滤P值均大于0.05的行

        r <- c()

        for (i in rownames(data)){

            if(min(data[i, ]) <= pmax){ #存在P值小于等于0.05的行

                r <- c(r, i)

            }else{

                print(i)

            }

        }

        return(r)

    }

    filter_rvalue_row <- function(data, rmin=0.6){#过滤R值均小于0.6的行

        r <- c()

        for (i in rownames(data)){

            if(max(abs(data[i, ])) >= rmin){ #存在R值大于等于0.6的行

                r <- c(r, i)

            }else{

                print(i)

            }

        }

        return(r)

    }

    mark_pvalue <- function(pvalue){

        if(!is.null(pvalue)){

            site1 <- pvalue<0.01

            pvalue[site1] <- "**"

            site2 <- pvalue > 0.01& pvalue < 0.05

            pvalue[site2] <- "*"

            pvalue[!site2&!site1]<- ""

        } else{

            pvalue <- F

        }

        return(pvalue)

    }

    filter_pvalue <- function(pvalue, rvalue){

        indexs <- which(apply(pvalue, 1, min, na.rm=TRUE) < 0.05)

        pvalue <- pvalue[indexs,]

        rvalue <- rvalue[indexs,]

        r <- list(pvalue=pvalue, rvalue=rvalue)

        return(r)

    }

    correlation_analysis <- function(data1, data2, prefix){

        data1 <- run_data(data1)

        data2 <- run_data(data2)

        sample_id <- rownames(data1)

        data2 <- data2[sample_id, ] #匹配样本

        result <- corr.test(data1, data2, method="spearman", adjust="none") #pearson

        rvalue <- result$r

        pvalue <- result$p

        rowpid <- filter_pvalue_row(pvalue, 0.05) #获取有P值小于0.05的行

        pvalue <- t(pvalue[rowpid,])

        colpid <- filter_pvalue_row(pvalue, 0.05) #获取有P值小于0.05的列

        rvalue <- rvalue[rowpid, colpid]

        rowrid <- filter_rvalue_row(rvalue, 0.6) #获取有R值小于0.6的行

        rvalue <- t(rvalue[rowrid,])

        colrid <- filter_rvalue_row(rvalue, 0.6) #R值小于0.6的行

        rvalue <- rvalue[colrid, ]

        pvalue <- pvalue[colrid, rowrid]

        r <- filter_pvalue(pvalue, rvalue)

        rvalue <- r$rvalue

        pvalue <- r$pvalue

        result <- melt(rvalue, value.name="cor")

        result$pvalue <- as.vector(pvalue)

        write.table(result, file=paste(prefix, ".correlation.xls", sep=""), row.names=FALSE, sep="\t", quote=FALSE, na ="")

        pvalue <- mark_pvalue(pvalue)

        mycol <- colorRampPalette(c("blue","white","tomato"))(800)

        pheatmap(rvalue, scale="none", cluster_row=T, cluster_col=T,

                border=NA, display_numbers=pvalue, fontsize_number=12,

                number_color = "white", cellwidth=12, cellheight=15,

                color=mycol, filename=paste(prefix, ".correlation_heatmap.pdf", sep=""))

        pheatmap(rvalue, scale="none", cluster_row=T, cluster_col=T,

                border=NA, display_numbers=pvalue, fontsize_number=12,

                number_color = "white", cellwidth=12, cellheight=15,

                color=mycol, filename=paste(prefix, ".correlation_heatmap.png", sep=""))

    }

    2.3 代谢物与微生物的相关性热图

    用法:Rscript ellipse_heatmap.R metabolites_differential.tsv genus_otu.tsv  prefix

    可视化示例图:

    library(psych)

    library(corrplot)

    library(reshape2)

    options(bitmapType='cairo') #关闭服务器与界面的互动响应

    run_data <- function(data){

        data <- read.table(data, sep="\t", header=T, row.names=1, check.names=FALSE)

        #check.names=FALSE 保留原始表头

        data <- data[which(rowSums(data) > 0),] #过滤所有丰度都为0得行

        data <- t(data)

        return(data)

    }

    filter_pvalue_row <- function(data, pmax=0.05){#过滤P值均大于0.05的行

        r <- c()

        for (i in rownames(data)){

            if(min(data[i, ]) <= pmax){ #存在P值小于等于0.05的行

                r <- c(r, i)

            }else{

                print(i)

            }

        }

        return(r)

    }

    filter_rvalue_row <- function(data, rmin=0.6){#过滤R值均小于0.6的行

        r <- c()

        for (i in rownames(data)){

            if(max(abs(data[i, ])) >= rmin){ #存在R值大于等于0.6的行

                r <- c(r, i)

            }else{

                print(i)

            }

        }

        return(r)

    }

    max_name <- function(samples){ #获取样本的最长名称长度

        maxlen <- 0

        for(i in samples){

          if(maxlen <= nchar(i)){

              maxlen <- nchar(i)

          }

        }

        return(maxlen)

    }

    ellipse_heatmap <- function(data1, data2, prefix){

        data1 <- run_data(data1)

        data2 <- run_data(data2)

        sample_id1 <- rownames(data1)  #获取样本名称

        sample_id2 <- rownames(data2)  #获取样本名称

        sample_id <- intersect(sample_id1, sample_id2)  #提取共有的样本名称

        print(sample_id)

        data1 <- data1[sample_id, ]

        data2 <- data2[sample_id, ]

        #连续数据,正态分布,线性关系,用pearson相关系数是最恰当

        #上述任一条件不满足,就用spearman相关系数,不能用pearson相关系数。

        result <- corr.test(data1, data2, method="spearman", adjust="none")

        pvalue <- result$p

        rowpid <- filter_pvalue_row(pvalue, 0.05) #获取有P值小于0.05的行

        pvalue <- t(pvalue[rowpid,])

        colpid <- filter_pvalue_row(pvalue, 0.05) #获取有P值小于0.05的列

        rvalue <- result$r

        rvalue <- rvalue[rowpid, colpid]

        rowrid <- filter_rvalue_row(rvalue, 0.6) #获取有R值小于0.6的行

        rvalue <- t(rvalue[rowrid,])

        colrid <- filter_rvalue_row(rvalue, 0.6) #R值小于0.6的行

        rvalue <- rvalue[colrid, ]

        pvalue <- pvalue[colrid, rowrid]

        #rows <- nrow(rvalue) #获取行数

        rows <-length(colrid)

        rowmaxlen <- max_name(colrid) #最长的行名称

        #columns <- length(rvalue[1,])  #获取列数目

        columns <- length(rowrid)

        colmaxlen <- max_name(rowrid) #最长的列名称

        tlcex <- 2

        if(rows<=10){

            heights <- 6

        }else if(rows<=20){

            heights <- 14

            tlcex <- 1.8

        }else if(rows<=50){

            heights <- 18

            tlcex <- 1.6

        }else{

            heights <- 22

            tlcex <- 1.4

        }

        heights <- heights + rowmaxlen*0.15 

        if(columns<=4) {

            widths <- 6

        }else if(columns<=8) {

            widths <- 10

        }else {

            widths <- 10 + (columns-8)*0.2

        }

        widths <- widths + colmaxlen*0.15

        #col1 = colorRampPalette(colors=c("red", "white", "darkgreen"), space="Lab")

        col1 = colorRampPalette(c("#7F0000", "red", "#FF7F00", "yellow", "white",

                              "cyan", "#007FFF", "blue", "#00007F"))

        pdf(paste(prefix, ".ellipse_heatmap.pdf", sep=""), width=widths, height=heights)

        a <- dev.cur()

        png(paste(prefix, ".ellipse_heatmap.png", sep=""), width=widths*60, height=heights*60)

        dev.control("enable")

        corrplot(rvalue, p.mat=pvalue, method="ellipse", tl.col="black", tl.cex=tlcex,

            insig="label_sig", sig.level=c(0.001, 0.01, 0.05),

            pch.col="black", pch.cex=0.8) #不显著相关性系数图块上有X符号,  col=col1(10)

        #corrplot(rvalue, p.mat=pvalue, method="circle", type="lower",

        #    tl.col="black", tl.cex=tlcex, tl.srt=45,

        #    insig="label_sig", sig.level=c(0.001, 0.01, 0.05),

        #    pch.col="black", pch.cex=0.8) #不显著相关性系数图块上有X符号,  col=col1(10)

        dev.copy(which=a)

        dev.off()

        dev.off()

    }

    相关文章

      网友评论

          本文标题:知识分享|多组学相关性热图实操

          本文链接:https://www.haomeiwen.com/subject/lxsasdtx.html