【问题标题】:How do I create a graph that has a continuous axes with matplotlib?如何使用 matplotlib 创建具有连续轴的图形?
【发布时间】:2019-01-08 06:11:06
【问题描述】:

我正在尝试创建交互式图表。我不知道如何绘制一个连续的二次图 - 就像你缩小/移动轴一样,方程被绘制在那里,而不仅仅是在 2 x 点之间,所以它是连续的。

到目前为止,我已经得到了这个。

import matplotlib.pyplot as plt

xcoord=[]
ycoord=[]

for x in range(0,10):
    y=(2*x)**2 + 2*x + 4
    xcoord.append(x)
    ycoord.append(y)

plt.plot(xcoord,ycoord)
plt.show()

【问题讨论】:

    标签: python python-3.x matplotlib plot graph


    【解决方案1】:

    Matplotlib 不是绘图函数,而是点。当然,只要足够密集,任何连续函数都可以用点来近似。

    在放大绘图时确实会出现问题,在这种情况下,以前密集的点会散开,并且可以观察到多边形结构。相反,当缩小时,可能会发生函数没有在特定范围之外进行评估,因此绘图将大部分保持空白。

    一种解决方案是在每次轴限制发生变化时评估函数,特别是在覆盖整个轴范围并且具有与像素一样多的点的网格上。我们可以从图形大小和dpi中找出像素数。

    为了展示效果,我在这里添加了一个低振幅的正弦函数。

    import numpy as np
    import matplotlib.pyplot as plt
    
    func = lambda x: (2*x)**2 + 2*x + -4 + 0.2*np.sin(x*20)
    
    fig, ax = plt.subplots()
    ax.axis([-8,8,-100,400])
    line, = ax.plot([])
    
    def update(evt=None):
        xmin,xmax = ax.get_xlim()
        npoints = fig.get_size_inches()[0]*fig.dpi
        x = np.linspace(xmin, xmax, npoints)
        y = func(x)
        line.set_data(x,y)
        fig.canvas.draw_idle()
    
    ax.callbacks.connect('xlim_changed', update)    
    fig.canvas.mpl_connect("resize_event", update)
    plt.show()
    

    【讨论】:

      【解决方案2】:

      连续性很难复制,听起来你需要的是增加情节密度。更改循环并使用numpy

      import numpy as np
      numpy.linspace
      import matplotlib.pyplot as plt
      
      xcoord=[]
      ycoord=[]
      
      for x in np.linspace(0,10,1000):
          y=(2*x)**2 + 2*x + 4
          xcoord.append(x)
          ycoord.append(y)
      
      plt.plot(xcoord,ycoord)
      plt.show()
      

      【讨论】:

      • 如果使用 numpy,则无需循环。 xcoord=np.linspace(0,10,1000)ycoord=(2*xcoord)**2 + 2*xcoord + 4 就够了
      【解决方案3】:

      如果我理解您的问题,您希望根据当前轴平移/缩放动态重新计算绘图的内容(坐标)。这样做需要使用event handling 检测轴限制的变化,然后在这些限制之间使用预定义的点数重新计算坐标,最后相应地更新绘图

      import matplotlib as mpl
      import matplotlib.pyplot as plt
      import numpy as np
      
      
      def my_func(x):
          return (2 * x) ** 2 + 2 * x + 4
      
      
      def on_lims_change(axes):
          xmin, xmax = axes.get_xlim()
          new_x = np.linspace(xmin, xmax, 1000)
          new_y = my_func(new_x)
          l.set_data(new_x, new_y)
      
      
      fig, ax = plt.subplots()
      xcoord = np.linspace(0, 10, 1000)
      ycoord = my_func(xcoord)
      l, = ax.plot(xcoord, ycoord, 'r-')
      
      ax.callbacks.connect('xlim_changed', on_lims_change)
      ax.callbacks.connect('ylim_changed', on_lims_change)
      
      on_lims_change(ax)
      plt.show()
      

      感谢 @ImportanceOfBeingErnest 展示如何连接事件处理程序以更改坐标轴限制 in this answer

      【讨论】:

        猜你喜欢
        • 2021-12-27
        • 1970-01-01
        • 1970-01-01
        • 2018-11-07
        • 1970-01-01
        • 1970-01-01
        • 2020-11-09
        • 2021-07-26
        • 1970-01-01
        相关资源
        最近更新 更多