【问题标题】:Values in Python list won't change in for loopPython 列表中的值在 for 循环中不会改变
【发布时间】:2021-06-21 16:14:11
【问题描述】:

我正在对某种类型的三对角矩阵进行 LU 分解,但我遇到了一个我完全无法理解的 Python 问题。

def trisolve2(b):
    length = len(b)

    # Solve Ly = b
    y = b.copy()
    for i in range(1, length):
        print('y[' + str(i) + '] = ' + str(b[i]) + ' - (-' + str(i) + ' / (' + str(i+1)
            + ')) * ' + str(y[i-1]))
        y[i] = b[i] - (-1 * i / (i+1)) * y[i-1]
    print("y = " + str(y))

    # Solve Ux = y
    x = y.copy()
    for i in range(length - 2, 0, -1):
        print("x = " + str(x))
        x[i] =  (y[i] + x[i+1]) / ((i+2) / (i+1))

    return x

test_b = np.array([[1], [0], [0], [0], [1]])
print("b = " + str(test_b))
test_x = trisolve2(test_b)
print("x = " + str(test_x))

我希望当 i = 1 时,y[i] 被分配到 1/2,它甚至看起来应该与我放在那里的打印语句一样,但由于某种原因我无法包装我的绕着它走永远不会改变。 y 保持 b,x 保持 y 不变。输出是:

b = [[1]
 [0]
 [0]
 [0]
 [1]]
y[1] = [0] - (-1 / (2)) * [1]
y[2] = [0] - (-2 / (3)) * [0]
y[3] = [0] - (-3 / (4)) * [0]
y[4] = [1] - (-4 / (5)) * [0]
y = [[1]
 [0]
 [0]
 [0]
 [1]]
x = [[1]
 [0]
 [0]
 [0]
 [1]]
x = [[1]
 [0]
 [0]
 [0]
 [1]]
x = [[1]
 [0]
 [0]
 [0]
 [1]]
x = [[1]
 [0]
 [0]
 [0]
 [1]]```

【问题讨论】:

  • 我怀疑这与多维 numpy 数组的工作方式有关,而不是与 for 循环的机制有关——它闻起来很像引用与值的问题。
  • 尝试使用deepcopy() 而不是copy()
  • 您使用的是什么版本的 Python?如果是 Python 2.x(没有 from __future__ import division),那么 i / (i+1) 不会像你想的那样:它总是会返回零。如果是这种情况,请尝试在您的打印语句中包含表达式 b[i] - (-1 * i / (i+1)) * y[i-1]实际评估值,以了解原因。

标签: python list numpy for-loop linear-algebra


【解决方案1】:

您的 numpy 数组默认为 int32,0.5 被四舍五入为最接近的整数:1。

>> b = np.array([[1], [0], [0], [0], [1]])
>> b
array([[1],
       [0],
       [0],
       [0],
       [1]])
>> b.dtype
dtype('int32')

尝试传递dtype 参数:

test_b = np.array([[1], [0], [0], [0], [1]], dtype=float)

【讨论】:

  • 没错。 OP 可以看到这一点的一种方法是打印 表达式的实际评估值 (print( b[i] - (-1 * i / (i+1)) * y[i-1])),而不是仅仅将其打印出来,并将变量替换为当前值 (print('y[' + str(i) + '] = ' + str(b[i]) + ' - (-' + str(i) + ' / (' + str(i+1) + ')) * ' + str(y[i-1])) )
  • 正确的是在使用 numpy 时尽可能多地进行类型检查,因为函数背后的向量化代码经常从 c++ 版本更改为线性化 simd 序列。自从从 python 3.5 升级到更新的版本后,我遇到了类似的问题,并且在将 float 和 double 类型传递给 numpy 时解决了它做一些类型检查。找不到错误本身,但超过了升级到比 3.5 更新的 python 版本。我发现它在某些 3.7.2 版本中运行良好,但其他版本的类型传递错误到 numpy 模块
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-06-17
  • 2019-07-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多