对齐顶部和底部轴的刻度线坐标

问题描述 投票:2回答:2

我想构建一个在其底部x轴上有一组刻度线的图形,在其顶部x轴上有另一组与底部刻度线对齐的刻度线。特别是在我的情况下,这些是批次和时代。对于底部的每个n批次点(不一定是刻度),我想在顶部刻上一个纪元。考虑这个例子:

import numpy as np
import matplotlib.pyplot as plt

batches = np.arange(1,101)
epoch_ends = batches[[(i*10)-1 for i in range(1,11)]]
accuracy = np.apply_along_axis(arr=batches, axis=0, func1d=lambda x : x/len(batches))
loss = np.apply_along_axis(arr=batches, axis=0, func1d=lambda x : 1 - (x/len(batches)))

fig, ax1 = plt.subplots( nrows=1, ncols=1 )
ax2 = ax1.twinx()
ax3 = ax1.twiny()

ax1.set_xlabel('batches')
ax1.set_xticks(np.arange(1, len(batches)+1, 9))
ax1.set_ylabel('accuracy')
ax1.grid()

ax2.set_ylabel('loss')
ax2.set_yticklabels(np.linspace(3, 10, 9))

ax3.set_xlabel('epochs')
ax3.set_xticks(epoch_ends)
ax3.set_xticklabels(range(1, len(epoch_ends)+1))

acc_plt = ax1.plot(batches, accuracy, color='red', label='acc')
loss_plt = ax2.plot(batches, loss, color='blue', label='loss')

lns = acc_plt+loss_plt
labs = [l.get_label() for l in lns]
ax1.legend(lns, labs, loc=2)

plt.show()

batchesepoch_ends分别是这样的

[  1   2   3   4   5   6   7   8   9  10  11  12  13  14  15  16  17  18
  19  20  21  22  23  24  25  26  27  28  29  30  31  32  33  34  35  36
  37  38  39  40  41  42  43  44  45  46  47  48  49  50  51  52  53  54
  55  56  57  58  59  60  61  62  63  64  65  66  67  68  69  70  71  72
  73  74  75  76  77  78  79  80  81  82  83  84  85  86  87  88  89  90
  91  92  93  94  95  96  97  98  99 100]
[ 10  20  30  40  50  60  70  80  90 100]

所以我希望epoch tick 1与批x-coorrdiante 10,2与20等对齐。

但正如你在图片中看到的那样,他们没有排队。

enter image description here

我需要在代码中进行哪些更改才能使其正常工作?

python matplotlib alignment axes
2个回答
2
投票

这是一种对齐它们的方法。这个想法如下:

  • 首先使用(ax1)在较低的x轴上绘制数据
  • 然后使用ax3.set_xlim(ax1.get_xlim())将上部x轴的极限设置为与下部x轴相同
  • 然后将上x轴的刻度设置在与较低x轴值(10,20,30,...,90,100)对应的位置
  • 最后,使用ax3.set_xticklabels()重命名刻度标签。

以下是代码:我正在通过注释#替换代码中已有的部分。

# imports and define data and compute accuracy and loss here

# Initiate figure and axis objects here

ax1.set_xlabel('batches')
ax1.set_xticks(np.arange(1, len(batches)+1, 9))
ax1.set_ylabel('accuracy')
ax1.grid()

acc_plt = ax1.plot(batches, accuracy, color='red', label='acc')
loss_plt = ax2.plot(batches, loss, color='blue', label='loss')

ax2.set_ylabel('loss')
ax2.set_yticklabels(np.linspace(3, 10, 9))

new_tick_locations = np.arange(1, 11)*10
new_tick_labels = range(1, 11)

ax3.set_xlabel('epochs')
ax3.set_xlim(ax1.get_xlim())
ax3.set_xticks(new_tick_locations)
ax3.set_xticklabels(new_tick_labels)

# Set legends and show the plot

enter image description here


1
投票

这会失去你对蜱虫的控制(你没有说是否需要),但会像你说的那样排列两个x轴:(新线被评论)

import numpy as np
import matplotlib.pyplot as plt

batches = np.arange(1,101)
epoch_ends = batches[[(i*10)-1 for i in range(1,11)]]
accuracy = np.apply_along_axis(arr=batches, axis=0, func1d=lambda x : x/len(batches))
loss = np.apply_along_axis(arr=batches, axis=0, func1d=lambda x : 1 - (x/len(batches)))

fig, ax1 = plt.subplots( nrows=1, ncols=1 )
ax2 = ax1.twinx()
ax3 = ax1.twiny()

ax1.set_xlabel('batches')
#ax1.set_xticks(np.arange(1, len(batches)+1, 9))
ax1.set_xlim(0, 100)                               # Set xlim
ax1.set_ylabel('accuracy')
ax1.grid()

ax2.set_ylabel('loss')
ax2.set_yticklabels(np.linspace(3, 10, 9))

ax3.set_xlabel('epochs')
#ax3.set_xticks(epoch_ends)
#ax3.set_xticklabels(range(1, len(epoch_ends)+1))
ax3.set_xlim(0, 10)                                # Set xlim

acc_plt = ax1.plot(batches, accuracy, color='red', label='acc')
loss_plt = ax2.plot(batches, loss, color='blue', label='loss')

lns = acc_plt+loss_plt
labs = [l.get_label() for l in lns]
ax1.legend(lns, labs, loc=2)

plt.show()
© www.soinside.com 2019 - 2024. All rights reserved.