如何在分散自动放置的箭头上注释点

新手上路,请多包涵

如果我用 matplotlib 绘制散点图:

 plt.scatter(randn(100),randn(100))
# set x, y lims
plt.xlim([...])
plt.ylim([...])

我想用指向它的箭头和标签来注释给定点 (x, y) 。我知道这可以用 annotate 来完成,但我希望箭头及其标签“最佳”放置的方式是,如果可能(给定当前轴刻度/限制)箭头和标签不与其他点重叠。例如,如果你想标记一个离群点。有没有办法做到这一点?它不一定是完美的,而只是箭头/标签的智能放置,仅给出要标记的点的 (x,y) 坐标。谢谢。

原文由 user248237 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 378
2 个回答

基本上,不,没有。

处理放置与此类似的地图标签的布局引擎非常复杂,超出了 matplotlib 的范围。 (边界框相交实际上是决定标签放置位置的一种相当糟糕的方法。为只能在 1000 个案例中的一个案例中工作的东西编写大量代码有什么意义?)

除此之外,由于 matplotlib 执行的复杂文本渲染量(例如乳胶),如果不首先完全渲染文本就不可能确定文本的范围(这相当慢)。

但是,在许多情况下,您会发现在放置有注释的标签后面使用透明框是一种合适的解决方法。

例如

import numpy as np
import matplotlib.pyplot as plt

np.random.seed(1)
x, y = np.random.random((2,500))

fig, ax = plt.subplots()
ax.plot(x, y, 'bo')

# The key option here is `bbox`. I'm just going a bit crazy with it.
ax.annotate('Something', xy=(x[0], y[0]), xytext=(-20,20),
            textcoords='offset points', ha='center', va='bottom',
            bbox=dict(boxstyle='round,pad=0.2', fc='yellow', alpha=0.3),
            arrowprops=dict(arrowstyle='->', connectionstyle='arc3,rad=0.5',
                            color='red'))

plt.show()

在此处输入图像描述

原文由 Joe Kington 发布,翻译遵循 CC BY-SA 3.0 许可协议

使用 adjustText (完全公开,我写的)。

让我们标记前 10 个点。我更改的唯一参数是降低点的排斥力,因为它们太多了,我们希望算法花费更多时间并更仔细地放置注释。

 import numpy as np
import matplotlib.pyplot as plt
from adjustText import adjust_text
np.random.seed(1)
x, y = np.random.random((2,500))

fig, ax = plt.subplots()
ax.plot(x, y, 'bo')
ts = []
for i in range(10):
    ts.append(plt.text(x[i], y[i], 'Something'+str(i)))
adjust_text(ts, x=x, y=y, force_points=0.1, arrowprops=dict(arrowstyle='->',
color='red'))
plt.show()

在此处输入图像描述 这并不理想,但这里的点非常密集,有时无法将文本放置在目标附近而不与它们重叠。但它是自动且易于使用的,并且不会让标签相互重叠。

PS 它使用边界框交叉点,但我会说相当成功!

原文由 Phlya 发布,翻译遵循 CC BY-SA 3.0 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题