当前位置: 首页 > 知识库问答 >
问题:

左右对齐matplotlib分散标记

郎增
2023-03-14

我正在使用matplotlibscatterplot函数在垂直线上创建句柄的外观,以描绘图形的某些部分。然而,为了使它们看起来正确,我需要能够将散点图标记向左对齐(对于左线/划定线)和/或向右对齐(对于右线/划定线)。

这里有一个例子:

#create the figure
fig = plt.figure(facecolor = '#f3f3f3', figsize = (11.5, 6))
ax = plt. ax = plt.subplot2grid((1, 1), (0,0))

#make some random data
index = pandas.DatetimeIndex(start = '01/01/2000', freq  = 'b', periods = 100)
rand_levels = pandas.DataFrame( numpy.random.randn(100, 4)/252., index = index, columns = ['a', 'b', 'c', 'd'])
rand_levels = 100*numpy.exp(rand_levels.cumsum(axis = 0))
ax.stackplot(rand_levels.index, rand_levels.transpose())

#create the place holder for the vertical lines
d1, d2 = index[25], index[50]

#draw the lines
ymin, ymax = ax.get_ylim()
ax.vlines([index[25], index[50]], ymin = ymin, ymax = ymax, color = '#353535', lw = 2)

#draw the markers
ax.scatter(d1, ymax, clip_on = False, color = '#353535', marker = '>', s = 200, zorder = 3)
ax.scatter(d2, ymax, clip_on = False, color = '#353535', marker = '<', s = 200, zorder = 3)

#reset the limits
ax.set_ylim(ymin, ymax)
ax.set_xlim(rand_levels.index[0], rand_levels.index[-1])
plt.show()

上面的代码几乎给出了我要找的图形,如下所示:

对如何以灵活的方式实现这一目标有任何指导或建议?

注意:实际上,我的dataframe索引是pandas.datetime而不是我为这个简单示例提供的整数。

共有1个答案

魏雅惠
2023-03-14

我喜欢这个问题,对我的第一个回答不满意。特别是,创建特定于图形的对象(mark_align_*)来对齐标记似乎是不必要的麻烦。我最终找到了通过verts指定标记的功能(2元素浮点列表或Nx2数组,用于指定标记顶点相对于(0,0)处的目标绘图点)。为了利用这个功能,我编写了这个函数,

from matplotlib import markers
from matplotlib.path import Path

def align_marker(marker, halign='center', valign='middle',):
    """
    create markers with specified alignment.

    Parameters
    ----------

    marker : a valid marker specification.
      See mpl.markers

    halign : string, float {'left', 'center', 'right'}
      Specifies the horizontal alignment of the marker. *float* values
      specify the alignment in units of the markersize/2 (0 is 'center',
      -1 is 'right', 1 is 'left').

    valign : string, float {'top', 'middle', 'bottom'}
      Specifies the vertical alignment of the marker. *float* values
      specify the alignment in units of the markersize/2 (0 is 'middle',
      -1 is 'top', 1 is 'bottom').

    Returns
    -------

    marker_array : numpy.ndarray
      A Nx2 array that specifies the marker path relative to the
      plot target point at (0, 0).

    Notes
    -----
    The mark_array can be passed directly to ax.plot and ax.scatter, e.g.::

        ax.plot(1, 1, marker=align_marker('>', 'left'))

    """

    if isinstance(halign, (str, unicode)):
        halign = {'right': -1.,
                  'middle': 0.,
                  'center': 0.,
                  'left': 1.,
                  }[halign]

    if isinstance(valign, (str, unicode)):
        valign = {'top': -1.,
                  'middle': 0.,
                  'center': 0.,
                  'bottom': 1.,
                  }[valign]

    # Define the base marker
    bm = markers.MarkerStyle(marker)

    # Get the marker path and apply the marker transform to get the
    # actual marker vertices (they should all be in a unit-square
    # centered at (0, 0))
    m_arr = bm.get_path().transformed(bm.get_transform()).vertices

    # Shift the marker vertices for the specified alignment.
    m_arr[:, 0] += halign / 2
    m_arr[:, 1] += valign / 2

    return Path(m_arr, bm.get_path().codes)

使用此函数,可以将所需的标记绘制为,

ax.plot(d1, 1, marker=align_marker('>', halign='left'), ms=20,
        clip_on=False, color='k', transform=ax.get_xaxis_transform())
ax.plot(d2, 1, marker=align_marker('<', halign='right'), ms=20,
        clip_on=False, color='k', transform=ax.get_xaxis_transform())

或者使用ax.scatter,

ax.scatter(d1, 1, 200, marker=align_marker('>', halign='left'),
           clip_on=False, color='k', transform=ax.get_xaxis_transform())
ax.scatter(d2, 1, 200, marker=align_marker('<', halign='right'),
           clip_on=False, color='k', transform=ax.get_xaxis_transform())

干杯!

 类似资料:
  • 问题内容: 我有可变长度的刻度标签,我想将它们向左对齐(即,较短的标签和y轴之间有一个空格)。有什么合理的方法可以做到这一点吗?使用水平对齐方式“向左”会将其向左对齐,但是它们都从轴开始,因此最终在绘图内。因此,另一个问题可能是- 我可以更改其起点吗? 演示代码: 问题答案: 您只需要添加一个。查看matplotlib刻度相对于轴的位置 (文件) 确定垫子应该是什么:

  • 问题内容: 使用典型的CSS,我可以在两列之间向左浮动另一列,并在两者之间留出一定的间距。我该如何使用flexbox? 问题答案: 您可以添加到父元素。这样做时,子级flexbox项将与相对侧对齐,并在它们之间留有空间。 您也可以添加到第二个元素以使其向右对齐。

  • 问题内容: 我正在使用flexbox对齐我的子元素。我想做的是将一个元素居中,而另一个保持最左对齐。通常我会使用来设置left元素。问题是将中心元素推离中心。这是可能的 ,而不 使用绝对定位? HTML和CSS 问题答案: 编辑: 请参阅下面的[Solo答案,这是更好的解决方案。 flexbox背后的想法是提供一个框架,可以轻松地将容器中尺寸可变的元素对齐。这样,提供一个布局而完全忽略一个元素的宽

  • 问题内容: 基本上,我有一个JTable包含具有右对齐单元格但左对齐标题的列,这看起来确实很糟糕。我想在不更改标题的“外观”的情况下,将这些列的标题右对齐。 谢谢 问题答案: 这是修改表格的的另一种方法。对于此用法,这不是严格必要的,但可以最大程度地减少对UI委托外观的影响。 典型用法: 自定义标题渲染器:

  • 问题内容: 我想显示一些观点。这是我的代码: 和我一样: 所以我有两种不同颜色的点。但是我也想有两个不同的标记。我该怎么做?给出一个错误。 问题答案: 每个标记可以使用一个散点图。

  • 在Java中,如何使用printf()对同一行的输出进行一致的左对齐和右对齐?这是所有left aligned的代码: 这是所有东西都保持对齐的输出: 相反,如果第三个元素(0.20,1.00,9.00)是正确的,那么我想要的是什么。我在上面的输出中指出“l”是左对齐的,但我希望变量在“r”所在的位置是右对齐的。如何使右边的输出(0.20,1.00,9.00)右对齐,同时使左边的输出(苹果,派,奶