【问题标题】:Independent axis for each subplot in pandas boxplot熊猫箱线图中每个子图的独立轴
【发布时间】:2018-11-30 22:29:32
【问题描述】:

下面的代码有助于获得带有独特颜色框的子图。但所有子图共享一组共同的 x 和 y 轴。我期待每个子图都有独立的轴:

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from matplotlib.patches import PathPatch

df = pd.DataFrame(np.random.rand(140, 4), columns=['A', 'B', 'C', 'D'])

df['models'] = pd.Series(np.repeat(['model1','model2', 'model3', 'model4',     'model5', 'model6', 'model7'], 20))

bp_dict = df.boxplot(
by="models",layout=(2,2),figsize=(6,4),
return_type='both',
patch_artist = True,
)

colors = ['b', 'y', 'm', 'c', 'g', 'b', 'r', 'k', ]
for row_key, (ax,row) in bp_dict.iteritems():
    ax.set_xlabel('')
    for i,box in enumerate(row['boxes']):
        box.set_facecolor(colors[i])

plt.show()

这是上述代码的输出:

我正在尝试为每个子图设置单独的 x 轴和 y 轴...

【问题讨论】:

    标签: python pandas dataframe matplotlib boxplot


    【解决方案1】:

    您需要事先创建图形和子图,并将其作为参数传递给df.boxplot()。这也意味着您可以删除参数layout=(2,2)

    fig, axes = plt.subplots(2,2,sharex=False,sharey=False)
    

    然后使用:

    bp_dict = df.boxplot(
    by="models", ax=axes, figsize=(6,4),
    return_type='both',
    patch_artist = True,
    )
    

    【讨论】:

    • 感谢您的回答...将布局限制为 plt.subplots 要求网格框的数量等于所需的子图。你能建议一种相对简单的方法来容纳 2xn 布局中的 13 个子图吗?如果我在 df.boxplot 中使用布局参数,那么轴保持共享..
    【解决方案2】:

    您可以将刻度标签重新设置为可见,例如通过

    plt.setp(ax.get_xticklabels(), visible=True)
    

    虽然这不会使轴独立,但它们仍然相互绑定,但您似乎在询问可见性,而不是此处的共享行为。

    【讨论】:

    • 感谢您的回答..但我的意思是为所有轴设置具有独立范围的独立轴(尤其是 ylims 需要为每个子图分开的 y 轴)。边界范围会抑制数据范围较低但轴范围较高的框的视图。
    • 在这种情况下,请参阅其他答案。
    【解决方案3】:

    如果您真的认为有必要在创建boxplot 数组之后取消共享轴,您可以这样做,但您必须“手动”完成所有操作。通过stackoverflow搜索一段时间并查看matplotlib文档页面,我想出了以下解决方案来取消共享Axes实例的yaxes,对于xaxes,您必须进行类似的操作:

    import pandas as pd
    import numpy as np
    import matplotlib.pyplot as plt
    from matplotlib.patches import PathPatch
    from matplotlib.ticker import AutoLocator, AutoMinorLocator
    
    ##using differently scaled data for the different random series:
    df = pd.DataFrame(
        np.asarray([
            np.random.rand(140),
            2*np.random.rand(140),
            4*np.random.rand(140),
            8*np.random.rand(140),
        ]).T,
        columns=['A', 'B', 'C', 'D']
    )
    
    df['models'] = pd.Series(np.repeat([
        'model1','model2', 'model3', 'model4',   'model5', 'model6', 'model7'
    ], 20))
    
    ##creating the boxplot array:
    bp_dict = df.boxplot(
        by="models",layout = (2,2),figsize=(6,8),
        return_type='both',
        patch_artist = True,
        rot = 45,
    )
    
    colors = ['b', 'y', 'm', 'c', 'g', 'b', 'r', 'k', ]
    
    ##adjusting the Axes instances to your needs
    for row_key, (ax,row) in bp_dict.items():
        ax.set_xlabel('')
    
        ##removing shared axes:
        grouper = ax.get_shared_y_axes()
        shared_ys = [a for a in grouper]
        for ax_list in shared_ys:
            for ax2 in ax_list:
                grouper.remove(ax2)
    
        ##setting limits:
        ax.axis('auto')
        ax.relim()      #<-- maybe not necessary
    
        ##adjusting tick positions:
        ax.yaxis.set_major_locator(AutoLocator())
        ax.yaxis.set_minor_locator(AutoMinorLocator())
    
        ##making tick labels visible:    
        plt.setp(ax.get_yticklabels(), visible=True)
    
        for i,box in enumerate(row['boxes']):
            box.set_facecolor(colors[i])
    
    plt.show()
    

    生成的图如下所示:

    解释

    您首先需要告诉每个Axes 实例它不应与任何其他Axis 实例共享其yaxisThis post 让我了解了如何做到这一点——Axes.get_shared_y_axes() 返回一个Grouper object,它包含对所有其他Axes 实例的引用,当前Axes 应该与之共享其xaxis。循环遍历这些实例并调用 Grouper.remove 会执行实际的取消共享。

    yaxis 取消共享后,y 限制和 y 刻度需要调整。前者可以通过ax.axis('auto')ax.relim() 实现(不确定是否需要第二条命令)。可以使用ax.yaxis.set_major_locator()ax.yaxis.set_minor_locator() 以及适当的Locators 来调整刻度。最后,可以使用plt.setp(ax.get_yticklabels(), visible=True) (see here) 使刻度标签可见。

    考虑到这一切,我认为@DavidG 的answer 是更好的方法。

    【讨论】:

      猜你喜欢
      • 2018-09-16
      • 2015-05-04
      • 2018-11-30
      • 2021-10-14
      • 2017-09-09
      • 2014-11-05
      • 2017-03-20
      • 2021-02-09
      • 2018-10-15
      相关资源
      最近更新 更多