代码之家  ›  专栏  ›  技术社区  ›  Bastien Léonard

带PYX的绘图大括号

  •  3
  • Bastien Léonard  · 技术社区  · 15 年前

    如何用PYX在任意两点之间绘制支撑线?

    它看起来像这样:

    Brace example http://tof.canardpc.com/view/d16770a8-0fc6-4e9d-b43c-a11eaa09304d

    2 回复  |  直到 9 年前
        1
  •  9
  •   tom10    15 年前

    您可以使用 sigmoidals . 我没有安装PYX,所以我将使用Matplotlib(这里是PYLAB)绘制这些图。在这里 beta 控制大括号中曲线的锐度。

    import numpy as nx
    import pylab as px
    
    
    def half_brace(x, beta):
        x0, x1 = x[0], x[-1]
        y = 1/(1.+nx.exp(-1*beta*(x-x0))) + 1/(1.+nx.exp(-1*beta*(x-x1)))
        return y
    
    xmax, xstep = 20, .01
    xaxis = nx.arange(0, xmax/2, xstep)
    y0 = half_brace(xaxis, 10.)
    y = nx.concatenate((y0, y0[::-1]))
    
    px.plot(nx.arange(0, xmax, xstep), y)
    px.show()
    

    alt text http://i26.tinypic.com/23iyp76.png

    为了节省屏幕空间,我沿着X轴绘制了这个图,但是为了沿着Y轴获得支撑,只需交换X和Y。最后,PYX内置了大量的路径绘制功能,可以满足您的需要。

        2
  •  4
  •   travc    11 年前

    TOM10提供了一个很好的解决方案,但可能需要一些改进。
    关键是在范围[0,1]、[0,1]上创建一个大括号,然后缩放它。
    这个版本还允许您稍微调整形状。对于奖励点,它使用二阶导数来计算这些点的空间密度。

    mid 设置上下部分之间的平衡。
    beta1 beta2 控制曲线(上下)的锐度。
    你可以改变 height (或者用y乘以一个标量)。
    使它垂直而不是水平,只需要交换x和y。
    initial_divisions resolution_factor 控制如何选择x值,但通常应忽略。

    import numpy as NP
    
    def range_brace(x_min, x_max, mid=0.75, 
                    beta1=50.0, beta2=100.0, height=1, 
                    initial_divisions=11, resolution_factor=1.5):
        # determine x0 adaptively values using second derivitive
        # could be replaced with less snazzy:
        #   x0 = NP.arange(0, 0.5, .001)
        x0 = NP.array(())
        tmpx = NP.linspace(0, 0.5, initial_divisions)
        tmp = beta1**2 * (NP.exp(beta1*tmpx)) * (1-NP.exp(beta1*tmpx)) / NP.power((1+NP.exp(beta1*tmpx)),3)
        tmp += beta2**2 * (NP.exp(beta2*(tmpx-0.5))) * (1-NP.exp(beta2*(tmpx-0.5))) / NP.power((1+NP.exp(beta2*(tmpx-0.5))),3)
        for i in range(0, len(tmpx)-1):
            t = int(NP.ceil(resolution_factor*max(NP.abs(tmp[i:i+2]))/float(initial_divisions)))
            x0 = NP.append(x0, NP.linspace(tmpx[i],tmpx[i+1],t))
        x0 = NP.sort(NP.unique(x0)) # sort and remove dups
        # half brace using sum of two logistic functions
        y0 = mid*2*((1/(1.+NP.exp(-1*beta1*x0)))-0.5)
        y0 += (1-mid)*2*(1/(1.+NP.exp(-1*beta2*(x0-0.5))))
        # concat and scale x
        x = NP.concatenate((x0, 1-x0[::-1])) * float((x_max-x_min)) + x_min
        y = NP.concatenate((y0, y0[::-1])) * float(height)
        return (x,y)
    

    用法很简单:

    import pylab as plt
    
    fig = plt.figure()
    ax = fig.add_subplot(111)
    
    x,y = range_brace(0, 100)
    ax.plot(x, y,'-')
    
    plt.show()
    

    Plot produced by example

    附言:别忘了你可以通过 clip_on=False plot 把它放在轴的外面。