在Scipy中,我有一个7x7的矩阵,其中有些条目的大小最大为10 ^ 22。
[[7.87720699e+21 5.81984000e+12 4.06283195e+18 1.36914426e+15
6.84296262e+21 1.18920842e+20 2.30532710e+21]
[5.81984000e+12 6.32869618e+03 3.12159108e+09 8.49240505e+05
5.05790011e+12 8.25020510e+10 1.71012096e+12]
[4.06283195e+18 3.12159108e+09 2.10517370e+15 6.90360153e+11
3.52958137e+18 6.08623401e+16 1.18959479e+18]
[1.36914426e+15 8.49240505e+05 6.90360153e+11 2.68568446e+08
1.18907574e+15 2.15022766e+13 3.99729760e+14]
[6.84296262e+21 5.05790011e+12 3.52958137e+18 1.18907574e+15
5.94451366e+21 1.03298010e+20 2.00265814e+21]
[1.18920842e+20 8.25020510e+10 6.08623401e+16 2.15022766e+13
1.03298010e+20 1.81926760e+18 3.47747090e+19]
[2.30532710e+21 1.71012096e+12 1.18959479e+18 3.99729760e+14
2.00265814e+21 3.47747090e+19 6.74706499e+20]]
当我在其上致电spicy.linalg.eigvalsh
时,我会得到
scipy.linalg.eigvalsh(square_matrix)
array([-1.65239967e+05, 3.55247340e+04, 2.64944833e+06, 2.26542682e+09,\n 2.01743752e+14, 5.56910661e+16, 1.44981926e+22])
那不好,因为矩阵是对称的正半定数(形式为AA ^ T),所以它应该具有所有非负特征值。当我只要求特征值最小时,它得到的答案与上次完全不同。
scipy.linalg.eigvalsh(square_matrix, eigvals = (0,0))
array([-464577.85826165])
这是怎么回事?仅仅是数字如此之大以至于在计算中引起巨大的误差?
感谢您的帮助,我对这种数值实验还是有些陌生。
编辑:这是另一个列表形式的列表:
[[178484429459288.62, 1.262534539362581e+16, 5756113437609551.0, 1.5274842899247696e+17, 6343247145.960138, 3119899812227.452, 2.6847705451184886e+17], [1.262534539362581e+16, 9.311154944318847e+17, 4.25182007604871e+17, 1.0968899948471126e+19, 418362473621.39294, 236566750583994.28, 1.929426966567391e+19], [5756113437609551.0, 4.25182007604871e+17, 1.9416578714719302e+17, 5.00372260140452e+18, 190262613997.92053, 108142802848362.1, 8.801791711005543e+18], [1.5274842899247696e+17, 1.0968899948471126e+19, 5.00372260140452e+18, 1.3144272477543575e+20, 5288261203200.205, 2737268307603631.5, 2.3109381789197917e+20], [6343247145.960138, 418362473621.39294, 190262613997.92053, 5288261203200.205, 258730.2206841113, 99079200.39025305, 9282686524313.389], [3119899812227.452, 236566750583994.28, 108142802848362.1, 2737268307603631.5, 99079200.39025305, 61292039604.753365, 4817296126969346.0], [2.6847705451184886e+17, 1.929426966567391e+19, 8.801791711005543e+18, 2.3109381789197917e+20, 9282686524313.389, 4817296126969346.0, 4.0629951073761985e+20]]
scipy.linalg.eigvalsh(square_matrix, eigvals = (0,0))
> array([-9362.07065027])
scipy.linalg.eigvalsh(square_matrix)
> array([3.04005337e+01, 1.06920150e+04, 9.94140064e+06, 3.42415026e+09,\n 2.27074109e+13, 1.99821497e+16, 5.38847690e+20])
我已经确认我在Scipy 1.1.0中。如果有区别的话,这些是在调试过程中在脚本中间获得的。使用VS Code作为IDE。
答案 0 :(得分:1)
矩阵的条目最多达到1e22
,但其最小特征值可能要小得多,可能约为1000。当使用双精度数字执行复杂的计算时(每一步的相对误差为1e-16
,尤其是对于近似特征值的迭代计算时,得到大小为1e-12
的相对误差就不足为奇了。以绝对值表示,它变成1e10
,完全使最小的特征值相形见and,并且很容易使其变为负值。
搜索k个最小或最大特征值是另一项任务:SciPy不仅计算所有特征值并截断输出。在source中,根据eigvals
参数的存在,可以看到对基于LAPACK的代码的不同调用,而且我敢肯定,该参数在LAPACK内部也有不同。所有这些意味着,根据参数eigvals
,您得到的随机错误可能会有所不同。
我正在尝试估算条件数
我建议为此使用np.linalg.cond
。
通常,处理A的奇异值要好于将A的特征值乘以其转置(条件编号gets nearly squared)。