2017-06-05 48 views
1

当添加残差与add_axes时,我无法让子图工作。它运行良好,没有残差,我可以将残差添加到一个图中。这是我正在做的一个例子:Python - 为由for循环生成的子图添加残差

首先,为了给你一个我正在绘制什么的想法,(t,y)是我想绘制的数据,拟合是对数据的拟合,差异是拟合和数据之间的差异。

t, s, fit = [], [], [] 
diff = [] 
for i in range(12): 
    t.append(x/y[i]) 

    s.append(np.linspace(0, 1, num=100, endpoint=True)) 
    fit.append(UnivariateSpline(t[i], y, er, s=5e20)) 
    diff.append(fit[i](t[i]) - y) 

这是图中:

fig = plt.figure() 
for i in range(12): 
    plt.subplot(4,3,i+1) 
    fig.add_axes((0.,0.3,0.7,0.9)) 
    plt.plot(s[i], fit[i](s[i]), 'r-') # this is the fit 
    plt.errorbar(t[i], y, er, fmt='.k',ms=6) # this is the data 
    plt.axis([0,1, 190, 360]) 

    fig.add_axes((0.,0.,0.7,0.3))  
    plot(t[i],diff[i],'or') # this are the residuals 
    plt.axis([0,1, 190, 360]) 

因此,大家可以看到我生成12个次要情节,它工作得很好,直到我添加fig.add_axes数据+配合和之间的每个副区分开残差,但我得到的是对次要情节(图已经皱缩看到在次要情节)的顶部有一个凌乱的情节:

messy plot

和我要的是12个分支情节,其中每一个看起来是这样的:

correct plot

回答

1

通常plt.subplot(..)fig.add_axes(..)是互补的。这意味着这两个命令都会在图形中创建一个轴。

然而他们的用法会有所不同。要创建12个次要情节与subplot你会做

for i in range(12): 
    plt.subplot(4,3,i+1) 
    plt.plot(x[i],y[i]) 

要创建12个次要情节与add_axes你需要做这样的事情

for i in range(12): 
    ax = fig.add_axes([.1+(i%3)*0.8/3, 0.7-(i//3)*0.8/4, 0.2,.18]) 
    ax.plot(x[i],y[i]) 

哪里需要传递到add_axes轴的位置。

两者都正常工作。但是将它们合并并不是直接的,因为子图是根据网格定位的,而使用add_axes则需要知道网格位置。

所以我建议从头开始。创建子图的合理和干净的方法是使用plt.subplots()

fig, axes = plt.subplots(nrows=4, ncols=3) 
for i, ax in enumerate(axes.flatten()): 
    ax.plot(x[i],y[i]) 

每个副区可以通过使用轴分频器(make_axes_locatable

from mpl_toolkits.axes_grid1 import make_axes_locatable 
divider = make_axes_locatable(ax) 
ax2 = divider.append_axes("bottom", size=size, pad=pad) 
ax.figure.add_axes(ax2) 

所以遍历轴线和上述操作后对每个轴被分成2允许以获得所需的网格。

import numpy as np 
import matplotlib.pyplot as plt 
from mpl_toolkits.axes_grid1 import make_axes_locatable 
plt.rcParams["font.size"] = 8 

x = np.linspace(0,2*np.pi) 
amp = lambda x, phase: np.sin(x-phase) 
p = lambda x, m, n: m+x**(n) 

fig, axes = plt.subplots(nrows=3, ncols=4, figsize=(8,6), sharey=True, sharex=True) 

def createplot(ax, x, m, n, size="20%", pad=0): 
    divider = make_axes_locatable(ax) 
    ax2 = divider.append_axes("bottom", size=size, pad=pad) 
    ax.figure.add_axes(ax2) 
    ax.plot(x, amp(x, p(x,m,n))) 
    ax2.plot(x, p(x,m,n), color="crimson") 
    ax.set_xticks([]) 

for i in range(axes.shape[0]): 
    for j in range(axes.shape[1]): 
     phase = i*np.pi/2 
     createplot(axes[i,j], x, i*np.pi/2, j/2.,size="36%") 

plt.tight_layout()   
plt.show() 

enter image description here

+0

对不起穷人的解释,我已经编辑我的问题,以使其更清晰。我将两种方法混合在一起,试图在同一个子图中绘制我的数据+拟合和残差 – JVR

+0

哦,这与真正的问题完全不同。 ;-)我会稍后再研究它。 – ImportanceOfBeingErnest

+0

我现在更新了答案。 – ImportanceOfBeingErnest