Meta 设备¶
“元”设备是一种抽象设备,表示一个张量,它记录 只有元数据,但没有实际数据。元张量有两个主要用例:
模型可以在 meta 设备上加载,允许您加载一个 表示模型而不实际加载实际参数 到内存中。如果您需要对 加载实际数据之前的模型。
大多数操作都可以在 meta tensor 上执行,从而产生新的 meta 张量,这些张量描述如果您执行 对真实张量的操作。您可以使用它来执行 abstract 分析,而无需花费时间在计算或空间上来表示 实际的张量。因为元张量没有真实数据,所以你不能 执行依赖于数据的操作,如
或
。在某些情况下,并非所有设备类型(例如 CPU 和 CUDA)具有完全相同的操作输出元数据;我们 通常更喜欢在此 情况。
警告
尽管原则上元张量计算应该始终比 等效的 CPU/CUDA 计算,许多 meta tensor 实现都是 在 Python 中实现,并且为了提高速度而尚未移植到 C++,因此您 可能会发现使用较小的 CPU 张量时,框架的绝对延迟会降低。
使用元张量的惯用语¶
>>> torch.save(torch.randn(2), 'foo.pt')
>>> torch.load('foo.pt', map_location='meta')
tensor(..., device='meta', size=(2,))
如果您有一些任意代码执行一些张量构造,而没有
显式指定设备,你可以通过使用
上下文管理器:
>>> with torch.device('meta'):
... print(torch.randn(30, 30))
...
tensor(..., device='meta', size=(30, 30))
这是特别有用的 NN 模块构建,而您通常不会 能够显式传入设备进行初始化:
>>> from torch.nn.modules import Linear
>>> with torch.device('meta'):
... print(Linear(20, 30))
...
Linear(in_features=20, out_features=30, bias=True)
您不能将元张量直接转换为 CPU/CUDA 张量,因为 Meta Tensor 不存储任何数据,我们不知道正确的数据值是什么 您的新 Tensor 是:
>>> torch.ones(5, device='meta').to("cpu")
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
NotImplementedError: Cannot copy out of meta tensor; no data!
NN 模块有一个方便的方法,
允许您将模块连接到另一个设备,保留所有参数
初始 化。您需要显式地重新初始化参数
手动地:
>>> from torch.nn.modules import Linear
>>> with torch.device('meta'):
... m = Linear(20, 30)
>>> m.to_empty(device="cpu")
Linear(in_features=20, out_features=30, bias=True)
torch._subclasses.meta_utils
包含未记录的实用程序,用于获取
任意 Tensor 并构造一个等效的 meta Tensor
保真度。这些 API 是实验性的,可能会以 BC 中断的方式进行更改
随时。