PyTorch 稀疏函数解析:embedding 、one_hot详解

52 篇文章 0 订阅
50 篇文章 0 订阅

目录

PyTorch子模块Sparse functions详解

embedding

参数

输出形状

示例

带有 padding_idx 的示例

embedding_bag

参数

输出形状

示例

使用 padding_idx 的示例

one_hot

参数

返回

示例

总结


PyTorch子模块Sparse functions详解

embedding

torch.nn.functional.embedding 是 PyTorch 中的一个函数,用于从固定字典和大小的简单查找表中检索嵌入(embeddings)。这个函数通常用于使用索引检索词嵌入。其输入是一个索引列表和嵌入矩阵,输出是相应的词嵌入。

参数

  • input (LongTensor):包含嵌入矩阵索引的张量。
  • weight (Tensor):嵌入矩阵,行数等于最大可能索引 + 1,列数等于嵌入大小。
  • padding_idx (int, 可选):如果指定,padding_idx 处的条目不会对梯度产生贡献;因此,在训练期间,padding_idx 处的嵌入向量不会更新,即它保持为固定的“填充”。
  • max_norm (float, 可选):如果给定,每个嵌入向量的范数大于 max_norm 时将被重新规范化为 max_norm。注意:这将就地修改 weight。
  • norm_type (float, 可选):用于计算 max_norm 选项的 p-范数的 p。默认为 2。
  • scale_grad_by_freq (bool, 可选):如果给定,将按照小批量中单词频率的倒数来缩放梯度。默认为 False。
  • sparse (bool, 可选):如果为 True,weight 相对于的梯度将是一个稀疏张量。有关稀疏梯度的更多细节,请参阅 torch.nn.Embedding

输出形状

  • 输入:任意形状的 LongTensor,包含要提取的索引。
  • 权重:浮点类型的嵌入矩阵,形状为 (V, embedding_dim),其中 V = 最大索引 + 1,embedding_dim = 嵌入大小。
  • 输出:(*, embedding_dim),其中 * 是输入的形状。

示例

import torch
import torch.nn.functional as F

# 两个样本的批次,每个样本有 4 个索引
input = torch.tensor([[1, 2, 4, 5], [4, 3, 2, 9]])

# 包含 10 个大小为 3 的张量的嵌入矩阵
embedding_matrix = torch.rand(10, 3)

# 使用 F.embedding 获取嵌入
output = F.embedding(input, embedding_matrix)

此例中,input 包含两个样本的索引,embedding_matrix 是一个随机初始化的嵌入矩阵。F.embedding 函数返回了这些索引对应的嵌入向量。

带有 padding_idx 的示例

weights = torch.rand(10, 3)
weights[0, :].zero_()  # 将索引 0 的嵌入向量设置为零
embedding_matrix = weights
input = torch.tensor([[0, 2, 0, 5]])

# 使用 padding_idx
output = F.embedding(input, embedding_matrix, padding_idx=0)

在这个例子中,索引 0 被用作填充索引(padding_idx),因此它的嵌入向量在训练过程中不会更新,且初始化为零。这对于处理可变长度的序列数据特别有用,其中某些位置可能需要被忽略。 

embedding_bag

torch.nn.functional.embedding_bag 是 PyTorch 中的一个函数,它计算嵌入向量的“包”(bag)的和、均值或最大值,而无需实例化中间的嵌入向量。这个函数对于处理文本数据特别有用,特别是在处理变长序列或者需要聚合嵌入表示时。

参数

  • input (LongTensor):包含嵌入矩阵索引的包的张量。
  • weight (Tensor):嵌入矩阵,行数等于最大可能索引 + 1,列数等于嵌入大小。
  • offsets (LongTensor, 可选):仅当输入是1D时使用。offsets确定每个包(序列)在输入中的起始索引位置。
  • max_norm (float, 可选):如果给定,每个嵌入向量的范数大于 max_norm 时将被重新规范化为 max_norm。注意:这将就地修改 weight。
  • norm_type (float, 可选):用于计算 max_norm 选项的 p-范数的 p。默认为 2。
  • scale_grad_by_freq (bool, 可选):如果给定,将按照小批量中单词频率的倒数来缩放梯度。默认为 False。
  • mode (str, 可选):可选 "sum", "mean" 或 "max"。指定聚合包的方式。默认为 "mean"。
  • sparse (bool, 可选):如果为 True,weight 相对于的梯度将是一个稀疏张量。
  • per_sample_weights (Tensor, 可选):浮点/双精度权重的张量,或 None 表示所有权重应视为 1。如果指定,per_sample_weights 的形状必须与 input 完全相同。
  • include_last_offset (bool, 可选):如果为 True,offsets 的大小等于包的数量 + 1。最后一个元素是输入的大小,或最后一个包(序列)的结束索引位置。
  • padding_idx (int, 可选):如果指定,padding_idx 处的条目不会对梯度产生贡献;因此,训练期间不会更新 padding_idx 处的嵌入向量,即它保持为固定的“填充”。

