SymPy 提速 sympy-lambdified 函数和矢量化函数
在本文中,我们将介绍如何提速 SymPy 的 sympy-lambdified 函数,并使用矢量化函数进一步优化性能。SymPy 是一个用于符号计算的 Python 库,它提供了强大的数学符号处理功能。sympy-lambdified 函数是 SymPy 中常用的转换符号表达式为可执行函数的方法之一,然而它的执行速度比较慢。通过矢量化函数,我们可以进一步提速。
阅读更多:SymPy 教程
SymPy 和 sympy-lambdified 简介
SymPy 是一个功能强大的计算机代数系统,它提供了符号计算的能力。使用 SymPy,我们可以进行代数运算、求解方程、求导、积分、矩阵运算等等。SymPy 的核心特点是它能够处理符号表达式而不是具体的数值,这使得我们可以进行精确的计算和符号推导。
在 SymPy 中,我们可以通过 sympy-lambdified 函数将符号表达式转化为可执行函数。sympy-lambdified 函数的调用方式如下所示:
import sympy as sp
# 创建符号变量
x, y = sp.symbols("x y")
# 创建符号表达式
expr = sp.sin(x) + sp.cos(y)
# 将符号表达式转化为可执行函数
f = sp.lambdify((x, y), expr, modules="numpy")
# 调用可执行函数进行数值计算
result = f(1, 2)
print(result)
以上代码中,我们首先创建了两个符号变量 x
和 y
,然后定义了一个符号表达式 expr
,其中包含了 x
和 y
的函数。接着,我们使用 lambdify
函数将 expr
转化为可执行函数,并指定了 modules="numpy"
,表示导出的函数会使用 NumPy 来进行数值计算。最后,我们可以通过调用 f
函数并传入实际值来计算结果。
然而,上述使用 sympy-lambdified 得到的函数执行速度相对较慢,因为它对每个输入值都进行了符号表达式的解析和计算。
优化 sympy-lambdified 函数的执行速度
要优化 sympy-lambdified 函数的执行速度,我们可以使用 SymPy 提供的 ufuncify
函数,它将表达式转换为一个可以使用 NumPy 和 SciPy 的通用函数(ufunc)。ufunc 是一种快速执行数学运算的函数,它可以在多个输入上并行执行计算,以提高执行速度。
使用 ufuncify
的方法与 lambdify
相似,调用方式如下所示:
import sympy as sp
import numpy as np
# 创建符号变量
x, y = sp.symbols("x y")
# 创建符号表达式
expr = sp.sin(x) + sp.cos(y)
# 将符号表达式转化为可执行函数
f = sp.ufuncify((x, y), expr)
# 调用可执行函数进行数值计算
result = f(np.array([1, 2, 3]), np.array([4, 5, 6]))
print(result)
通过使用 ufuncify
,我们可以获得更快的执行速度,因为它会将符号表达式转化为可在 NumPy 数组上进行矢量化计算的函数。在上述代码中,我们传入了 NumPy 数组作为输入值,并获得了对应的计算结果。
需要注意的是,使用 ufuncify
时,输入的变量应该是 NumPy 数组或者符合 NumPy 数组接口的对象,这样才能获得最佳的执行效果。
示例:比较 sympy-lambdified 和 ufuncify 的执行速度
下面我们通过一个实例来比较 sympy-lambdified 函数和 ufuncify 函数的执行速度。
首先,我们定义一个较为复杂的符号表达式,包含了多个函数和常量:
import sympy as sp
import numpy as np
# 创建符号变量
x, y, z = sp.symbols("x y z")
# 创建符号表达式
expr = sp.sin(x) / sp.tan(y) + sp.sqrt(z) - sp.log(x ** 2 + y ** 2 + 1) * sp.exp(2 * z)
然后,我们分别使用 sympy-lambdified 函数和 ufuncify 函数将该符号表达式转化为可执行函数,并进行计时:
import time
# 将符号表达式转化为 sympy-lambdified 函数
f_lambdified = sp.lambdify((x, y, z), expr)
# 将符号表达式转化为 ufuncify 函数
f_ufuncify = sp.ufuncify((x, y, z), expr)
# 定义输入值
x_vals = np.random.random(10000)
y_vals = np.random.random(10000)
z_vals = np.random.random(10000)
# 测试 sympy-lambdified 函数的执行速度
start = time.time()
result_lambdified = f_lambdified(x_vals, y_vals, z_vals)
end = time.time()
print("sympy-lambdified 函数执行时间:", end - start)
# 测试 ufuncify 函数的执行速度
start = time.time()
result_ufuncify = f_ufuncify(x_vals, y_vals, z_vals)
end = time.time()
print("ufuncify 函数执行时间:", end - start)
运行上述代码,我们可以得到 sympy-lambdified 函数和 ufuncify 函数的执行时间。
总结
通过本文的介绍,我们了解了如何提速 SymPy 的 sympy-lambdified 函数和使用矢量化函数进一步优化性能。使用 sympy-lambdified 函数,我们可以将符号表达式转化为可执行函数,方便进行数值计算。然而,sympy-lambdified 函数的执行速度相对较慢。通过使用 SymPy 提供的 ufuncify 函数,我们可以得到更快的执行速度,因为它将符号表达式转化为可以在 NumPy 数组上进行矢量化计算的函数。
如果在实际应用中需要大规模计算符号表达式的数值结果,建议使用 ufuncify 函数,以获得更好的执行性能。同时,为了进一步优化性能,注意将输入的变量转化为 NumPy 数组或符合 NumPy 数组接口的对象。
希望本文对您理解 SymPy 的符号计算功能和优化 sympy-lambdified 函数有所帮助。感谢阅读!
参考文献:
– SymPy官方文档:https://docs.sympy.com/
– SymPy GitHub 仓库:https://github.com/sympy/sympy