2016-11-26 57 views
0

这是我想在热图来显示数据:如何在统计热图中使用图形参数(par/mtext)?

structure(c(0.275131583482786, 0.313534037727115, 0.962898063173055, 0.370113551736794, 1.14085845291068, 1.02395544767755, 0.610512768755584, 0.992090676567594, 1.01157287717658, 0.679398973271326, 1.28114204694855, 0.963474557283888, 0.963249806395876, 0.952350396411827, 0.917066806607197, 0.721011695495292, 0.621362668286169, 0.905890374647831, 1.2375342589893, 0.80959426908998, 0.89503844823737, 1.33699982243824, 1.00649486312353, 0.897702695054227, 1.47859465133637, 1.00649486312353, 0.896753478691479), .Dim = c(3L, 9L), .Dimnames = list(c("Connectivity", "Dunn", "Silhouette"), c("2", "3", "4", "5", "6", "7", "8", "9", "10")), "`scaled:scale`" = structure(c(19.2058175118873, 0.0166116998686644, 0.748614066120069), .Names = c("Connectivity", "Dunn", "Silhouette"))) 

这是我的热图功能:

par(mar=c(5,5,5,5), cex=.4) 
vhm<-heatmap(vkm,Rowv = NA,Colv = NA, 
    main="Ionospheric Reflection Variance") 
mtext("K-Means Cluster Size Analysis: 2-10") 

下面是什么样子: enter image description here

我想更改:

  1. 边距:我如何在剧情的顶部和底部之间获得等量的空间?现在主标题正好对着窗口顶部,底部有太多空间。
  2. 文字大小:行名太大了。
  3. 小标题:我想把它放在主标题下面。
  4. 文本位置:我希望行名在左边,列名在右边。

我不知道为什么,似乎没有任何被工作正常,我的猜测是,这是因为该地块是从统计包,但doc说,它的建设与graphics package情节。

如何获得par和mtext与热图匹配的工作?

+0

ROW和COL名大小可以用'cexRow'和'cexCox'进行调整。 – mt1022

回答

1

通过调整heatmap的源代码,存在肮脏但不是快速的解决方案。不灵活,但稍加努力:

  1. 请参阅下面的代码中的评论a;
  2. cexRow and cexCol;
  3. 调整line;
  4. 将行轴的一侧改为右侧(请参阅下面代码中的注释b);

的是修改后的功能:

heatmap <- function (x, 
       Rowv = NULL, 
       Colv = if (symm) "Rowv" else NULL, 
       distfun = dist, 
       hclustfun = hclust, 
       reorderfun = function(d, w) reorder(d, w), 
       add.expr, 
       symm = FALSE, 
       revC = identical(Colv, "Rowv"), 
       scale = c("row", "column", "none"), 
       na.rm = TRUE, 
       margins = c(5, 5), 
       ColSideColors, 
       RowSideColors, 
       cexRow = 0.2 + 
        1/log10(nr), 
       cexCol = 0.2 + 1/log10(nc), 
       labRow = NULL, 
       labCol = NULL, 
       main = NULL, 
       xlab = NULL, 
       ylab = NULL, 
       keep.dendro = FALSE, 
       verbose = getOption("verbose"), 
       ...) 