输出形状

  • 输入:LongTensor,和可选的 offsets (LongTensor)

    • 如果输入是二维的,形状为 (B, N),它将被视为 B 个固定长度 N 的包(序列),这将根据 mode 返回 B 个聚合值。在这种情况下,offsets 被忽略并且要求为 None。
    • 如果输入是一维的,形状为 (N),它将被视为多个包(序列)的串联。offsets 是一个一维张量,包含输入中每个包的起始索引位置。因此,对于形状为 (B) 的 offsets,输入将被视为有 B 个包。空包(即长度为0)将返回由零填充的向量。
  • 权重 (Tensor):可学习的模块权重,形状为 (num_embeddings, embedding_dim)。

  • per_sample_weights (Tensor, 可选):具有与输入相同形状的张量。

  • 输出:聚合后的嵌入值,形状为 (B, embedding_dim)。

示例

import torch
import torch.nn.functional as F

# 包含 10 个大小为 3 的张量的嵌入矩阵
embedding_matrix = torch.rand(10, 3)

# 一个样本的批次,包含 4 个索引
input = torch.tensor([1, 2, 4, 5, 4, 3, 2, 9])

# 指定每个包(序列)的开始位置
offsets = torch.tensor([0, 4])

# 使用 F.embedding_bag 获取嵌入
output = F.embedding_bag(input, embedding_matrix, offsets)

在此示例中,input 包含 8 个索引,表示两个序列(或“包”),由 offsets 指定其开始位置。embedding_matrix 是一个随机初始化的嵌入矩阵。F.embedding_bag 函数将返回这些索引对应的嵌入向量的聚合(默认为均值)。

使用 padding_idx 的示例

embedding_matrix = torch.rand(10, 3)
input = torch.tensor([2, 2, 2, 2, 4, 3, 2, 9])
offsets = torch.tensor([0, 4])

# 使用 padding_idx
output = F.embedding_bag(input, embedding_matrix, offsets, padding_idx=2, mode='sum')

在这个例子中,索引 2 被用作填充索引(padding_idx),这意味着在聚合时,索引为 2 的嵌入向量不会对结果产生贡献,并且在训练过程中不会更新这个嵌入向量。这在处理变长序列时特别有用,其中某些位置可能需要被忽略。示例中使用的 mode='sum' 表示对每个包内的嵌入向量进行求和操作。

embedding_bag 函数的这种处理方式比标准的 embedding 函数更高效,因为它避免了创建大量中间嵌入向量的步骤,特别是在处理包含许多短序列的大批量数据时。此外,它允许不同长度的序列共存于同一个批次中,这在处理自然语言处理任务时尤其有价值。

one_hot

torch.nn.functional.one_hot 是 PyTorch 中的一个函数,它用于将长整型张量(LongTensor)转换为一种称为 one-hot 编码的形式。在 one-hot 编码中,每个类别的索引将被转换为一个向量,该向量中除了对应类别索引处的值为 1 外,其余位置均为 0。

参数

  • tensor (LongTensor):任何形状的类别值。
  • num_classes (int):总类别数。如果设置为 -1,则类别数将推断为输入张量中最大类别值加1。

返回

  • 返回一个多了一维的 LongTensor,其中在最后一个维度的索引处,由输入指定的位置为 1,其他位置为 0。

示例

import torch
import torch.nn.functional as F

# 示例 1:基本用法
output = F.one_hot(torch.arange(0, 5) % 3)
print(output)
# tensor([[1, 0, 0],
#         [0, 1, 0],
#         [0, 0, 1],
#         [1, 0, 0],
#         [0, 1, 0]])

# 示例 2:指定 num_classes
output = F.one_hot(torch.arange(0, 5) % 3, num_classes=5)
print(output)
# tensor([[1, 0, 0, 0, 0],
#         [0, 1, 0, 0, 0],
#         [0, 0, 1, 0, 0],
#         [1, 0, 0, 0, 0],
#         [0, 1, 0, 0, 0]])

