去除numpy中的嵌套循环

2 投票
2 回答
1789 浏览
提问于 2025-04-16 21:15

我正在写一个程序,用来暴力破解一串数字,寻找欧拉砖块(euler bricks),但是我想到的方法是用三重循环。因为在Python中,嵌套循环通常会非常慢,所以我在想有没有更好的办法,能用numpy来生成我需要的数值数组。

#x=max side length of brick. User Input.    
for t in range(3,x):
    a=[];b=[];c=[];
    for u in range(2,t):
        for v in range(1,u):
                a.append(t)
                b.append(u)
                c.append(v)
    a=np.array(a)
    b=np.array(b)
    c=np.array(c)
    ...

有没有更好的方法,使用numpy命令来生成这些数值数组呢?

谢谢。

举个例子:如果x=10,当t=3时,我想得到:

a=[3]  
b=[2]     
c=[1]

第一次循环的时候。之后,当t=4时:

a=[4, 4, 4]
b=[2, 3, 3]
c=[1, 1, 2]

第三次(t=5)我想要:

a=[5, 5, 5, 5, 5, 5]
b=[2, 3, 3, 4, 4, 4]
c=[1, 1, 2, 1, 2, 3]

以此类推,直到最大边长大约在5000左右。

补充:解决方案

a=array(3)
b=array(2)
c=array(1)
for i in range(4,x): #Removing the (3,2,1) check from code does not affect results.
    foo=arange(1,i-1)
    foo2=empty(len(foo))
    foo2.fill(i-1)
    c=hstack((c,foo))
    b=hstack((b,foo2))
    a=empty(len(b))
    a.fill(i)
    ...

现在运行速度快了很多。谢谢大家。

2 个回答

2

试着使用 .empty 和 .fill 方法(可以查看这个链接:http://docs.scipy.org/doc/numpy/reference/generated/numpy.ndarray.fill.html)

1

有几个方法可以帮助你,但可能只对很大的x值有效。首先,使用xrange代替range,这样可以避免创建一个你根本不需要的列表。你还可以创建一个正确长度的空numpy数组,然后在处理过程中逐步填充值,而不是先添加到列表中再转换成numpy数组。

我相信这段代码可以正常工作(现在没有Python环境可以测试):

for t in xrange(3, x):
    size = (t - 2) * (t - 3)
    a = np.zeros(size)
    b = np.zeros(size)
    c = np.zeros(size)

    idx = 0
    for u in xrange(2,t):
        for v in xrange(1,u):
            a[idx] = t
            b[idx] = u
            c[idx] = v
            idx += 1

撰写回答