【问题标题】:Pagebreak inside Subplot? Matplotlib subplot over mulitple pages子图中的分页符?多个页面上的 Matplotlib 子图
【发布时间】:2020-01-02 17:49:57
【问题描述】:

我想创建一个能够将多个图形绘制到一个 PDF 文件中的 python 程序,但是子图的数量是可变的。我已经这样做了,每页一张图。但是,由于我有时会得到大约 100 个地块,这些地块会进行大量滚动并且并没有真正清楚地显示出来。因此,我希望每页获得 5X4 个 subpltots。 我已经为此编写了代码,整个代码很长,而且由于我对 pyhton 很陌生,所以对于知道该怎么做的人来说它看起来很糟糕,但是绘图部分看起来像这样:

rows = (len(tags))/5
fig = plt.figure()
count = 0    
for keyInTags in tags:
       count = count + 1
       ax = fig.add_subplot(int(rows), 5, count)
       ax.set_title("cell" + keyInTags)
       ax.plot(x, y_green, color='k')
       ax.plot(x, y_red, color='k')
       plt.subplots_adjust(hspace=0.5, wspace=0.3)
pdf.savefig(fig)

我的想法是我得到一个 PDF,其中绘制了所有“细胞”(用于生物学研究)。到目前为止,我编写的代码运行良好,但是如果我有超过 4 行的子图,我想做一个“pageprake”。在某些情况下,我在一页上有超过 21 行,这使得看不到任何东西。

那么,有没有解决方案,例如,告诉 Python 在 4 行后进行分页符?在有 21 行 id 的情况下,希望有 6 页具有漂亮可见图的页面。还是通过做 5x4 绘图然后以某种方式遍历文件来完成? 如果有人可以提供一点帮助或提示,我会非常高兴。我在这里坐了 4 个小时,没有找到解决办法。

【问题讨论】:

    标签: python matplotlib subplot


    【解决方案1】:

    A.循环页面

    您可以找出需要多少页 (npages) 并为每页创建一个新图形。

    import numpy as np
    import matplotlib.pyplot as plt
    from matplotlib.backends.backend_pdf import PdfPages
    
    
    tags = ["".join(np.random.choice(list("ABCDEFG123"), size=5)) for _ in range(53)]
    
    N = len(tags)  # number of subplots
    nrows = 5      # number of rows per page
    ncols = 4      # number of columns per page
    
    # calculate number of pages needed
    npages = N // (nrows*ncols)
    if N % (nrows*ncols) > 0:
        npages += 1
    
    pdf = PdfPages('out2.pdf')
    
    for page in range(npages):
        fig = plt.figure(figsize=(8,11))
        for i in range(min(nrows*ncols, N-page*(nrows*ncols))):
            # Your plot here
            count = page*ncols*nrows+i
            ax = fig.add_subplot(nrows, ncols, i+1)
            ax.set_title(f"{count} - {tags[count]}")
            ax.plot(np.cumsum(np.random.randn(33)))
            # end of plotting
    
        fig.tight_layout()
        pdf.savefig(fig)
    
    pdf.close()
    plt.show()
    

    B.循环数据

    或者,您也可以循环遍历标签本身并在需要时创建一个新图形:

    import numpy as np
    import matplotlib.pyplot as plt
    from matplotlib.backends.backend_pdf import PdfPages
    
    
    tags = ["".join(np.random.choice(list("ABCDEFG123"), size=5)) for _ in range(53)]
    
    nrows = 5      # number of rows per page
    ncols = 4      # number of columns per page
    
    pdf = PdfPages('out2.pdf')
    
    for i, tag in enumerate(tags):
        j = i % (nrows*ncols)
        if j == 0:
            fig = plt.figure(figsize=(8,11))
    
        ax = fig.add_subplot(nrows, ncols,j+1)
        ax.set_title(f"{i} - {tags[i]}")
        ax.plot(np.cumsum(np.random.randn(33)))
        # end of plotting
        if j == (nrows*ncols)-1 or i == len(tags)-1:
           fig.tight_layout()
           pdf.savefig(fig)
    
    pdf.close()
    plt.show()
    

    【讨论】:

    • 我现在用的是你的“B”版本,太棒了!万分感谢。我会玩弄它,因为我只想要绘制超过 40 个 x 值的数据。我认为在绘图之前选择数据。我们也得到了我想要被识别和标记的事件!无论如何,非常感谢:)
    【解决方案2】:

    您可以使用matplotlibPdfPages,如下所示。

    from matplotlib.backends.backend_pdf import PdfPages
    import matplotlib.pyplot as plt 
    import numpy as np
    
    pp = PdfPages('multipage.pdf')
    
    x=np.arange(1,10)
    y=np.arange(1,10)
    
    fig=plt.figure()
    ax1=fig.add_subplot(211)
    # ax1.set_title("cell" + keyInTags)
    # ax1.plot(x, y, color='k')
    # ax.plot(x, y_red, color='k')
    ax2=fig.add_subplot(212)
    
    pp.savefig(fig)
    
    fig2=plt.figure()
    ax1=fig2.add_subplot(321)
    ax1.plot(x, y, color='k')
    ax2=fig2.add_subplot(322)
    ax2.plot(x, y, color='k')
    ax3=fig2.add_subplot(313)
    
    pp.savefig(fig2)
    
    pp.close()
    

    稍微玩一下这些子图的数字,这样你就会明白如何处理哪个图去哪里了。

    【讨论】:

      猜你喜欢
      • 2015-10-20
      • 2010-11-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-10-24
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多