这是之前的一篇:矩阵一些运算的时间复杂度,说明了矩阵乘积、矩阵求逆、矩阵的特征值计算和矩阵维度的大致关系。本篇记录不同大小的矩阵的内存占用和计算时间,以 Python 程序为例。其中,时间测试包括了:矩阵创建、for 循环赋值、numba for 循环赋值,以及矩阵的迹、矩阵转置、矩阵加法、矩阵行列式、矩阵乘法、矩阵求逆、矩阵的秩、矩阵的特征值、矩阵的特征值和特征向量。
内存占用的主要结论:
- 如果程序中存在多个大矩阵,那么程序的预期内存占用大概是 4~10 倍的单个矩阵的内存占用。
- 当矩阵维度为 7000,单个矩阵的内存占用会接近 400M,内存大于 2G~4G 的设备可以计算。
- 当矩阵维度为 10000,单个矩阵的内存占用会接近 1GB,内存大于 4G~10G 的设备可以计算。
- 当矩阵维度为 20000,单个矩阵的内存占用会超过 3GB,内存大于 12G~30G 的设备可以计算。
- 当矩阵维度为 30000,单个矩阵的内存占用会接近 7GB,内存大于 28G~70G 的设备可以计算。
计算时间的主要结论:
- 当矩阵维度为 20000,对于矩阵乘法、矩阵求逆、矩阵的秩、矩阵的特征值和特征向量等运算,计算时间就显得稍长了。一般来说,矩阵维度控制在 10000 以下或左右,计算起来会轻松一些。
- 大矩阵的计算时间的大概排序为:矩阵的迹 < 矩阵转置 < 矩阵加法 < numba for 循环赋值 < 矩阵创建 < for 循环赋值 < 矩阵行列式 < 矩阵乘法 < 矩阵求逆 < 矩阵的秩 < 矩阵的特征值 < 矩阵的特征值和特征向量。
- numba for 循环赋值比直接的 for 循环赋值快很多,因此当涉及比较多的 for 循环时,可以考虑用 numba 进行优化,参考:Numba加速Python的时间测试。
- 对于矩阵乘法、矩阵求逆、矩阵的秩、矩阵的特征值和特征向量等运算,多核计算比单核计算有明显的并行加速,参考:不同CPU核数对矩阵运算的加速效果。
测试代码如下:
"""
This code is supported by the website: https://www.guanjihuan.com
The newest version of this code is on the web page: https://www.guanjihuan.com/archives/45275
"""
import numpy as np
import time
import sys
from numba import jit
n_array = np.concatenate((np.arange(1000, 10000, 1000), np.arange(10000, 40000, 10000)))
print(f'n_array={n_array}\n')
@jit
def numba_test(C, n):
for i0 in range(n):
for j0 in range(n):
C[i0, j0] = np.random.rand()
return C
for n in n_array:
print(f'n={n}')
A = np.random.rand(n, n)
B = np.random.rand(n, n)
C = np.random.rand(n, n)
# 矩阵占用内存
size = sys.getsizeof(C)
print(f'矩阵占用内存: {size/(1024*1024):.2f} MB')
# 矩阵的迹
start_time = time.time()
trace_A = np.trace(A)
trace_time = time.time() - start_time
print(f"矩阵的迹时间: {trace_time:.3f} 秒")
# 矩阵转置
start_time = time.time()
A_T = A.T
transpose_time = time.time() - start_time
print(f"矩阵转置时间: {transpose_time:.3f} 秒")
# 矩阵加法
start_time = time.time()
C = A + B
add_time = time.time() - start_time
print(f"矩阵加法时间: {add_time:.3f} 秒")
# numba for 循环赋值
start_time = time.time()
numba_test(C, n)
create_time = time.time() - start_time
print(f"numba for 循环赋值时间: {create_time:.3f} 秒")
# 矩阵创建
start_time = time.time()
C = np.random.rand(n, n)
create_time = time.time() - start_time
print(f"矩阵创建时间: {create_time:.3f} 秒")
# for 循环赋值
start_time = time.time()
for i0 in range(n):
for j0 in range(n):
C[i0, j0] = np.random.rand()
create_time = time.time() - start_time
print(f"for 循环赋值时间: {create_time:.3f} 秒")
# 矩阵行列式
start_time = time.time()
det_A = np.linalg.det(A)
det_time = time.time() - start_time
print(f"矩阵行列式时间: {det_time:.3f} 秒")
# 矩阵乘法
start_time = time.time()
C = np.dot(A, B)
multiply_time = time.time() - start_time
print(f"矩阵乘法时间: {multiply_time:.3f} 秒")
# 矩阵求逆
start_time = time.time()
inv_A = np.linalg.inv(A)
inv_time = time.time() - start_time
print(f"矩阵求逆时间: {inv_time:.3f} 秒")
# 矩阵的秩
start_time = time.time()
rank_A = np.linalg.matrix_rank(A)
rank_time = time.time() - start_time
print(f"矩阵的秩时间: {rank_time:.3f} 秒")
# 矩阵的特征值
start_time = time.time()
eigenvalues_A = np.linalg.eigvals(A)
eigen_time = time.time() - start_time
print(f"矩阵特征值时间: {eigen_time:.3f} 秒")
# 矩阵的特征值和特征向量
start_time = time.time()
eigenvalues_A, eigenvector_A = np.linalg.eig(A)
eigen_time = time.time() - start_time
print(f"矩阵特征值和特征向量时间: {eigen_time:.3f} 秒")
print()
运行结果(单核):
n_array=[ 1000 2000 3000 4000 5000 6000 7000 8000 9000 10000 20000 30000
40000 50000]
n=1000
矩阵占用内存: 7.63 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.000 秒
矩阵加法时间: 0.006 秒
numba for 循环赋值时间: 1.597 秒
矩阵创建时间: 0.009 秒
for 循环赋值时间: 0.446 秒
矩阵行列式时间: 0.054 秒
矩阵乘法时间: 0.095 秒
矩阵求逆时间: 0.119 秒
矩阵的秩时间: 0.281 秒
矩阵特征值时间: 0.628 秒
矩阵特征值和特征向量时间: 0.886 秒
n=2000
矩阵占用内存: 30.52 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.000 秒
矩阵加法时间: 0.015 秒
numba for 循环赋值时间: 0.020 秒
矩阵创建时间: 0.026 秒
for 循环赋值时间: 1.773 秒
矩阵行列式时间: 0.186 秒
矩阵乘法时间: 0.336 秒
矩阵求逆时间: 0.537 秒
矩阵的秩时间: 2.037 秒
矩阵特征值时间: 2.895 秒
矩阵特征值和特征向量时间: 4.975 秒
n=3000
矩阵占用内存: 68.66 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.000 秒
矩阵加法时间: 0.035 秒
numba for 循环赋值时间: 0.044 秒
矩阵创建时间: 0.075 秒
for 循环赋值时间: 4.004 秒
矩阵行列式时间: 0.546 秒
矩阵乘法时间: 1.128 秒
矩阵求逆时间: 1.701 秒
矩阵的秩时间: 3.218 秒
矩阵特征值时间: 9.864 秒
矩阵特征值和特征向量时间: 15.712 秒
n=4000
矩阵占用内存: 122.07 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.000 秒
矩阵加法时间: 0.062 秒
numba for 循环赋值时间: 0.078 秒
矩阵创建时间: 0.132 秒
for 循环赋值时间: 7.124 秒
矩阵行列式时间: 1.257 秒
矩阵乘法时间: 2.645 秒
矩阵求逆时间: 3.971 秒
矩阵的秩时间: 7.724 秒
矩阵特征值时间: 23.538 秒
矩阵特征值和特征向量时间: 37.521 秒
n=5000
矩阵占用内存: 190.73 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.000 秒
矩阵加法时间: 0.097 秒
numba for 循环赋值时间: 0.123 秒
矩阵创建时间: 0.205 秒
for 循环赋值时间: 11.185 秒
矩阵行列式时间: 2.321 秒
矩阵乘法时间: 5.168 秒
矩阵求逆时间: 7.605 秒
矩阵的秩时间: 13.565 秒
矩阵特征值时间: 45.365 秒
矩阵特征值和特征向量时间: 80.265 秒
n=6000
矩阵占用内存: 274.66 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.001 秒
矩阵加法时间: 0.141 秒
numba for 循环赋值时间: 0.211 秒
矩阵创建时间: 0.329 秒
for 循环赋值时间: 19.439 秒
矩阵行列式时间: 3.900 秒
矩阵乘法时间: 9.506 秒
矩阵求逆时间: 14.469 秒
矩阵的秩时间: 23.906 秒
矩阵特征值时间: 89.140 秒
矩阵特征值和特征向量时间: 136.497 秒
n=7000
矩阵占用内存: 373.84 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.001 秒
矩阵加法时间: 0.199 秒
numba for 循环赋值时间: 0.290 秒
矩阵创建时间: 0.472 秒
for 循环赋值时间: 25.998 秒
矩阵行列式时间: 6.091 秒
矩阵乘法时间: 15.412 秒
矩阵求逆时间: 22.411 秒
矩阵的秩时间: 38.326 秒
矩阵特征值时间: 124.900 秒
矩阵特征值和特征向量时间: 210.791 秒
n=8000
矩阵占用内存: 488.28 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.001 秒
矩阵加法时间: 0.244 秒
numba for 循环赋值时间: 0.344 秒
矩阵创建时间: 0.521 秒
for 循环赋值时间: 29.591 秒
矩阵行列式时间: 8.753 秒
矩阵乘法时间: 20.965 秒
矩阵求逆时间: 30.456 秒
矩阵的秩时间: 52.435 秒
矩阵特征值时间: 195.694 秒
矩阵特征值和特征向量时间: 294.924 秒
n=9000
矩阵占用内存: 617.98 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.001 秒
矩阵加法时间: 0.311 秒
numba for 循环赋值时间: 0.456 秒
矩阵创建时间: 0.752 秒
for 循环赋值时间: 41.978 秒
矩阵行列式时间: 12.345 秒
矩阵乘法时间: 31.079 秒
矩阵求逆时间: 45.033 秒
矩阵的秩时间: 79.933 秒
矩阵特征值时间: 289.316 秒
矩阵特征值和特征向量时间: 407.273 秒
n=10000
矩阵占用内存: 762.94 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.002 秒
矩阵加法时间: 0.391 秒
numba for 循环赋值时间: 0.575 秒
矩阵创建时间: 0.944 秒
for 循环赋值时间: 51.109 秒
矩阵行列式时间: 17.626 秒
矩阵乘法时间: 42.732 秒
矩阵求逆时间: 60.364 秒
矩阵的秩时间: 106.439 秒
矩阵特征值时间: 380.776 秒
矩阵特征值和特征向量时间: 611.635 秒
n=20000
矩阵占用内存: 3051.76 MB
矩阵的迹时间: 0.001 秒
矩阵转置时间: 0.003 秒
矩阵加法时间: 1.640 秒
numba for 循环赋值时间: 2.291 秒
矩阵创建时间: 3.738 秒
for 循环赋值时间: 212.194 秒
矩阵行列式时间: 137.455 秒
矩阵乘法时间: 341.421 秒
矩阵求逆时间: 482.127 秒
矩阵的秩时间: 766.457 秒
矩阵特征值时间: 2775.898 秒
矩阵特征值和特征向量时间: 4807.064 秒
n=30000
矩阵占用内存: 6866.46 MB
矩阵的迹时间: 0.001 秒
矩阵转置时间: 0.007 秒
矩阵加法时间: 6.090 秒
numba for 循环赋值时间: 5.195 秒
矩阵创建时间: 8.435 秒
for 循环赋值时间: 477.623 秒
矩阵行列式时间: 430.537 秒
矩阵乘法时间: 1168.907 秒
矩阵求逆时间: 1614.139 秒
矩阵的秩时间: 2272.073 秒
矩阵特征值时间: 9281.661 秒
矩阵特征值和特征向量时间: 15251.770 秒
运行结果(四核):
n_array=[ 1000 2000 3000 4000 5000 6000 7000 8000 9000 10000 20000 30000
40000 50000]
n=1000
矩阵占用内存: 7.63 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.000 秒
矩阵加法时间: 0.005 秒
numba for 循环赋值时间: 1.153 秒
矩阵创建时间: 0.014 秒
for 循环赋值时间: 0.541 秒
矩阵行列式时间: 0.208 秒
矩阵乘法时间: 0.068 秒
矩阵求逆时间: 0.080 秒
矩阵的秩时间: 0.145 秒
矩阵特征值时间: 0.555 秒
矩阵特征值和特征向量时间: 0.790 秒
n=2000
矩阵占用内存: 30.52 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.000 秒
矩阵加法时间: 0.016 秒
numba for 循环赋值时间: 0.023 秒
矩阵创建时间: 0.030 秒
for 循环赋值时间: 2.066 秒
矩阵行列式时间: 0.075 秒
矩阵乘法时间: 0.106 秒
矩阵求逆时间: 0.221 秒
矩阵的秩时间: 0.969 秒
矩阵特征值时间: 2.053 秒
矩阵特征值和特征向量时间: 3.304 秒
n=3000
矩阵占用内存: 68.66 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.000 秒
矩阵加法时间: 0.026 秒
numba for 循环赋值时间: 0.050 秒
矩阵创建时间: 0.083 秒
for 循环赋值时间: 4.545 秒
矩阵行列式时间: 0.223 秒
矩阵乘法时间: 0.332 秒
矩阵求逆时间: 0.622 秒
矩阵的秩时间: 1.657 秒
矩阵特征值时间: 6.039 秒
矩阵特征值和特征向量时间: 10.583 秒
n=4000
矩阵占用内存: 122.07 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.000 秒
矩阵加法时间: 0.065 秒
numba for 循环赋值时间: 0.090 秒
矩阵创建时间: 0.147 秒
for 循环赋值时间: 8.224 秒
矩阵行列式时间: 0.483 秒
矩阵乘法时间: 0.781 秒
矩阵求逆时间: 1.441 秒
矩阵的秩时间: 3.980 秒
矩阵特征值时间: 13.757 秒
矩阵特征值和特征向量时间: 21.800 秒
n=5000
矩阵占用内存: 190.73 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.000 秒
矩阵加法时间: 0.099 秒
numba for 循环赋值时间: 0.139 秒
矩阵创建时间: 0.228 秒
for 循环赋值时间: 12.640 秒
矩阵行列式时间: 0.726 秒
矩阵乘法时间: 1.483 秒
矩阵求逆时间: 3.393 秒
矩阵的秩时间: 6.026 秒
矩阵特征值时间: 21.143 秒
矩阵特征值和特征向量时间: 41.571 秒
n=6000
矩阵占用内存: 274.66 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.001 秒
矩阵加法时间: 0.146 秒
numba for 循环赋值时间: 0.201 秒
矩阵创建时间: 0.330 秒
for 循环赋值时间: 18.506 秒
矩阵行列式时间: 1.481 秒
矩阵乘法时间: 2.536 秒
矩阵求逆时间: 3.998 秒
矩阵的秩时间: 9.744 秒
矩阵特征值时间: 42.314 秒
矩阵特征值和特征向量时间: 74.825 秒
n=7000
矩阵占用内存: 373.84 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.001 秒
矩阵加法时间: 0.192 秒
numba for 循环赋值时间: 0.268 秒
矩阵创建时间: 0.442 秒
for 循环赋值时间: 24.707 秒
矩阵行列式时间: 2.349 秒
矩阵乘法时间: 3.933 秒
矩阵求逆时间: 5.928 秒
矩阵的秩时间: 13.863 秒
矩阵特征值时间: 58.228 秒
矩阵特征值和特征向量时间: 112.797 秒
n=8000
矩阵占用内存: 488.28 MB
矩阵的迹时间: 0.001 秒
矩阵转置时间: 0.001 秒
矩阵加法时间: 0.245 秒
numba for 循环赋值时间: 0.313 秒
矩阵创建时间: 0.521 秒
for 循环赋值时间: 28.609 秒
矩阵行列式时间: 3.166 秒
矩阵乘法时间: 7.573 秒
矩阵求逆时间: 10.245 秒
矩阵的秩时间: 22.854 秒
矩阵特征值时间: 98.880 秒
矩阵特征值和特征向量时间: 175.645 秒
n=9000
矩阵占用内存: 617.98 MB
矩阵的迹时间: 0.000 秒
矩阵转置时间: 0.001 秒
矩阵加法时间: 0.310 秒
numba for 循环赋值时间: 0.396 秒
矩阵创建时间: 0.659 秒
for 循环赋值时间: 36.487 秒
矩阵行列式时间: 4.417 秒
矩阵乘法时间: 10.234 秒
矩阵求逆时间: 15.217 秒
矩阵的秩时间: 30.049 秒
矩阵特征值时间: 138.918 秒
矩阵特征值和特征向量时间: 244.765 秒
n=10000
矩阵占用内存: 762.94 MB
矩阵的迹时间: 0.254 秒
矩阵转置时间: 0.002 秒
矩阵加法时间: 0.380 秒
numba for 循环赋值时间: 0.490 秒
矩阵创建时间: 0.813 秒
for 循环赋值时间: 45.182 秒
矩阵行列式时间: 5.552 秒
矩阵乘法时间: 13.261 秒
矩阵求逆时间: 18.668 秒
矩阵的秩时间: 40.731 秒
矩阵特征值时间: 176.486 秒
矩阵特征值和特征向量时间: 306.722 秒
n=20000
矩阵占用内存: 3051.76 MB
矩阵的迹时间: 0.002 秒
矩阵转置时间: 0.002 秒
矩阵加法时间: 1.526 秒
numba for 循环赋值时间: 1.953 秒
矩阵创建时间: 3.255 秒
for 循环赋值时间: 180.067 秒
矩阵行列式时间: 36.621 秒
矩阵乘法时间: 104.103 秒
矩阵求逆时间: 145.663 秒
矩阵的秩时间: 276.173 秒
矩阵特征值时间: 1243.477 秒
矩阵特征值和特征向量时间: 2490.158 秒
n=30000
矩阵占用内存: 6866.46 MB
矩阵的迹时间: 0.001 秒
矩阵转置时间: 0.007 秒
矩阵加法时间: 3.416 秒
numba for 循环赋值时间: 4.389 秒
矩阵创建时间: 7.314 秒
for 循环赋值时间: 402.068 秒
矩阵行列式时间: 138.942 秒
矩阵乘法时间: 340.128 秒
矩阵求逆时间: 464.236 秒
矩阵的秩时间: 844.484 秒
矩阵特征值时间: 3988.969 秒
矩阵特征值和特征向量时间: 8426.078 秒
【说明:本站主要是个人的一些笔记和代码分享,内容可能会不定期修改。为了使全网显示的始终是最新版本,这里的文章未经同意请勿转载。引用请注明出处:https://www.guanjihuan.com】