首页 > 其他分享 >pytorch损失函数

pytorch损失函数

时间:2023-11-07 15:01:13浏览次数:35  
标签:plt 函数 nn torch 损失 pytorch import true

pytorch损失函数

目录

损失函数 名称 场景
nn.MSELoss() 均方误差损失(MSE) 回归
nn.L1Loss() 平均绝对误差损失(MAE) 回归
nn.SmoothL1Loss() 平滑L1损失 回归
nn.HuberLoss() Huber损失,平滑平均绝对误差 回归
nn.BCELoss() 二分类交叉熵,结合sigmoid函数使用 分类
nn.BCEWithLogitsLoss() 二分分类交叉熵 分类
nn.CrossEntropyLoss() 多分类交叉熵损失函数 分类
nn.NLLLoss() 负对数似然损失,结合结合log softmax使用 分类
nn.CosineSimilarity() 余弦相似度 计算距离
均方误差            L2 范数  nn.MSELoss()
平均绝对误差         L1 范数  nn.L1Loss()

Smooth L1 Loss     Smooth L1 Loss   nn.SmoothL1Loss()
Huber损失           HuberLoss        nn.HuberLoss()
 
KL散度损失                           nn.KLDivLoss()
负对数似然损失                        nn.NLLLoss()

二分类交叉熵损失     nn.BCELoss()
多类别交叉熵损失     nn.CrossEntropyLoss()

余弦相似度损失

损失函数概念

损失函数: 衡量模型输出与真实标签的差异。

通常,说到损失函数会出现3个概念

(1)损失函数(Loss Function):计算单样本的差异

\[Loss=f( y , \hat{y}) \]

(2)代价函数(Cost Function):计算整个训练集、样本集(所有样本)Loss的平均值

\[Cost=\frac{1}{n}\sum_{i-1}^{n}( y , \hat{y}) \]

(3)目标函数(Objective Function):训练模型的最终目标—目标包含cost和Regularization

\[Obj=Cost + Regularization \]

均方误差损失Mean Squared Error,MSE

均方误差是一种常用的损失函数,通常用于衡量回归模型预测结果与真实值之间的差异程度。

均方误差是通过计算预测值与真实值之间差异的平方和来衡量模型的性能。
它对于较大的差异给予更高的权重,因为平方操作会放大较大的差异。
均方误差的数值越小,表示模型预测的结果与真实值越接近。
公式如下

\[MSE=\frac{1}{n}\sum_{i-1}^{n}\left ( y_{i} - \hat{y} _{i} \right )^{2} \]

# torch 损失函数
torch.nn.MSELoss(*size_average=None*, *reduce=None*, *reduction='mean'*)
import numpy as np
import matplotlib.pyplot as plt
import torch
import torch.nn as nn

plt.style.use("seaborn-v0_8-whitegrid")

# 真实值和预测值  y_true,y_pred
y_pred = np.array(range(1,20))
y_true = y_pred + np.random.randn(19)    

# 计算均方误差
mse = np.mean((y_true - y_pred) ** 2)
print("MSE:", mse)

# torch 
mseloss=nn.MSELoss()
mse=mseloss.forward(torch.tensor(y_true),torch.tensor(y_pred))
print("mse",mse)

# 绘制真实值和预测值的散点图
plt.scatter(y_true, y_true,c="g")
plt.scatter(y_true, y_pred,c="r")

plt.plot([min(y_true), max(y_true)], [min(y_true), max(y_true)], 'k--',c="b", lw=2)  # 绘制直线y=x
plt.xlabel('True Values')
plt.ylabel('Predicted Values')
plt.title('Scatter plot of True vs Predicted Values')
plt.show()

# MSE: 1.3939309147057835
# mse tensor(1.3939, dtype=torch.float64)
img

平均绝对误差损失Mean Absolute Error, MAE

平均绝对误差(Mean Absolute Error,MAE)是一种用于衡量预测模型性能的损失函数,通常用于回归问题。
它衡量了模型的预测值与实际观测值之间的平均绝对差异。MAE 的值越小,表示模型的预测越准确。

MAE 的原理非常简单,它是所有绝对误差的平均值。绝对误差是指每个观测值的预测值与实际值之间的差的绝对值。
MAE 的计算过程非常直观,它将每个样本的绝对误差取绝对值后求平均,因此它对异常值不敏感。
平均绝对误差的计算公式:

\[MAE=\frac{1}{n}\sum_{i=1}^{n}\left | y _{i} - \hat{y} _{i} \right | \]

# torch 损失函数
criterion = nn.L1Loss()
import numpy as np
import matplotlib.pyplot as plt
import torch
import torch.nn as nn

plt.style.use("seaborn-v0_8-whitegrid")

