Document never type fallback in !'s docs
This commit is contained in:
@@ -268,6 +268,47 @@ mod prim_bool {}
|
|||||||
/// [`Debug`]: fmt::Debug
|
/// [`Debug`]: fmt::Debug
|
||||||
/// [`default()`]: Default::default
|
/// [`default()`]: Default::default
|
||||||
///
|
///
|
||||||
|
/// # Never type fallback
|
||||||
|
///
|
||||||
|
/// When the compiler sees a value of type `!` it implicitly inserts a coercion (if possible),
|
||||||
|
/// to allow type check to infer any type:
|
||||||
|
///
|
||||||
|
/// ```rust,ignore (illustrative-and-has-placeholders)
|
||||||
|
/// // this
|
||||||
|
/// let x: u8 = panic!();
|
||||||
|
///
|
||||||
|
/// // is (essentially) turned by the compiler into
|
||||||
|
/// let x: u8 = absurd(panic!());
|
||||||
|
///
|
||||||
|
/// // where absurd is a function with the following signature
|
||||||
|
/// // (it's sound, because `!` always marks unreachable code):
|
||||||
|
/// fn absurd<T>(_: !) -> T { ... }
|
||||||
|
// FIXME: use `core::convert::absurd` here instead, once it's merged
|
||||||
|
/// ```
|
||||||
|
///
|
||||||
|
/// While it's convenient to be able to use non-diverging code in one of the branches (like
|
||||||
|
/// `if a { b } else { return }`) this could lead to compilation errors:
|
||||||
|
///
|
||||||
|
/// ```compile_fail
|
||||||
|
/// // this
|
||||||
|
/// { panic!() };
|
||||||
|
///
|
||||||
|
/// // gets turned into this
|
||||||
|
/// { absurd(panic!()) }; // error: can't infer the type of `absurd`
|
||||||
|
/// ```
|
||||||
|
///
|
||||||
|
/// To prevent such errors, compiler remembers where it inserted `absurd` calls, and if it can't
|
||||||
|
/// infer their type, it sets the type to the fallback type. `{ absurd::<Fallback>(panic!()) };`.
|
||||||
|
/// This is what is known as "never type fallback".
|
||||||
|
///
|
||||||
|
/// Historically fallback was [`()`], causing confusing behavior where `!` spontaneously coerced
|
||||||
|
/// to `()`, even though `()` was never mentioned (because of the fallback). There are plans to
|
||||||
|
/// change it in 2024 edition (and possibly in all editions on a later date), see
|
||||||
|
/// [Tracking Issue for making `!` fall back to `!`][fallback-ti].
|
||||||
|
///
|
||||||
|
/// [`()`]: prim@unit
|
||||||
|
/// [fallback-ti]: https://github.com/rust-lang/rust/issues/123748
|
||||||
|
///
|
||||||
#[unstable(feature = "never_type", issue = "35121")]
|
#[unstable(feature = "never_type", issue = "35121")]
|
||||||
mod prim_never {}
|
mod prim_never {}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user