You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

为何NumPy中np.uint8数组转np.float16比转np.float32速度更慢?

uint8 转 float16 耗时是转 float32 两倍的原因说明

ndarray.astype() 执行类型转换时会返回全新的数组,按照常规认知,np.float16 单元素占2字节内存,比占4字节的np.float32 更省空间,np.uint8 数组转np.float16 的速度理应快于转np.float32,但实际测试结果和预期完全相反:转float16的耗时达到转float32的两倍以上。

测试复现

测试用原始数组

import numpy as np
original_array = np.ones([10,512,1280,3], dtype=np.uint8) 

测试结果

  • 转np.float16测试代码:
%%timeit -r 10
float16_array = original_array.astype(np.float16)

耗时:93.5 ms ± 1.68 ms per loop (mean ± std. dev. of 10 runs, 10 loops each)

  • 转np.float32测试代码:
%%timeit -r 10
float32_array = original_array.astype(np.float32)

耗时:41.4 ms ± 278 µs per loop (mean ± std. dev. of 10 runs, 10 loops each)

核心原因

这个现象本质是硬件指令支持差异导致的,和内存占用大小没有直接关系:

  1. 主流桌面级x86 CPU、常规ARM CPU 都没有提供uint8/整数直接转float16的硬件向量指令,甚至早期CPU连原生float16计算指令都不支持。numpy在这类硬件上执行uint8转float16操作时,走的是纯软件实现的转换路径,实际拆成了两步执行:
    • 第一步:调用硬件加速的向量指令,把uint8批量转成CPU原生支持的float32,这一步耗时和直接转float32基本持平
    • 第二步:逐元素对float32值做软件层面的舍入、阶码尾数截断,转换成float16的存储格式写入新数组,这一步额外消耗了和第一步接近的时间
  2. 而uint8转float32的操作,CPU本身提供了对应的SIMD(单指令多数据)加速指令,可以一次性批量完成多个元素的并行转换,不需要额外做格式适配,全程走硬件加速路径,实际耗时只有两步操作的float16转换的一半左右。

补充说明

如果是在原生支持FP16计算加速的硬件上执行同样的转换操作,比如带FP16计算单元的NVIDIA独立显卡、支持ARMv8.2-A FP16扩展指令集的新款移动端/服务器ARM处理器,float16转换的速度才会符合“数据量更小、转换更快”的预期。

内容的提问来源于stack exchange,提问作者Laassairi Abdellah

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.29 01:45:45