Python 列表中的值被覆盖

时间:2021-04-10 04:15:06

标签: python list linear-algebra

我正在为不同大小的某种类型的矩阵 A 计算一些值。即后向误差、前向误差、条件数和误差放大倍数(一切都具有无穷范数)。我的值被计算出来,然后我试图将它们放入列表中,通过增加矩阵 A 的大小进行循环。问题是每次循环后,我的列表中的值都会被当前的条件数覆盖,我不明白为什么.这是我的代码。

import numpy as np
import math as m
from scipy import io, integrate, linalg, signal
from scipy.sparse.linalg import eigs

sizes = [50, 100, 200, 300, 400]
forward_errors = sizes
backward_errors = sizes
magnification_factors = sizes
cond_numbers = sizes

number = 0
for n in sizes:
    A = np.zeros((n, n))

    # fill out matrix
    i = 0
    while(i < n):
        j = 0
        while(j < n):
            A[i, j] = 1.0 / (abs(i - j)**2.0 + 1.0)
            j = j + 1

        i = i + 1


    # fill out x_exact
    x_exact = np.ones((n, 1))

    # calculate b
    b = A.dot(x_exact)

    # calculate x_approx
    x_approx = linalg.solve(A, b)

    # calculate forward error
    forward_error = linalg.norm(x_approx - x_exact, ord=np.inf)
    print("forward_error = " + str(forward_error))

    # calculate residual, backwards error
    r = b - A.dot(x_approx)
    #print("r = " + str(r))


    # calculate error magnification
    error_mag = ((forward_error * linalg.norm(b, ord=np.inf)) / 
        (linalg.norm(r, ord=np.inf) * linalg.norm(x_exact, ord=np.inf))) 
    #print("error_mag = " + str(error_mag))

    # calculate inf-norm condition number of A
    cond_number = linalg.norm(A, ord=np.inf)
    print("cond_number = " + str(cond_number))

    forward_errors[number] = forward_error
    print(forward_errors)
    backward_errors[number] = r
    magnification_factors[number] = error_mag
    #print("magnification_factors = " + str(magnification_factors))
    cond_numbers[number] = cond_number
    print("cond_numbers = " + str(cond_numbers))
    #TODO figure out why these 4 are getting overwritten by cond_number

    number = number + 1

#TODO figure out why these 4 only print the condition numbers string
print("forward_errors = " + str(forward_errors))
print("backward_errors = " + str(backward_errors))
print("magnification_factors = " + str(magnification_factors))
print("cond_numbers = " + str(cond_numbers))

这里是使用前向错误作为示例的输出,因为它们很短。

forward_error = 3.3306690738754696e-15
cond_number = 3.0733694622250525
[3.3306690738754696e-15, 100, 200, 300, 400]
cond_numbers = [3.0733694622250525, 100, 200, 300, 400]
forward_error = 4.6629367034256575e-15
cond_number = 3.113350762669095
[3.0733694622250525, 4.6629367034256575e-15, 200, 300, 400]
cond_numbers = [3.0733694622250525, 3.113350762669095, 200, 300, 400]
forward_error = 5.995204332975845e-15
cond_number = 3.1333484283038167
[3.0733694622250525, 3.113350762669095, 5.995204332975845e-15, 300, 400]
cond_numbers = [3.0733694622250525, 3.113350762669095, 3.1333484283038167, 300, 400]
forward_error = 7.327471962526033e-15
cond_number = 3.1400148603736495
[3.0733694622250525, 3.113350762669095, 3.1333484283038167, 7.327471962526033e-15, 400]
cond_numbers = [3.0733694622250525, 3.113350762669095, 3.1333484283038167, 3.1400148603736495, 400]
forward_error = 6.8833827526759706e-15
cond_number = 3.143348136604871
[3.0733694622250525, 3.113350762669095, 3.1333484283038167, 3.1400148603736495, 6.8833827526759706e-15]
cond_numbers = [3.0733694622250525, 3.113350762669095, 3.1333484283038167, 3.1400148603736495, 3.143348136604871]
forward_errors = [3.0733694622250525, 3.113350762669095, 3.1333484283038167, 3.1400148603736495, 3.143348136604871]
backward_errors = [3.0733694622250525, 3.113350762669095, 3.1333484283038167, 3.1400148603736495, 3.143348136604871]
magnification_factors = [3.0733694622250525, 3.113350762669095, 3.1333484283038167, 3.1400148603736495, 3.143348136604871]
cond_numbers = [3.0733694622250525, 3.113350762669095, 3.1333484283038167, 3.1400148603736495, 3.143348136604871]

我将所有这些打印语句留在了注释后面以进行测试,这就是我发现所有内容都被条件编号替换的方式。我怀疑它一定是我没有得到的一些简单的 Python 东西。我只是不明白为什么或在哪里一切都被覆盖了,这对我来说太奇怪了。感谢阅读。

1 个答案:

答案 0 :(得分:1)

这是由于 Python 处理变量引用的方式造成的。

当你这样做

sizes = [50, 100, 200, 300, 400]
forward_errors = sizes
backward_errors = sizes
magnification_factors = sizes
cond_numbers = sizes

您基本上是在共享变量 sizes 引用而不是它的值。这意味着 forward_errorsbackward_errorsmagnification_factorscond_numbers 对 Python 来说是完全相同的变量。


您有一些方法可以解决这个问题。

1- 使用复制库

from copy import deepcopy

sizes = [50, 100, 200, 300, 400]

forward_errors = deepcopy(sizes)
backward_errors = deepcopy(sizes)
magnification_factors = deepcopy(sizes)
cond_numbers = deepcopy(sizes)

2- 简单地重复值

sizes = [50, 100, 200, 300, 400]

forward_errors = [50, 100, 200, 300, 400]
backward_errors = [50, 100, 200, 300, 400]
magnification_factors = [50, 100, 200, 300, 400]
cond_numbers = [50, 100, 200, 300, 400]

您可以找到有关 here 主题的更多信息。

相关问题