IndexError:使用列表进行索引时,维度 1 张量的索引过多

kon*_*nin 5 python pytorch

因此,我正在解决一个机器学习问题,在我的一个函数中,我尝试使用torch.tensor张量列表对 a 进行索引,有时索引有效,有时则无效。我知道此错误通常会发生的情况,即当尝试使用 2 个或更多索引对一维数组进行索引时,但当我使用索引列表进行索引时(根据我的理解),不应发生此错误。

因此,下面我将介绍发生在我身上的准确可重现的情况。我有两个由同一代码片段生成的张量列表。

>>> a
[tensor(7, device='cuda:0'), tensor(3, device='cuda:0'), tensor(5, device='cuda:0'), tensor(0, device='cuda:0'), tensor(4, device='cuda:0'), tensor(24, device='cuda:0'), tensor(27, device='cuda:0'), tensor(2, device='cuda:0'), tensor(6, device='cuda:0'), tensor(9, device='cuda:0'), tensor(18, device='cuda:0'), tensor(31, device='cuda:0'), tensor(1, device='cuda:0'), tensor(8, device='cuda:0')]
>>> b
[tensor(20319, device='cuda:0'), tensor(19303, device='cuda:0'), tensor(20181, device='cuda:0'), tensor(17466, device='cuda:0'), tensor(4941, device='cuda:0'), tensor(21132, device='cuda:0'), tensor(17381, device='cuda:0'), tensor(17332, device='cuda:0'), tensor(18432, device='cuda:0'), tensor(18205, device='cuda:0'), tensor(19689, device='cuda:0'), tensor(20743, device='cuda:0'), tensor(18466, device='cuda:0'), tensor(16804, device='cuda:0'), tensor(17521, device='cuda:0'), tensor(21147, device='cuda:0'), tensor(16152, device='cuda:0'), tensor(14863, device='cuda:0'), tensor(15458, device='cuda:0'), tensor(18847, device='cuda:0'), tensor(21549, device='cuda:0'), tensor(21203, device='cuda:0'), tensor(17209, device='cuda:0'), tensor(18552, device='cuda:0'), tensor(16517, device='cuda:0'), tensor(18763, device='cuda:0'), tensor(19538, device='cuda:0'), tensor(12202, device='cuda:0'), tensor(19727, device='cuda:0'), tensor(21218, device='cuda:0'), tensor(8635, device='cuda:0'), tensor(15368, device='cuda:0'), tensor(18322, device='cuda:0'), tensor(17593, device='cuda:0'), tensor(17529, device='cuda:0'), tensor(18036, device='cuda:0'), tensor(12566, device='cuda:0'), tensor(18911, device='cuda:0'), tensor(7387, device='cuda:0'), tensor(16160, device='cuda:0'), tensor(20432, device='cuda:0'), tensor(16536, device='cuda:0'), tensor(14990, device='cuda:0')]
>>> c = torch.ones(100000)
>>> c[a]
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
IndexError: too many indices for tensor of dimension 1
>>> c[b]
tensor([1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1.,
        1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1., 1.,
        1., 1., 1., 1., 1., 1., 1.])
Run Code Online (Sandbox Code Playgroud)

最后我确实通过将 list 转换为 解决了这个问题torch.tensor,但它让我烦恼为什么会发生这种情况。预先感谢所有的答案。

小智 0

我首先重现该错误以及 Jasper 和 Daraan 的建议:

c = torch.arange(0,1000,1)
b = [torch.tensor(i) for i in range(1000)]
print("List lengths for which there is an index error: ", end=" ")
for i in range(10000):
    try:
        c[b[:i]]
    except IndexError:
        print(f"{i}", end=", ")
Run Code Online (Sandbox Code Playgroud)

输出是:

List lengths for which there is an index error: 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31
Run Code Online (Sandbox Code Playgroud)

这证明唯一会产生索引错误的列表长度是在 2 到 31 之间(我使用的是 torch 版本 2.0.1+cu117)。

如果我们将一维张量 c 重塑为形状为 (1000,1) 的矩阵,我们会观察到相同的行为:

c = torch.arange(0,1000,1).reshape(1000,1)
Run Code Online (Sandbox Code Playgroud)

有趣的是,在这两种情况下,将张量列表封装为列表的唯一元素(使用c[[b]]而不是c[b])不会给出错误。这意味着以下代码对于任何测试的索引长度都不会返回任何错误(相对于上面代码的唯一更改是行c[[b[:i]]]):

c = torch.arange(0,1000,1)
b = [torch.tensor(i) for i in range(1000)]
print("List lengths for which there is an index error: ", end=" ")
for i in range(10000):
    try:
        c[[b[:i]]]
    except IndexError:
        print(f"{i}", end=", ")
Run Code Online (Sandbox Code Playgroud)