首页 文章

在ipython notebook中的matplotlib图中添加任意一行

提问于
浏览
88

我对python / matplotlib都很陌生,并通过ipython笔记本使用它 . 我正在尝试向现有图形添加一些注释线,我无法弄清楚如何在图形上渲染线条 . 因此,例如,如果我绘制以下内容:

import numpy as np
np.random.seed(5)
x = arange(1, 101)
y = 20 + 3 * x + np.random.normal(0, 60, 100)
p =  plot(x, y, "o")

我得到以下图表:

beautiful scatter plot

那么我如何添加从(70,100)到(70,250)的垂直线?从(70,100)到(90,200)的对角线怎么样?

我已经尝试了一些 Line2D() 的事情,但除此之外我只会感到困惑 . 在 R 中,我只想使用segments()函数来添加线段 . matplotlib 中是否有等价物?

4 回答

  • 4

    使用vlines

    import numpy as np
    np.random.seed(5)
    x = arange(1, 101)
    y = 20 + 3 * x + np.random.normal(0, 60, 100)
    p =  plot(x, y, "o")
    vlines(70,100,250)
    

    基本呼叫签名是:

    vlines(x, ymin, ymax)
    hlines(y, xmin, xmax)
    
  • 46

    正如OP所寻求的那样,Matplolib现在允许'annotation lines' . annotate() 功能允许几种形式的连接路径,无头和无头箭头,即简单的线,就是其中之一 .

    ax.annotate("",
                xy=(0.2, 0.2), xycoords='data',
                xytext=(0.8, 0.8), textcoords='data',
                arrowprops=dict(arrowstyle="-",
                          connectionstyle="arc3, rad=0"),
                )
    

    the documentation中,它表示您只能绘制一个带有空字符串的箭头作为第一个参数 .

    从OP的例子来看:

    %matplotlib notebook
    import numpy as np
    import matplotlib.pyplot as plt
    
    np.random.seed(5)
    x = np.arange(1, 101)
    y = 20 + 3 * x + np.random.normal(0, 60, 100)
    plt.plot(x, y, "o")
    
    
    # draw vertical line from (70,100) to (70, 250)
    plt.annotate("",
                  xy=(70, 100), xycoords='data',
                  xytext=(70, 250), textcoords='data',
                  arrowprops=dict(arrowstyle="-",
                                  connectionstyle="arc3,rad=0."), 
                  )
    
    # draw diagonal line from (70, 90) to (90, 200)
    plt.annotate("",
                  xy=(70, 90), xycoords='data',
                  xytext=(90, 200), textcoords='data',
                  arrowprops=dict(arrowstyle="-",
                                  connectionstyle="arc3,rad=0."), 
                  )
    
    plt.show()
    

    Example inline image

    就像在gcalmettes的答案中的方法一样,您可以选择颜色,线宽,线条样式等 .

    以下是对代码的一部分的更改,这将使两个示例行中的一个变为红色,更宽,而不是100%不透明 .

    # draw vertical line from (70,100) to (70, 250)
    plt.annotate("",
                  xy=(70, 100), xycoords='data',
                  xytext=(70, 250), textcoords='data',
                  arrowprops=dict(arrowstyle="-",
                                  edgecolor = "red",
                                  linewidth=5,
                                  alpha=0.65,
                                  connectionstyle="arc3,rad=0."), 
                  )
    

    您还可以通过调整 connectionstyle 将曲线添加到连接线 .

  • 151

    您可以通过使用相应的数据(段的边界)提供 plot 命令来直接绘制所需的行:

    plot([x1, x2], [y1, y2], color='k', linestyle='-', linewidth=2)

    (当然你可以选择颜色,线宽,线条样式等)

    从你的例子:

    import numpy as np
    import matplotlib.pyplot as plt
    
    np.random.seed(5)
    x = np.arange(1, 101)
    y = 20 + 3 * x + np.random.normal(0, 60, 100)
    plt.plot(x, y, "o")
    
    
    # draw vertical line from (70,100) to (70, 250)
    plt.plot([70, 70], [100, 250], 'k-', lw=2)
    
    # draw diagonal line from (70, 90) to (90, 200)
    plt.plot([70, 90], [90, 200], 'k-')
    
    plt.show()
    

    new chart

  • 35

    这对新人来说还不算太晚 .

    plt.axvline(x, color='r')
    

    http://matplotlib.org/api/pyplot_api.html#matplotlib.pyplot.axvline

    使用ymin和ymax也需要y的范围 .

相关问题