1 //! A crate that provides support for half-precision 16-bit floating point types.
3 //! This crate provides the [`f16`] type, which is an implementation of the IEEE 754-2008 standard
4 //! [`binary16`] a.k.a `half` floating point type. This 16-bit floating point type is intended for
5 //! efficient storage where the full range and precision of a larger floating point value is not
6 //! required. This is especially useful for image storage formats.
8 //! This crate also provides a [`bf16`] type, an alternative 16-bit floating point format. The
9 //! [`bfloat16`] format is a truncated IEEE 754 standard `binary32` float that preserves the
10 //! exponent to allow the same range as [`f32`] but with only 8 bits of precision (instead of 11
11 //! bits for [`f16`]). See the [`bf16`] type for details.
13 //! Because [`f16`] and [`bf16`] are primarily for efficient storage, floating point operations such
14 //! as addition, multiplication, etc. are not implemented by hardware. While this crate does provide
15 //! the appropriate trait implementations for basic operations, they each convert the value to
16 //! [`f32`] before performing the operation and then back afterward. When performing complex
17 //! arithmetic, manually convert to and from [`f32`] before and after to reduce repeated conversions
18 //! for each operation.
20 //! This crate also provides a [`slice`][mod@slice] module for zero-copy in-place conversions of
21 //! [`u16`] slices to both [`f16`] and [`bf16`], as well as efficient vectorized conversions of
22 //! larger buffers of floating point values to and from these half formats.
24 //! The crate uses `#[no_std]` by default, so can be used in embedded environments without using the
25 //! Rust [`std`] library. A `std` feature to enable support for the standard library is available,
26 //! see the [Cargo Features](#cargo-features) section below.
28 //! A [`prelude`] module is provided for easy importing of available utility traits.
32 //! This crate supports a number of optional cargo features. None of these features are enabled by
33 //! default, even `std`.
35 //! - **`use-intrinsics`** -- Use [`core::arch`] hardware intrinsics for `f16` and `bf16` conversions
36 //! if available on the compiler target. This feature currently only works on nightly Rust
37 //! until the corresponding intrinsics are stabilized.
39 //! When this feature is enabled and the hardware supports it, the functions and traits in the
40 //! [`slice`][mod@slice] module will use vectorized SIMD intructions for increased efficiency.
42 //! By default, without this feature, conversions are done only in software, which will also be
43 //! the fallback if the target does not have hardware support. Note that without the `std`
44 //! feature enabled, no runtime CPU feature detection is used, so the hardware support is only
45 //! compiled if the compiler target supports the CPU feature.
47 //! - **`alloc`** -- Enable use of the [`alloc`] crate when not using the `std` library.
49 //! Among other functions, this enables the [`vec`] module, which contains zero-copy
50 //! conversions for the [`Vec`] type. This allows fast conversion between raw `Vec<u16>` bits and
51 //! `Vec<f16>` or `Vec<bf16>` arrays, and vice versa.
53 //! - **`std`** -- Enable features that depend on the Rust [`std`] library. This also enables the
54 //! `alloc` feature automatically.
56 //! Enabling the `std` feature also enables runtime CPU feature detection when the
57 //! `use-intrsincis` feature is also enabled. Without this feature detection, intrinsics are only
58 //! used when compiler target supports the target feature.
60 //! - **`serde`** -- Adds support for the [`serde`] crate by implementing [`Serialize`] and
61 //! [`Deserialize`] traits for both [`f16`] and [`bf16`].
63 //! - **`num-traits`** -- Adds support for the [`num-traits`] crate by implementing [`ToPrimitive`],
64 //! [`FromPrimitive`], [`AsPrimitive`], [`Num`], [`Float`], [`FloatCore`], and [`Bounded`] traits
65 //! for both [`f16`] and [`bf16`].
67 //! - **`bytemuck`** -- Adds support for the [`bytemuck`] crate by implementing [`Zeroable`] and
68 //! [`Pod`] traits for both [`f16`] and [`bf16`].
70 //! - **`zerocopy`** -- Adds support for the [`zerocopy`] crate by implementing [`AsBytes`] and
71 //! [`FromBytes`] traits for both [`f16`] and [`bf16`].
73 //! [`alloc`]: https://doc.rust-lang.org/alloc/
74 //! [`std`]: https://doc.rust-lang.org/std/
75 //! [`binary16`]: https://en.wikipedia.org/wiki/Half-precision_floating-point_format
76 //! [`bfloat16`]: https://en.wikipedia.org/wiki/Bfloat16_floating-point_format
77 //! [`serde`]: https://crates.io/crates/serde
78 //! [`bytemuck`]: https://crates.io/crates/bytemuck
79 //! [`num-traits`]: https://crates.io/crates/num-traits
80 //! [`zerocopy`]: https://crates.io/crates/zerocopy
87 not(feature = "alloc"),
90 [`Vec`]: https://docs.rust-lang.org/stable/alloc/vec/struct.Vec.html"
95 [`Serialize`]: serde::Serialize
96 [`Deserialize`]: serde::Deserialize"
99 not(feature = "serde"),
101 [`Serialize`]: https://docs.rs/serde/*/serde/trait.Serialize.html
102 [`Deserialize`]: https://docs.rs/serde/*/serde/trait.Deserialize.html"
105 feature = "num-traits",
107 [`ToPrimitive`]: ::num_traits::ToPrimitive
108 [`FromPrimitive`]: ::num_traits::FromPrimitive
109 [`AsPrimitive`]: ::num_traits::AsPrimitive
110 [`Num`]: ::num_traits::Num
111 [`Float`]: ::num_traits::Float
112 [`FloatCore`]: ::num_traits::float::FloatCore
113 [`Bounded`]: ::num_traits::Bounded"
116 not(feature = "num-traits"),
118 [`ToPrimitive`]: https://docs.rs/num-traits/*/num_traits/cast/trait.ToPrimitive.html
119 [`FromPrimitive`]: https://docs.rs/num-traits/*/num_traits/cast/trait.FromPrimitive.html
120 [`AsPrimitive`]: https://docs.rs/num-traits/*/num_traits/cast/trait.AsPrimitive.html
121 [`Num`]: https://docs.rs/num-traits/*/num_traits/trait.Num.html
122 [`Float`]: https://docs.rs/num-traits/*/num_traits/float/trait.Float.html
123 [`FloatCore`]: https://docs.rs/num-traits/*/num_traits/float/trait.FloatCore.html
124 [`Bounded`]: https://docs.rs/num-traits/*/num_traits/bounds/trait.Bounded.html"
127 feature = "bytemuck",
129 [`Zeroable`]: bytemuck::Zeroable
130 [`Pod`]: bytemuck::Pod"
133 not(feature = "bytemuck"),
135 [`Zeroable`]: https://docs.rs/bytemuck/*/bytemuck/trait.Zeroable.html
136 [`Pod`]: https://docs.rs/bytemuck/*bytemuck/trait.Pod.html"
139 feature = "zerocopy",
141 [`AsBytes`]: zerocopy::AsBytes
142 [`FromBytes`]: zerocopy::FromBytes"
145 not(feature = "zerocopy"),
147 [`AsBytes`]: https://docs.rs/zerocopy/*/zerocopy/trait.AsBytes.html
148 [`FromBytes`]: https://docs.rs/zerocopy/*/zerocopy/trait.FromBytes.html"
152 missing_copy_implementations,
153 missing_debug_implementations,
154 trivial_numeric_casts,
157 #![allow(clippy::verbose_bit_mask, clippy::cast_lossless)]
158 #![cfg_attr(not(feature = "std"), no_std)]
161 feature = "use-intrinsics",
162 any(target_arch = "x86", target_arch = "x86_64")
164 feature(stdsimd, f16c_target_feature)
166 #![doc(html_root_url = "https://docs.rs/half/1.8.2")]
167 #![doc(test(attr(deny(warnings), allow(unused))))]
168 #![cfg_attr(docsrs, feature(doc_cfg))]
170 #[cfg(feature = "alloc")]
175 #[cfg(feature = "num-traits")]
179 #[cfg(feature = "alloc")]
180 #[cfg_attr(docsrs, doc(cfg(feature = "alloc")))]
183 pub use bfloat::bf16;
186 pub use binary16::consts;
187 pub use binary16::f16;
189 /// A collection of the most used items and traits in this crate for easy importing.
194 /// use half::prelude::*;
200 slice::{HalfBitsSliceExt, HalfFloatSliceExt},
203 #[cfg(feature = "alloc")]
205 #[cfg_attr(docsrs, doc(cfg(feature = "alloc")))]
206 pub use crate::vec::{HalfBitsVecExt, HalfFloatVecExt};
209 // Keep this module private to crate
211 use crate::{bf16, f16};
213 pub trait SealedHalf {}
215 impl SealedHalf for f16 {}
216 impl SealedHalf for bf16 {}