# 生成随机数据
np.random.seed(0)
n = 50
X = np.linspace(0, 10, n)
# y_true y_pred
y_pred = 2 * X   # 模拟的预测值
y_true = 2 * X  + np.random.normal(0, 1, n) * 0.5   # 真实的目标值,包含随机噪音
# 计算MAE
mae = np.mean(np.abs(y_true - y_pred))

# torch 计算
maeloss= nn.L1Loss()
maetorch=maeloss(torch.tensor(y_true),torch.tensor(y_pred))
print(mae,maetorch)

# 绘制数据点和预测线
plt.scatter(X, y_true, label='Actual', color='g')
plt.scatter(X, y_pred, label='Predicted', color='r')
plt.title(f'MAE = {mae:.2f}')
plt.xlabel('X')
plt.ylabel('y')
plt.legend()
plt.show()

# 0.45699838217894007 tensor(0.4570, dtype=torch.float64)
img

平滑L1损失,Smooth L1 Loss

Smooth L1 结合了 MSE 和 MAE 的优点,来自 Fast R-CNN 论文

当真实值和预测值之间的绝对差低于 β  时,使用 MSE 损失。
MSE 损失曲线是一条连续曲线,这意味着每个损失值处的梯度都会变化,并且可以在任何地方可导。
然而,对于非常大的损失值,梯度爆炸,使用平均绝对误差,
当绝对差变得大于 β 并且消除了潜在的梯度爆炸时,其梯度对于每个损失值几乎是恒定的。

\[l_{n}=\begin{cases}0.5(x_{n}-y_{n})^{2} / \delta,if \left | x_{n} -y_{n} \right |< \delta \\ \left | x_{n} -y_{n} \right | - 0.5* \delta, \end{cases} \]

torch.nn.SmoothL1Loss(size_average=None, *reduce=None, reduction='mean', beta=1.0)
import torch

loss = torch.nn.SmoothL1Loss()
input = torch.randn(3, 5, requires_grad=True)
target = torch.randn(3, 5)
output1 = loss(input, target)
print('output1: ',output1)
# output1:  tensor(0.7812, grad_fn=<SmoothL1LossBackward0>)

平滑平均绝对误差,Huber损失

Huber损失又称平滑平均绝对误差

Huber损失是一种用于回归问题的损失函数, 使用 detla 进行了缩放,结合L1Loss和MSELoss的优点

它对异常值不敏感,相比于均方误差(MSE),它对异常值的惩罚较小。

Huber损失的主要思想是在距离真实值较近的情况下采用均方误差,而在距离较远的情况下采用绝对误差,当δ趋向于0时它就退化成了MAE,而当δ趋向于无穷时则退化为了MSE

这种权衡可以有效减少异常值的影响。

\[l_{n}=\begin{cases}0.5(x_{n}-y_{n})^{2},if \left | x_{n} -y_{n} \right |\le \delta \\ \delta * (\left | x_{n} -y_{n} \right | - 0.5* \delta), \end{cases} \]

torch.nn.HuberLoss(reduction='mean', delta=1.0)

交叉熵损失Cross-Entropy Loss

交叉熵损失(Cross-Entropy Loss)是机器学习中常用的一种损失函数,主要应用于分类问题。

它用于衡量模型预测结果与实际标签之间的差异。

交叉熵损失基于信息论中的交叉熵概念,用于度量两个概率分布之间的相似性。
在分类问题中,我们将实际标签表示为一个one-hot向量,即只有一个元素为1,其余元素为0;而模型的预测结果通常是一个概率分布。
交叉熵损失通过计算实际标签和模型预测结果之间的交叉熵来评估模型的性能。
交叉熵:它主要刻画的是实际输出(概率)与期望输出(概率)的距离,也就是交叉熵的值越小,两个概率分布就越接近

\[Loss=-\sum_{i=1}^{n} y_{i}log(p_{i}) \]

其中 为实际标签中第个类别的概率(one-hot编码),为模型预测的第个类别的概率。

import numpy as np
import matplotlib.pyplot as plt

def cross_entropy_loss(y_true, p_pred):
    epsilon = 1e-10  # 添加一个小的常数以避免log(0)计算错误
    return -np.sum(y_true * np.log(p_pred + epsilon), axis=1)

# 模拟数据
num_samples = 1000
num_classes = 5

np.random.seed(42)
y_true = np.eye(num_classes)[np.random.choice(num_classes, num_samples)]  # 生成随机的one-hot标签
p_pred = np.random.rand(num_samples, num_classes)  # 模型预测的概率

loss = cross_entropy_loss(y_true, p_pred)

# 计算平均损失
average_loss = np.mean(loss)

