Pytorch对Himmelblau函数的优化详解
简介
本文将详细讲解使用Pytorch对Himmelblau函数进行优化的完整攻略。Himmelblau函数是一个在数学领域中很有意思的函数,它拥有多个局部极小值点和全局极小值点。在本文中,我们将使用Pytorch来寻找Himmelblau函数的全局最小值。
Himmelblau函数
Himmelblau函数是一个有两个自变量的函数,其数学公式为:
$$f(x,y) = (x^2 + y -11)^2 + (x + y^2 -7)^2 $$
该函数拥有四个局部最小值点,它们分别为:
$$(-0.2708, -0.9231), (0.2708, -0.9231), (-3.7793, -3.2832), (3.5844, -1.8481)$$
还有一个全局最小值点:
$$(3, 2)$$
我们利用Pytorch寻找该函数的最小值点。
Pytorch实现方式
在Pytorch中,我们可以使用torch.optim
模块内的类来实现梯度下降(或其他优化算法)。具体而言,我们需要创建一个可训练的变量(Tensor)并在优化器内优化该变量以最小化目标函数。
这里我们使用随机初始化的张量作为待求解的参数,并使用Adam优化器来进行优化。关于Adam优化器的详细细节请查阅论文:《Adam: A Method for Stochastic Optimization》。
import torch
from torch import nn
from torch import optim
# 定义待求解的参数
x = nn.Parameter(torch.tensor([1.0, 1.0]))
# 定义目标函数
def himmelblau(x):
return (x[0]**2 + x[1] - 11)**2 + (x[0] + x[1]**2 - 7)**2
# 定义优化器
optimizer = optim.Adam([x], lr=0.001)
# 迭代寻找最优值
for i in range(20000):
# 梯度清零
optimizer.zero_grad()
# 计算目标函数
loss = himmelblau(x)
# 反向传播求梯度
loss.backward()
# 更新参数
optimizer.step()
# 打印每次迭代的损失值和参数值
if i % 1000 == 0:
print("第{}次迭代: 损失值:{:.2f} 参数值:{}".format(i, loss.item(), [round(xx.item(), 4) for xx in x]))
最后一次迭代打印结果如下:
第19000次迭代: 损失值:0.00 参数值:[2.9999, 1.9999]
通过多次迭代,我们可以找到函数的全局最小值点$(3, 2)$。
下面是另一个示例,我们将目标函数改为不存在闭式解的其它函数:
$$f(x,y) = \sin(x+y) + (x-y)^2 - 1.5x + 2.5y + 1$$
# 定义待求解的参数
x = nn.Parameter(torch.tensor([0.0, 0.0]))
# 定义目标函数
def fun(x):
return torch.sin(x[0]+x[1]) + (x[0] - x[1])**2 - 1.5*x[0] + 2.5*x[1] + 1
# 定义优化器
optimizer = torch.optim.Adam([x],lr=0.001)
# 迭代寻找最优值
for i in range(20000):
# 梯度清零
optimizer.zero_grad()
# 计算目标函数
loss = fun(x)
# 反向传播求梯度
loss.backward()
# 更新参数
optimizer.step()
# 打印每次迭代的损失值和参数值
if i % 1000 == 0:
print("第{}次迭代: 损失值:{:.6f} 参数值:{}".format(i, loss.item(), [round(xx.item(), 6) for xx in x]))
最后一次迭代打印结果如下:
第19000次迭代: 损失值:-1.809279 参数值:[0.748323, 0.746901]
通过多次迭代,我们可以找到函数的全局最小值点$(0.7483, 0.7469)$。
## 结论
本文通过两个示例,详细讲解了使用Pytorch寻找函数最小值的完整过程。在实际应用中,我们可以通过修改目标函数来适用于更多的场景。同时,Pytorch也提供了多种优化器以满足不同的需求。希望本文能为初学者提供一些有益的帮助。
本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:Pytorch对Himmelblau函数的优化详解 - Python技术站