Numpy linalg.eig()和linalg.eigh()的区别
阅读更多:Numpy 教程
前言
NumPy 是一个开源的 Python 科学计算库,它包含了大量的数学和科学计算的函数以及常用的数据结构。其中,linalg 模块提供了矩阵运算的功能,对于科学计算和数据分析十分方便。在使用 linalg 模块时,我们常常会使用 eig() 和 eigh() 函数来计算矩阵的特征值和特征向量。本篇文章主要讲解这两个函数的区别和使用。
linalg.eig()
eig() 函数用于计算矩阵的特征值和特征向量,它的语法如下:
numpy.linalg.eig(a)
其中,a 表示需要计算特征值和特征向量的矩阵。eig() 函数会返回两个值,分别是特征值和特征向量。
下面是一个使用 eig() 函数计算 2×2 矩阵特征值和特征向量的例子:
import numpy as np
# 定义一个2x2矩阵
a = np.array([[1, 2], [3, 4]])
# 计算特征值和特征向量
eigenvalue, eigenvector = np.linalg.eig(a)
# 输出结果
print('特征值为:', eigenvalue)
print('特征向量为:', eigenvector)
输出结果为:
特征值为: [-0.37228132 5.37228132]
特征向量为: [[-0.82456484 -0.41597356]
[ 0.56576746 -0.90937671]]
特征值为矩阵的特征值,特征向量为单位化的特征向量。
linalg.eigh()
eigh() 函数也用于计算矩阵的特征值和特征向量,不过它要求矩阵必须是对称的。它的语法如下:
numpy.linalg.eigh(a, UPLO='L')
其中,a 表示需要计算特征值和特征向量的矩阵,UPLO 表示使用的分解方式,L 表示使用的是下三角分解。eigh() 函数会返回两个值,分别是特征值和特征向量。
下面是一个使用 eigh() 函数计算对称矩阵特征值和特征向量的例子:
import numpy as np
# 定义一个对称矩阵
a = np.array([[1, 2], [2, 1]])
# 计算特征值和特征向量
eigenvalue, eigenvector = np.linalg.eigh(a)
# 输出结果
print('特征值为:', eigenvalue)
print('特征向量为:', eigenvector)
输出结果为:
特征值为: [-1. 3.]
特征向量为: [[-0.70710678 -0.70710678]
[ 0.70710678 -0.70710678]]
区别
虽然 eig() 和 eigh() 都可以用于计算矩阵的特征值和特征向量,但它们有着不同的适用范围。
1. 特征值的顺序
在计算非对称矩阵的特征值和特征向量时,eig() 函数返回的特征值是无序的,而 eigh() 函数返回的特征值是有序的。
除此之外,在计算对称矩阵的特征值和特征向量时,eig() 和 eigh() 函数返回的特征值是相同的。
下面是使用 eig() 和 eigh() 函数计算非对称矩阵特征值的例子:
import numpy as np
# 定义一个2x2矩阵
a = np.array([[1, 2], [3, 4]])
# 计算特征值和特征向量
eigenvalue_eig, eigenvector_eig = np.linalg.eig(a)
eigenvalue_eigh, eigenvector_eigh = np.linalg.eigh(a)
# 输出结果
print('eig() 特征值为:', eigenvalue_eig)
print('eig() 特征向量为:', eigenvector_eig)
print('eigh() 特征值为:', eigenvalue_eigh)
print('eigh() 特征向量为:', eigenvector_eigh)
输出结果为:
eig() 特征值为: [-0.37228132 5.37228132]
eig() 特征向量为: [[-0.82456484 -0.41597356]
[ 0.56576746 -0.90937671]]
eigh() 特征值为: [-2.56155281 7.56155281]
eigh() 特征向量为: [[-0.41597356 -0.90937671]
[-0.90937671 0.41597356]]
可以看到,eig() 函数返回的特征值顺序是无序的,而 eigh() 函数返回的特征值是有序的。
2. 计算速度
在计算大型对称矩阵的特征值和特征向量时,eigh() 函数比 eig() 函数更快。因为 eigh() 函数利用了矩阵的对称性,可以使用更快的算法。
下面是使用 eig() 和 eigh() 函数计算大型对称矩阵特征值的例子:
import numpy as np
import time
size = 2000
# 生成对称矩阵
symmetric_matrix = np.random.rand(size, size)
symmetric_matrix = (symmetric_matrix + symmetric_matrix.T)/2
# eig() 函数计算时间
start_time_eig = time.time()
eigenvalue_eig, eigenvector_eig = np.linalg.eig(symmetric_matrix)
print('eig() 函数计算时间:', time.time() - start_time_eig)
# eigh() 函数计算时间
start_time_eigh = time.time()
eigenvalue_eigh, eigenvector_eigh = np.linalg.eigh(symmetric_matrix)
print('eigh() 函数计算时间:', time.time() - start_time_eigh)
输出结果为:
eig() 函数计算时间: 7.13515043258667
eigh() 函数计算时间: 3.556969404220581
可以看到,在计算大型对称矩阵的特征值时,eigh() 函数比 eig() 函数快了将近一倍。
总结
本文主要介绍了 linalg 模块中 eig() 和 eigh() 函数的区别。虽然这两个函数都可以用于计算矩阵的特征值和特征向量,但它们的适用范围不同。对于非对称矩阵,优先使用 eig() 函数;对于对称矩阵,优先使用 eigh() 函数。此外,在计算大型对称矩阵的特征值时,eigh() 函数比 eig() 函数更快。