如何理解我为一个问题编写的Python代码

2024-09-29 03:26:06 发布

您现在位置:Python中文网/ 问答频道 /正文

如果我给2输出是

2 2 2
2 1 2
2 2 2

对于3是

3 3 3 3 3
3 2 2 2 3
3 2 1 2 3
3 2 2 2 3
3 3 3 3 3

代码如下:

def square(arr, val):

    if val is 1:
        return [[1]]    //self understandable

    n = val + (val - 1)       //getting array size, for 2 its 3

    sideAdd = [val] * n              
    arr.insert(0, sideAdd)      //for 2 it add [2,2,2] at first
    arr.append(sideAdd)         //append [2,2,2]

    for i in range(1, n-1):      //for inner elements add val to either sides
        arr[i].insert(0, val)    // like, for 2 [val,1,val]
        arr[i].append(val)


    return(arr)


array = square([[2, 2, 2], [2, 1, 2], [2, 2, 2]], 3)


# print(array)
for i in array:
    print(*i)

输出如下:

3 3 3 3 3
3 2 2 2 3
3 2 1 2 3
3 2 2 2 3
3 3 3 3 3

这是一个正确的答案。你知道吗

但是当我试图通过for循环给出值并通过相同的函数再次发送返回的数组作为参数来完成整个解决方案时

n = 3  
arr = []

for i in range(1, n+1):

    arr = square(arr, i)

整个代码是

def square(arrx, val):

    if val is 1:
        return [[1]]

    n1 = val + (val - 1)

    sideAdd = [val] * n1
    arrx.insert(0, sideAdd)
    arrx.append(sideAdd)


    for i in range(1, n1-1):
        arrx[i].insert(0, val)
        arrx[i].append(val)

    return arrx


n = 3
arr = []

for i in range(1, n+1):

    arr = square(arr, i)



for i in arr:
    print(*i)

返回的答案为:

3 3 3 3 3
3 3 2 2 2 3 3
3 2 1 2 3
3 3 2 2 2 3 3
3 3 3 3 3

哪个是错的

我已经试过在pycharm的调试模式下运行了,在那里我得到了一个不寻常的东西。查看下面的屏幕截图。当j=1(索引)时,代码在蓝色下划线中插入2,但也在红色下划线中插入2,因为红色下划线索引为3(2的插入应发生在j=3),当j=3时,再次在索引1(j=1)处插入,使输出3 3 2 2 3而不是3 2 3。你知道吗

我不明白这是怎么回事。截图如下:

https://imgur.com/yce47Pi


Tags: 代码inforreturnrangevalarrayinsert
2条回答

我觉得你把事情弄得太复杂了。您可以仅从任何单元格的索引中确定其正确值。给定大小n和行/列[i,j],值为:

max(abs(n - 1 - j) + 1, abs(n - 1 - i) + 1)

例如:

def square(n):
    arr = []

    for i in range(n + n-1):
        cur = []
        arr.append(cur)
        for j in range(n + n -1):
            cur.append(max(abs(n - 1 - j) + 1, abs(n - 1 - i) + 1))
    return arr

那么

> square(3)  

[[3, 3, 3, 3, 3],
 [3, 2, 2, 2, 3],
 [3, 2, 1, 2, 3],
 [3, 2, 2, 2, 3],
 [3, 3, 3, 3, 3]]

> square(5)

[[5, 5, 5, 5, 5, 5, 5, 5, 5],
 [5, 4, 4, 4, 4, 4, 4, 4, 5],
 [5, 4, 3, 3, 3, 3, 3, 4, 5],
 [5, 4, 3, 2, 2, 2, 3, 4, 5],
 [5, 4, 3, 2, 1, 2, 3, 4, 5],
 [5, 4, 3, 2, 2, 2, 3, 4, 5],
 [5, 4, 3, 3, 3, 3, 3, 4, 5],
 [5, 4, 4, 4, 4, 4, 4, 4, 5],
 [5, 5, 5, 5, 5, 5, 5, 5, 5]]

编辑

当前代码的问题是:

sideAdd = [val] * n              
arr.insert(0, sideAdd)      
arr.append(sideAdd)  

两次添加对相同数组(sideAdd)的引用。因此,稍后添加列时:

arrx[i].insert(0, val)
arrx[i].append(val)

如果这两个数组是在前面的循环中添加的,那么它们是相同的。添加到第一个数组也会将一个数组添加到第二个数组,添加到第二个数组会将一个数组添加到第一个数组。所以你最后做了两次。有几种方法可以解决这个问题,但最简单的方法是第二次添加副本:

sideAdd = [val] * n              
arr.insert(0, sideAdd)   
arr.append(sideAdd[:]) # Make a copy — don't add the same reference

我们可以在这里使用numpy的广播规则:

>>> np.maximum(np.abs(np.arange(-2, 3)[:, None]), np.abs(np.arange(-2, 3))) + 1
array([[3, 3, 3, 3, 3],
       [3, 2, 2, 2, 3],
       [3, 2, 1, 2, 3],
       [3, 2, 2, 2, 3],
       [3, 3, 3, 3, 3]])

因此,我们可以使用以下方式渲染立方体:

将numpy作为np导入

def cube(n):
    ran = np.abs(np.arange(-n+1, n))
    cub = np.maximum(ran[:, None], ran) + 1
    return '\n'.join(' '.join(map(str, row)) for row in cub)

例如:

>>> print(cube(1))
1
>>> print(cube(2))
2 2 2
2 1 2
2 2 2
>>> print(cube(3))
3 3 3 3 3
3 2 2 2 3
3 2 1 2 3
3 2 2 2 3
3 3 3 3 3
>>> print(cube(4))
4 4 4 4 4 4 4
4 3 3 3 3 3 4
4 3 2 2 2 3 4
4 3 2 1 2 3 4
4 3 2 2 2 3 4
4 3 3 3 3 3 4
4 4 4 4 4 4 4
>>> print(cube(5))
5 5 5 5 5 5 5 5 5
5 4 4 4 4 4 4 4 5
5 4 3 3 3 3 3 4 5
5 4 3 2 2 2 3 4 5
5 4 3 2 1 2 3 4 5
5 4 3 2 2 2 3 4 5
5 4 3 3 3 3 3 4 5
5 4 4 4 4 4 4 4 5
5 5 5 5 5 5 5 5 5

相关问题 更多 >