# 绘制损失函数图形
plt.plot(range(num_samples), loss, 'bo', markersize=2)
plt.xlabel('Sample')
plt.ylabel('Cross-Entropy Loss')
plt.title('Cross-Entropy Loss for each Sample')
plt.axhline(average_loss, color='r', linestyle='--', label='Average Loss')
plt.legend()
plt.show()

print(f'Average Loss: {average_loss}')
img
二分类交叉熵损失:

criterion = nn.BCELoss()

多类别交叉熵损失:
torch.nn.CrossEntropyLoss(*weight=None*, *size_average=None*, *ignore_index=- 100*, *reduce=None*, *reduction='mean'*, *label_smoothing=0.0*)

KL散度损失Kullback-Leibler Divergence Loss

通常在生成模型中使用,用于测量两个概率分布之间的差异。

\[L(y_{pred},y_{true})=y_{true}\cdot log\frac{y_{true}}{y_{pred}} = y_{true}\cdot (log y_{true}-log y_{pred}) \]

criterion = nn.KLDivLoss()
import  numpy as np
import torch
import torch.nn.functional as F
import torch.nn as nn 

kl_loss = nn.KLDivLoss(reduction="batchmean")
# input should be a distribution in the log space
input1 = F.log_softmax(torch.randn(3, 5, requires_grad=True), dim=1)
# Sample a batch of distributions. Usually this would come from the dataset
input2 = torch.rand(3, 5)
print(input1)

target = F.softmax(input2, dim=1)
output = kl_loss(input1, target)

print(output)

kl_loss = nn.KLDivLoss(reduction="batchmean", log_target=True)
log_target = F.log_softmax(input2, dim=1)
output = kl_loss(input1, log_target)

print(output)

# tensor([[-3.1245, -0.4438, -2.7561, -2.9293, -1.6223],
#         [-1.6743, -2.2721, -1.2506, -0.9937, -2.9387],
#         [-1.0872, -2.4577, -1.0433, -1.6925, -3.1981]],
#        grad_fn=<LogSoftmaxBackward0>)
# tensor(0.4822, grad_fn=<DivBackward0>)
# tensor(0.4822, grad_fn=<DivBackward0>)

负对数似然损失(Negative Log Likelihood Loss)

Negative Log-Likelihood (NLL) 损失函数的工作原理与交叉熵损失函数非常相似

NLL要求网络最后一层使用 softmax 作为激活函数。通过softmax将输出值映射为每个类别的概率值。

criterion = nn.NLLLoss()
import  numpy as np
import torch
import torch.nn.functional as F
import torch.nn as nn 

m = nn.LogSoftmax(dim=1)
loss = nn.NLLLoss()
# input is of size N x C = 3 x 5
input = torch.randn(3, 5, requires_grad=True)
# each element in target has to have 0 <= value < C
target = torch.tensor([1, 0, 4])
output = loss(m(input), target)
print(output)
# tensor(1.6105, grad_fn=<NllLossBackward0>)

# 案例2
# 2D loss example (used, for example, with image inputs)
N, C = 5, 4
loss = nn.NLLLoss()
# input is of size N x C x height x width
data = torch.randn(N, 16, 10, 10)
conv = nn.Conv2d(16, C, (3, 3))
m = nn.LogSoftmax(dim=1)
# each element in target has to have 0 <= value < C
target = torch.empty(N, 8, 8, dtype=torch.long).random_(0, C)
output = loss(m(conv(data)), target)
print(output)
# tensor(1.5389, grad_fn=<NllLoss2DBackward0>)

余弦相似度损失Cosine Similarity Loss

余弦相似度损失是一种常用的机器学习损失函数,用于衡量向量之间的相似性。

它基于向量的内积和范数来计算相似度,并将其转化为一个损失值。

\[similarity(A,B)=\frac{A\cdot B}{\left | \left |A \right | | \left |B \right | \right | } \]

余弦相似度损失基于余弦相似度的概念。余弦相似度是两个向量之间的夹角的余弦值,范围在-1到1之间。
当夹角为0度时,余弦相似度为1,表示两个向量完全相同;
当夹角为90度时,余弦相似度为0,表示两个向量无关;
当夹角为180度时,余弦相似度为-1,表示两个向量完全相反。
# nn.CosineSimilarity(dim=1, eps=1e-08)
import torch
import torch.nn as nn
import torch.nn.functional as F

batch_sz = 5; num_feat = 128
loss_fn = torch.nn.CosineEmbeddingLoss()
v1 = torch.randn(batch_sz, num_feat)
v2 = torch.randn(batch_sz, num_feat)
target = torch.randint(2, size=(batch_sz,))*2 -1
res = loss_fn(v1, v2, target)
print(res)
# # tensor(0.3383)

