TL;DR:16 位浮点数确实存在,并且有各种软件和硬件实现
目前有2种常见的标准16位浮点格式:IEEE-754 二进制16和谷歌的bfloat16。由于它们是标准化的,显然任何了解规范的人都可以编写实现。一些例子:
- https://github.com/ramenhut/half https://github.com/ramenhut/half
- https://github.com/minhhn2910/cuda-half2 https://github.com/minhhn2910/cuda-half2
- https://github.com/tianshilei1992/half_ precision https://github.com/tianshilei1992/half_precision
- https://github.com/acgessler/half_float https://github.com/acgessler/half_float
或者如果你不想使用它们,你也可以设计一个不同的16位浮点格式并实现它
一般不使用 2 字节浮点数,因为即使float 的精度不足以满足正常操作 and double
应始终默认使用,除非您受到带宽或缓存大小的限制。浮点文字也是double
在 C 和类 C 语言中使用时不带后缀。看
- 为什么 double 优于 float? https://stackoverflow.com/q/22818382/995714
- 我应该使用双精度还是浮点? https://stackoverflow.com/q/1074474/995714
- 什么时候用float,什么时候用double https://softwareengineering.stackexchange.com/q/188721/98103
However 小于 32 位的浮点数确实存在 https://en.wikipedia.org/wiki/Minifloat。它们主要用于storage例如在图形中,每像素 96 位(每通道 32 位 * 3 个通道)太浪费了,并且将转换为正常的 32 位浮点数进行计算(某些特殊硬件上除外)。各种各样的10、11、14 位浮点类型 https://www.khronos.org/opengl/wiki/Small_Float_Formats存在于OpenGL中。许多 HDR 格式对每个通道使用 16 位浮点,而 Direct3D 9.0 以及 Radeon R300 和 R420 等一些 GPU 则采用 24 位浮点格式。还支持 24 位浮点数一些 8 位微控制器中的编译器 https://microchipdeveloper.com/c:understanding-floating-point-representations like PIC https://stackoverflow.com/q/26930117/995714其中 32 位浮点支持成本太高。 8 位或更窄的浮点类型用处不大,但由于其简单性,它们经常在计算机科学课程中教授。此外,还使用了一个小浮球ARM的指令编码 http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.dui0489c/CJAEFGHE.html对于小浮点立即数。
The IEEE 754-2008 修订版 https://en.wikipedia.org/wiki/IEEE_754正式添加了 16 位浮点格式,A.K.Abinary16 or 半精度 https://en.wikipedia.org/wiki/Half-precision_floating-point_format,带有 5 位指数和 11 位尾数
一些编译器支持 IEEE-754 二进制 16,但主要用于转换或向量化操作,而不是计算(因为它们不够精确)。例如ARM的工具链有__fp16 http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.dui0491f/CHDCJAEC.html可以在 2 种变体之间进行选择:IEEE 和替代,具体取决于您是否需要更多范围或 NaN/inf 表示。GCC https://gcc.gnu.org/onlinedocs/gcc/Half-Precision.html and Clang https://clang.llvm.org/docs/LanguageExtensions.html#half-precision-floating-point也支持__fp16
以及标准化名称_Float16
. See 如何在 x86_64 的 gcc 上启用 __fp16 类型 https://stackoverflow.com/q/45108628/995714
最近由于人工智能的兴起,另一种格式称为bfloat16 https://en.wikipedia.org/wiki/Bfloat16_floating-point_format (大脑浮点格式 https://en.wikichip.org/wiki/brain_floating-point_format)这是一个简单截断IEEE-754 二进制32 的前 16 位变得常见
减少尾数背后的动机源自谷歌的实验,该实验表明,只要仍然可以将接近于零的微小值表示为训练期间微小差异总和的一部分,就可以减少尾数。较小的尾数带来了许多其他优势,例如减少乘法器功率和物理硅面积。
- float32: 242=576 (100%)
- float16: 112=121 (21%)
- bfloat16: 82=64 (11%)
许多编译器喜欢 and 现在还获得了支持 bfloat16 的能力
有关 bfloat16 的更多信息:
- bfloat16 - 硬件数值定义 https://software.intel.com/en-us/download/bfloat16-hardware-numerics-definition
- 将 bfloat16 与 TensorFlow 模型结合使用 https://cloud.google.com/tpu/docs/bfloat16
- 什么是 tf.bfloat16“截断的 16 位浮点”? https://stackoverflow.com/q/44873802/995714
如果 bfloat16 不够用,还会出现一种新的 19 位类型,称为张量浮点数 https://blogs.nvidia.com/blog/2020/05/14/tensorfloat-32-precision-format/