IndexError:列表索引超出范围,拍摄方法

时间:2017-01-14 21:36:16

标签: python-3.x for-loop range

x1=np.linspace(xmin, xmax, Nsteps)
y1=np.linspace(0., 0., Nsteps)
h=x1[1]-x1[0]
V1=-V0*np.exp(-alpha*(x1)**2)
E=-1
k=math.sqrt(-2*E)
y1[0]=1
y1[1]=np.exp(k*h)
f=2*[V1-E]

def a():
   for i in range (1,Nsteps):
    denom = np.sum(2+10*h**2*f[i]/12)
    numer = np.sum(1-h**2*f[i+1]/12)   
    return denom/numer


def b():
  for i in range(1, Nsteps):
    denom = np.sum(1-h**2*f[i-1]/12)
    numer = np.sum(1-h**2*f[i+1]/12)
    return denom/numer

def y2():
    a[i]*y1[i] + b[i]*y1[i-1]

for i in range (1, Nsteps):
    print(y2)

plt.plot(x1, y2)
plt.show()

对于某些给定参数,我的目标是生成实现拍摄方法的代码。但是,在运行它时,由于x1和y2的长度不同,我得到了IndexError。我对 i 的界限是1和1001.我假设在边界f [i-1]和f [i + 1]产生超出定义范围的值?另外,当运行最后一个for循环时,我是否在for循环中再次运行先前的for循环,因此创建了一些奇怪的东西?这些是我的猜测,我的第二个问题是,如果有解决这个问题的技巧?我可以实现一些if条件来纠正这个问题吗?

1 个答案:

答案 0 :(得分:0)

您的代码存在许多问题,首先是可读性问题。这不是字节很贵的70年代 - 在你的陈述中添加空格,这样你就可以看到发生了什么。同样,请适当地命名变量和函数。读者应该如何知道a()的作用?举个例子,转过来:

V1=-V0*np.exp(-alpha*(x1)**2)

进入这个:

V1 = -V0 * np.exp(-alpha * (x1**2))

更容易看到发生了什么。

接下来,使用4个空格进行缩进,并始终如一地使用它 - 您可以更轻松地查看潜在的缩进问题 - 例如a()b() return for 内部 \t循环,导致它只运行一次。所有优秀的编程编辑器(除了Windows Notepad之外的几乎所有内容)都允许您设置在按下 Tab 键时插入的内容。在Python 3中混合制表符和空格是一个错误,所以根本不要使用制表符(y2())。

a[i]中,b[i]a没有意义,因为bi是函数,不能像那样切片,{ {1}}未在此上下文中定义。

print(y2)会打印类似<function y2 at 0x7fae9e8e3378>的内容,我很确定这不是您想要做的。同样,plt.plot(x1, y2)也不会做你想要的。如果您重构y2()实际返回某些内容(当前不是),并且某些内容是列表或与x1内容对应的NumPy数组,那么您应该使用plt.plot(x1, y2())代替。

将所有这些付诸实践,您仍然需要重构(并重命名)a()b(),以便他们计算并返回您想要的值。请记住,虽然函数可以读取定义函数的同一作用域中定义的变量,但是显式通过参数传递您希望函数处理的对象更好。所以,而不是:

some_lst = [1, 2, 3, 4, 5]
some_str = "abcde"

def zippem():
    return list(zip(some_lst, some_str))

您应该使用:

some_lst = [1, 2, 3, 4, 5]
some_str = "abcde"

def zippem(input_a, input_b):
    return list(zip(input_a, input_b))

然后这样称呼它:

list_o_tuples = zippem(some_lst, some_str)

这允许您将函数定义移动到另一个模块,将其放在一个类中,或者只使用任意输入而不是其范围内定义的对象。