参考资料

https://pytorch.org/docs/stable/nn.html#loss-functions 官网

https://mp.weixin.qq.com/s/vzh1We1rNVv1ZFWsxYTGMA

https://mp.weixin.qq.com/s/ugFeeHJlRerSwjygaXpOaQ

https://mp.weixin.qq.com/s/U8Bixzp1U4RoEz1W_YKhOQ

https://juejin.cn/post/7025444819379945503

https://www.cnblogs.com/peachtea/p/13461817.html

标签:plt,函数,nn,torch,损失,pytorch,import,true
From: https://www.cnblogs.com/tian777/p/17815018.html

相关文章

  • C++中的高阶函数 -- std::function实现回调
    C++中的高阶函数:以std::function优雅地实现回调1.简介1.1C++高阶函数的概念在函数式编程语言中,高阶函数(Higher-orderFunction)是一个常见的概念,它通常被定义为满足下列条件之一的函数: 接受一个或多个函数作为输入(参数)输出(返回值)是一个函数C++作为一门多范式编程语言,也......
  • C++ lambda函数总结
    C++lambda函数1lambda函数简介名称lambda来自lambdacalculus(lambda演算),一种定义和应用函数的数学系统。这个系统中可以使用匿名函数,对于接收函数指针或伪函数的函数,可以使用匿名函数定义(lambda)作为其参数。1.1为什么使用lambda函数?距离:定义位于使用的地方附近很有用,由于......
  • python初学者学习笔记-第五章-函数
    chapter5/函数5.1函数基础5.1.1函数形式函数是可实现一个或多个功能的代码块;函数的特点:重用性、模块化;Python的内置函数,如print()、len()、min()、max()等;同时,我们也可以自定义函数;5.1.2函数调用参数是函数重要组成部分,python的参数灵活多样;参数类型:默认参数,关键字......
  • 函数计算 FC 3.0 发布,全面降价,最高幅度达93%,阶梯计费越用越便宜
    作为国内最早布局Serverless的云厂商之一,阿里云在2017年推出函数计算FC,开发者只需编写代码并上传,函数计算就会自动准备好相应的计算资源,大幅简化开发运维过程。阿里云函数计算持续在ServerlessGPU方面投入研发,拥有极致弹性的GPU实例,以及大规格的函数计算性能实例,为承载......
  • 无涯教程-批处理 - EXPAND函数
    此批处理命令从压缩的.cab机柜文件中提取文件。EXPAND-语法EXPAND[cabinetfilename]EXPAND-示例@echooffEXPANDexcel.cab上面的命令将在当前位置提取excel.cab文件的内容。参考链接https://www.learnfk.com/batch-script/batch-script-expand.html......
  • 无涯教程-批处理 - DRIVERQUERY函数
    此批处理命令显示所有已安装的设备驱动程序及其属性。DRIVERQUERY-语法driverqueryDRIVERQUERY-示例@echooffdriverquery上面的命令将显示当前系统上安装的所有设备驱动程序的信息。以下是显示的信息子集的示例。WacomPenWacomSerialPenHIDDKernel......
  • oracle函数大全-字符串处理函数
    字符函数——返回字符值这些函数全都接收的是字符族类型的参数(CHR除外)并且返回字符值.除了特别说明的之外,这些函数大部分返回VARCHAR2类型的数值.字符函数的返回类型所受的限制和基本数据库类型所受的限制是相同的,比如:VARCHAR2数值被限制为2000字符(ORACLE8中为4000字符),......
  • Oracle 日期时间函数
    常用的时间格式在oracle中有yyyy-mm-ddhh24:mi:ss 而在Java中有些区别为yyyy-MM-ddHH:mm:ss这点还是经常容易模糊的。相信很多人都有过统计某些数据的经历,比如,要统计财务的情况,可能要按每年,每季度,每月,甚至每个星期来分别统计。那在oracle中应该怎么来写sql语句呢,这个时候Or......
  • Matlab命令集--常用字符串函数
    Matlab命令集--常用字符串函数常用函数eval :运行字符串表示的表达式char :将数组变成字符串double:将数字字符串变成数字字符串操作deblank:去掉字符串末尾的空格findstr:查找字符串lower  :转换为小写strcat :字符串连接组合strcmp :字符串比较strcmpi:字符串比较(......
  • PyTorch Tensor创建方法
    PyTorch提供了多种方法来创建张量。以下是一些常见的创建张量的方式:创建未初始化的张量#创建一个未初始化的5x3张量x=torch.empty(5,3)创建零张量#创建一个5x3的零张量x=torch.zeros(5,3,dtype=torch.long)创建单位张量#创建一个5x5的单位张量(对角线上的元素......