【问题标题】:Multiple imshow-subplots, each with colorbar多个 imshow-subplots,每个都有颜色条
【发布时间】:2013-08-18 11:11:22
【问题描述】:

我想要一个由四个子图组成的图形。其中两个是通常的线图,其中两个是 imshow-images。

我可以将 imshow-images 格式化为正确的绘图本身,因为它们中的每一个都需要自己的颜色条、修改后的轴和删除另一个轴。 然而,这似乎对子图毫无用处。谁能帮我解决这个问题?

我使用它来将上面“常规”图的数据显示为颜色图(通过将输入数组 i 缩放为 2D 的 [ i, i, i, i, i, i ] 并用它调用 imshow())。

下面的代码首先显示了我需要的子图,第二个显示了我能做的一切,这还不够。

#!/usr/bin/env python

import matplotlib.pyplot as plt
from matplotlib.colors import LogNorm

s = { 't':1, 'x':[1,2,3,4,5,6,7,8], 'D':[0.3,0.5,0.2,0.3,0.5,0.5,0.3,0.4] }
width = 40

# how I do it in just one plot
tot = []
for i in range(width):
    tot.append(s['D'])

plt.imshow(tot, norm=LogNorm(vmin=0.001, vmax=1))
plt.colorbar()
plt.axes().axes.get_xaxis().set_visible(False)
plt.yticks([0, 2, 4, 6], [s['x'][0], s['x'][2], s['x'][4], s['x'][6]])

plt.show()


f = plt.figure(figsize=(20,20))

plt.subplot(211)
plt.plot(s['x'], s['D'])
plt.ylim([0, 1])

#colorplot
sp = f.add_subplot(212)

#reshape (just necessary to see something)
tot = []
for i in range(width):
    tot.append(s['D'])

sp.imshow(tot, norm=LogNorm(vmin=0.001, vmax=1))

    #what I can't do now but needs to be done:
    #sp.colorbar()
#sp.axes().axes.get_xaxis().set_visible(False)
#sp.yticks([0, 200, 400, 600, 800, 1000], [s['x'][0], s['x'][200], s['x'][400], s['x'][600], s['x'][800], s['x'][1000]])

plt.show()

【问题讨论】:

  • 您的示例无法运行!您能否为 s 和 tot 添加一些示例数据,以便我们可以看到您正在查看的内容?为了完整起见,如果每个示例都以 show 命令结束,那也很好。
  • 抱歉,我添加了可运行代码。
  • 您不需要所有这些cla 命令。此外,在发布示例时,最容易绘制随机数据(除非问题取决于数据的确切值)。
  • 请将此代码减少到显示您的问题所需的最小值
  • 完成。 [一些字母来完成分钟。字符要求]

标签: python matplotlib


【解决方案1】:

您可以使用 matplotlibs 面向对象的接口而不是状态机接口,以便更好地控制每个轴。此外,要控制颜色条的高度/宽度,您可以使用 matplotlib 的 AxesGrid 工具包。

例如:

import matplotlib.pyplot as plt
import numpy as np
from mpl_toolkits.axes_grid1 import make_axes_locatable
from matplotlib.colors import LogNorm
from matplotlib.ticker import MultipleLocator

s = {'t': 1,
     'x': [1, 2, 3, 4, 5, 6, 7, 8],
     'T': [0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8],
     'D': [0.3, 0.5, 0.2, 0.3, 0.5, 0.5, 0.3, 0.4]}

width = 40

tot = np.repeat(s['D'],width).reshape(len(s['D']), width)
tot2 = np.repeat(s['T'],width).reshape(len(s['D']), width)

fig, (ax1, ax2, ax3, ax4) = plt.subplots(1,4)

fig.suptitle('Title of figure', fontsize=20)

# Line plots
ax1.set_title('Title of ax1')
ax1.plot(s['x'], s['T'])
ax1.set_ylim(0,1)

ax2.set_title('Title of ax2')
ax2.plot(s['x'], s['D'])
# Set locations of ticks on y-axis (at every multiple of 0.25)
ax2.yaxis.set_major_locator(MultipleLocator(0.25))
# Set locations of ticks on x-axis (at every multiple of 2)
ax2.xaxis.set_major_locator(MultipleLocator(2))
ax2.set_ylim(0,1)

ax3.set_title('Title of ax3')
# Display image, `aspect='auto'` makes it fill the whole `axes` (ax3)
im3 = ax3.imshow(tot, norm=LogNorm(vmin=0.001, vmax=1), aspect='auto')
# Create divider for existing axes instance
divider3 = make_axes_locatable(ax3)
# Append axes to the right of ax3, with 20% width of ax3
cax3 = divider3.append_axes("right", size="20%", pad=0.05)
# Create colorbar in the appended axes
# Tick locations can be set with the kwarg `ticks`
# and the format of the ticklabels with kwarg `format`
cbar3 = plt.colorbar(im3, cax=cax3, ticks=MultipleLocator(0.2), format="%.2f")
# Remove xticks from ax3
ax3.xaxis.set_visible(False)
# Manually set ticklocations
ax3.set_yticks([0.0, 2.5, 3.14, 4.0, 5.2, 7.0])

ax4.set_title('Title of ax4')
im4 = ax4.imshow(tot2, norm=LogNorm(vmin=0.001, vmax=1), aspect='auto')
divider4 = make_axes_locatable(ax4)
cax4 = divider4.append_axes("right", size="20%", pad=0.05)
cbar4 = plt.colorbar(im4, cax=cax4)
ax4.xaxis.set_visible(False)
# Manually set ticklabels (not ticklocations, they remain unchanged)
ax4.set_yticklabels([0, 50, 30, 'foo', 'bar', 'baz'])

plt.tight_layout()
# Make space for title
plt.subplots_adjust(top=0.85)
plt.show()


您可以使用set_ticksset_ticklabels 方法更改任一轴上刻度的位置和标签,如上例所示。


至于make_axes_locatable函数的作用,来自matplotlib site about the AxesGrid toolkit

axes_divider 模块提供了一个辅助函数 make_axes_locatable,这很有用。它需要一个现有的轴 实例并为其创建一个分隔符。

ax = subplot(1,1,1)
divider = make_axes_locatable(ax)

make_axes_locatable 返回 AxesLocator 类的一个实例, 源自定位器。它提供了 append_axes 方法来创建 (“top”,“right”,“bottom”和“left”)给定侧的新轴 的原始坐标轴。

【讨论】:

  • make_axis_locatable 到底是做什么的?
  • 除此之外,我需要调整图像本身的 yticks 以使目前 yticks 是字段的索引,但它们以 bin 的形式表示一定范围,所以我想把它写在轴上而不是索引上。有没有办法替换 yticks?
  • @michael 如果我正确理解您的最后评论,您正在寻找set_ticklabels 方法。我在示例中使用了它(最右边的轴)。您可以为此方法提供所需标签的列表。如果列表短于刻度数(如我的示例中),则剩余的刻度标签是空字符串,即它们不显示。
  • 完美,看起来我现在想要它。谢谢(很抱歉延迟回答)。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2012-07-24
  • 1970-01-01
  • 2018-06-29
  • 1970-01-01
  • 2017-05-19
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多