# 示例 3:使用多维张量
output = F.one_hot(torch.arange(0, 6).view(3, 2) % 3)
print(output)
# tensor([[[1, 0, 0],
#          [0, 1, 0]],
#         [[0, 0, 1],
#          [1, 0, 0]],
#         [[0, 1, 0],
#          [0, 0, 1]]])

在这些示例中,torch.arange(0, 5) % 3 生成一个周期为 3 的序列,然后 F.one_hot 将这些值转换为 one-hot 编码形式。在第二个示例中,通过指定 num_classes=5,可以控制 one-hot 编码向量的长度。在第三个示例中,展示了如何对多维张量进行 one-hot 编码。 

总结

本篇博客探讨了 PyTorch 框架中几个关键的稀疏函数,包括 embeddingembedding_bagone_hot。这些函数在处理自然语言处理(NLP)任务和其他需要高效、灵活处理大量类别或序列数据的应用中至关重要。embedding 函数用于从预定义的嵌入矩阵中检索指定索引的嵌入向量,支持自定义嵌入矩阵大小、填充索引和范数限制。embedding_bag 提供了一种高效的方法来处理变长序列,通过聚合(如求和、均值或最大值)嵌入向量,而无需单独处理每个序列。one_hot 函数则用于将类别标签转换为 one-hot 编码形式,适用于处理分类任务中的标签数据。这些函数的灵活性和高效性使它们成为深度学习模型设计和实现中的重要工具。

  • 17
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
### 回答1: 这个错误提示意味着你尝试使用 PyTorch 中的 `one_hot` 函数时,传入的参数不是索引张量,导致无法执行函数。 `one_hot` 函数的作用是将输入的张量转换为 one-hot 编码的张量。但是,它要求输入的张量必须是整数型的索引张量,不能是浮点型或其他类型的张量。 因此,要解决这个错误,你需要检查传入 `one_hot` 函数的张量是否是整数型的索引张量,如果不是,你需要先将其转换为索引张量,然后再传入 `one_hot` 函数。 ### 回答2: runtimeerror: one_hot is only applicable to index tensor 是一个常见的 Python 编程错误,通常是由于函数 one_hot 被传递了一个非索引张量而导致的。 one_hot 函数是一个 PyTorch 库中提供的函数,它可以将一个整数标签列表转换成一个独热向量。例如,如果数字标签为 4,one_hot 函数将转换该标签为列表 [0, 0, 0, 0, 1, 0, 0, ..., 0],其中 1 代表数字 4 对应的位置。 然而,当传递的张量不是整数索引张量时,one_hot 函数就会出现以上的错误提示信息。 解决这个问题的方法是确保 one_hot 函数的参数张量是索引张量。如果参数张量不是索引张量,则需要将其转换为索引张量。通常,可以使用 PyTorch 库中的函数将张量转换为索引张量。 例如,如果在编写神经网络时需要对标签做 one-hot 处理,应该在标签数据传入网络时,将标签数据先转为整数张量,然后再使用 one_hot 函数进行转换。此外,如果标签是字符串类型,则需将其编码为离散的整数张量。在这样处理后,就可以在运行过程中避免出现 one_hot 函数错误了。 总之,避免 one_hot 函数错误最重要的就是正确的处理输入数据类型和数据格式。弄清楚输入数据应该是什么类型和格式,可以有效提高代码的健壮性和可维护性。 ### 回答3: 该错误提示意为“one_hot函数只适用于索引张量”,出现这个错误的原因是程序在调用one_hot函数时传入了一个非索引张量。在深度学习中,one_hot函数通常用于将分类标签转换为对应的one-hot编码,这样方便进行后续的计算和训练。 索引张量是由整数序列组成的张量,其每个元素都表示一个类别或标签。例如,一个长度为10的索引张量可能代表10个不同类别的样本标签,其中每个元素的取值范围为0-9。 如果我们向one_hot函数传入一个非索引张量,例如一个浮点型张量,由于该函数只能处理整型数据,就会出现“one_hot is only applicable to index tensor”的错误提示。 解决该错误的方法是检查传入one_hot函数的张量是否为索引张量,如果不是则需要先将其转换为索引张量。可以使用torch.argmax()函数获取张量中最大元素的索引,然后将其作为索引张量传入one_hot函数。 总之,出现“one_hot is only applicable to index tensor”的错误,意味着程序中出现了传参错误,需要检查传入的张量是否符合one_hot函数的参数要求。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

E寻数据

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值