{ 
    scale <- if (symm && missing(scale)) 
     "none" 
    else match.arg(scale) 
    if (length(di <- dim(x)) != 2 || !is.numeric(x)) 
     stop("'x' must be a numeric matrix") 
    nr <- di[1L] 
    nc <- di[2L] 
    if (nr <= 1 || nc <= 1) 
     stop("'x' must have at least 2 rows and 2 columns") 
    if (!is.numeric(margins) || length(margins) != 2L) 
     stop("'margins' must be a numeric vector of length 2") 
    doRdend <- !identical(Rowv, NA) 
    doCdend <- !identical(Colv, NA) 
    if (!doRdend && identical(Colv, "Rowv")) 
     doCdend <- FALSE 
    if (is.null(Rowv)) 
     Rowv <- rowMeans(x, na.rm = na.rm) 
    if (is.null(Colv)) 
     Colv <- colMeans(x, na.rm = na.rm) 
    if (doRdend) { 
     if (inherits(Rowv, "dendrogram")) 
      ddr <- Rowv 
     else { 
      hcr <- hclustfun(distfun(x)) 
      ddr <- as.dendrogram(hcr) 
      if (!is.logical(Rowv) || Rowv) 
       ddr <- reorderfun(ddr, Rowv) 
     } 
     if (nr != length(rowInd <- order.dendrogram(ddr))) 
      stop("row dendrogram ordering gave index of wrong length") 
    } 
    else rowInd <- 1L:nr 
    if (doCdend) { 
     if (inherits(Colv, "dendrogram")) 
      ddc <- Colv 
     else if (identical(Colv, "Rowv")) { 
      if (nr != nc) 
       stop("Colv = \"Rowv\" but nrow(x) != ncol(x)") 
      ddc <- ddr 
     } 
     else { 
      hcc <- hclustfun(distfun(if (symm) 
       x 
       else t(x))) 
      ddc <- as.dendrogram(hcc) 
      if (!is.logical(Colv) || Colv) 
       ddc <- reorderfun(ddc, Colv) 
     } 
     if (nc != length(colInd <- order.dendrogram(ddc))) 
      stop("column dendrogram ordering gave index of wrong length") 
    } 
    else colInd <- 1L:nc 
    x <- x[rowInd, colInd] 
    labRow <- if (is.null(labRow)) 
     if (is.null(rownames(x))) 
      (1L:nr)[rowInd] 
    else rownames(x) 
    else labRow[rowInd] 
    labCol <- if (is.null(labCol)) 
     if (is.null(colnames(x))) 
      (1L:nc)[colInd] 
    else colnames(x) 
    else labCol[colInd] 
    if (scale == "row") { 
     x <- sweep(x, 1L, rowMeans(x, na.rm = na.rm), check.margin = FALSE) 
     sx <- apply(x, 1L, sd, na.rm = na.rm) 
     x <- sweep(x, 1L, sx, "/", check.margin = FALSE) 
    } 
    else if (scale == "column") { 
     x <- sweep(x, 2L, colMeans(x, na.rm = na.rm), check.margin = FALSE) 
     sx <- apply(x, 2L, sd, na.rm = na.rm) 
     x <- sweep(x, 2L, sx, "/", check.margin = FALSE) 
    } 
    lmat <- rbind(c(NA, 3), 2:1) 
    lwid <- c(if (doRdend) 1 else 0.05, 4) 
    lhei <- c((if (doCdend) 1 else 0.05) + if (!is.null(main)) 0.2 else 0, 
       4) 
    if (!missing(ColSideColors)) { 
     if (!is.character(ColSideColors) || length(ColSideColors) != 
      nc) 
      stop("'ColSideColors' must be a character vector of length ncol(x)") 
     lmat <- rbind(lmat[1, ] + 1, c(NA, 1), lmat[2, ] + 1) 
     lhei <- c(lhei[1L], 0.2, lhei[2L]) 
    } 
    if (!missing(RowSideColors)) { 
     if (!is.character(RowSideColors) || length(RowSideColors) != 
      nr) 
      stop("'RowSideColors' must be a character vector of length nrow(x)") 
     lmat <- cbind(lmat[, 1] + 1, c(rep(NA, nrow(lmat) - 1), 
             1), lmat[, 2] + 1) 
     lwid <- c(lwid[1L], 0.2, lwid[2L]) 
    } 
    lmat[is.na(lmat)] <- 0 
    if (verbose) { 
     cat("layout: widths = ", lwid, ", heights = ", lhei, 
      "; lmat=\n") 
     print(lmat) 
    } 
    dev.hold() 
    on.exit(dev.flush()) 
    op <- par(no.readonly = TRUE) 
    on.exit(par(op), add = TRUE) 
    layout(lmat, widths = lwid, heights = lhei, respect = TRUE) 
    if (!missing(RowSideColors)) { 
     par(mar = c(margins[1L], 0, 0, 0.5)) 
     image(rbind(if (revC) 
      nr:1L 
      else 1L:nr), col = RowSideColors[rowInd], axes = FALSE) 
    } 
    if (!missing(ColSideColors)) { 
     par(mar = c(0.5, 0, 0, margins[2L])) 
     image(cbind(1L:nc), col = ColSideColors[colInd], axes = FALSE) 
    } 
    # -------------------------- a ----------------------- 
    # plot main figure 
    # the following line controls margins around 
    par(mar = c(margins[1L], 5, 5, margins[2L])) 
    if (!symm || scale != "none") 
     x <- t(x) 
    if (revC) { 
     iy <- nr:1 
     if (doRdend) 
      ddr <- rev(ddr) 
     x <- x[, iy] 
    } 
    else iy <- 1L:nr 
    image(1L:nc, 1L:nr, x, xlim = 0.5 + c(0, nc), ylim = 0.5 + 
       c(0, nr), axes = FALSE, xlab = "", ylab = "", ...) 
    axis(1, 1L:nc, labels = labCol, las = 2, line = -0.5, tick = 0, 
     cex.axis = cexCol) 
    if (!is.null(xlab)) 
     mtext(xlab, side = 1, line = margins[1L] - 1.25) 
    # ----------------------- b -------------------------------- 
    # which side to plot rownames: right = 2 
    axis(2, iy, labels = labRow, las = 2, line = -0.5, tick = 0, 
     cex.axis = cexRow) 
    if (!is.null(ylab)) 
     # remember to change this to 2 as well 
     mtext(ylab, side = 2, line = margins[2L] - 1.25) 
    if (!missing(add.expr)) 
     eval.parent(substitute(add.expr)) 
    # plot row dendro 
    par(mar = c(margins[1L], 0, 0, 0)) 
    if (doRdend) 
     plot(ddr, horiz = TRUE, axes = FALSE, yaxs = "i", leaflab = "none") 
    else frame() 
    # plot col dendro 
    par(mar = c(0, 0, if (!is.null(main)) 1 else 0, margins[2L])) 
    if (doCdend) 
     plot(ddc, axes = FALSE, xaxs = "i", leaflab = "none") 
    else if (!is.null(main)) 
     frame() 
    # title 
    if (!is.null(main)) { 
     par(xpd = NA, mar = c(0, 0, 1, 0)) 
     title(main, cex.main = 1.5 * op[["cex.main"]]) 
    } 
    invisible(list(rowInd = rowInd, colInd = colInd, 
        Rowv = if (keep.dendro && doRdend) ddr, 
        Colv = if (keep.dendro && doCdend) ddc)) 
} 

绘制热图:

heatmap(
    vkm, 
    Rowv = NA, 
    Colv = NA, 
    cexRow = 1, 
    cexCol = 1, 
    margins = c(3, 5), 
    main = "Ionospheric Reflection Variance" 
) 
mtext("K-Means Cluster Size Analysis: 2-10", line = 0) 

这是图中的样子: enter image description here

然而,可以这样做更灵活用ggplot2::geom_raster

library(ggplot2) 
df <- expand.grid(
    vars = rownames(vkm), 
    cols = colnames(vkm) 
) 
df$value <- c(vkm) 

ggplot(df, aes(x = cols, y = vars)) + 
    geom_raster(aes(fill = value)) + 
    scale_fill_gradient(low = 'red', high = 'yellow') + 
    ggtitle(bquote(
     atop("Ionospheric Reflection Variance", 
      atop("K-Means Cluster Size Analysis: 2-10")))) + 
    theme(
     axis.title.x = element_blank(), 
     axis.title.y = element_blank() 
    ) 

结果是: enter image description here