]> git.proxmox.com Git - rustc.git/blame - library/std/src/primitive_docs.rs
Merge tag 'debian/1.52.1+dfsg1-1_exp2' into proxmox/buster
[rustc.git] / library / std / src / primitive_docs.rs
CommitLineData
c1a9b12d 1#[doc(primitive = "bool")]
83c7162d
XL
2#[doc(alias = "true")]
3#[doc(alias = "false")]
c1a9b12d
SL
4/// The boolean type.
5///
32a655c1
SL
6/// The `bool` represents a value, which could only be either `true` or `false`. If you cast
7/// a `bool` into an integer, `true` will be 1 and `false` will be 0.
7453a54e
SL
8///
9/// # Basic usage
10///
11/// `bool` implements various traits, such as [`BitAnd`], [`BitOr`], [`Not`], etc.,
12/// which allow us to perform boolean operations using `&`, `|` and `!`.
13///
5869c6ff
XL
14/// `if` requires a `bool` value as its conditional. [`assert!`], which is an
15/// important macro in testing, checks whether an expression is `true` and panics
16/// if it isn't.
7453a54e
SL
17///
18/// ```
19/// let bool_val = true & false | false;
20/// assert!(!bool_val);
21/// ```
22///
1b1a35ee
XL
23/// [`BitAnd`]: ops::BitAnd
24/// [`BitOr`]: ops::BitOr
25/// [`Not`]: ops::Not
7453a54e
SL
26///
27/// # Examples
28///
5869c6ff 29/// A trivial example of the usage of `bool`:
7453a54e
SL
30///
31/// ```
32/// let praise_the_borrow_checker = true;
33///
34/// // using the `if` conditional
35/// if praise_the_borrow_checker {
36/// println!("oh, yeah!");
37/// } else {
38/// println!("what?!!");
39/// }
40///
41/// // ... or, a match pattern
42/// match praise_the_borrow_checker {
43/// true => println!("keep praising!"),
44/// false => println!("you should praise!"),
45/// }
46/// ```
47///
1b1a35ee 48/// Also, since `bool` implements the [`Copy`] trait, we don't
7453a54e 49/// have to worry about the move semantics (just like the integer and float primitives).
32a655c1
SL
50///
51/// Now an example of `bool` cast to integer type:
52///
53/// ```
54/// assert_eq!(true as i32, 1);
55/// assert_eq!(false as i32, 0);
56/// ```
57#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 58mod prim_bool {}
c1a9b12d 59
ff7c6d11 60#[doc(primitive = "never")]
83c7162d 61#[doc(alias = "!")]
ff7c6d11
XL
62//
63/// The `!` type, also called "never".
64///
65/// `!` represents the type of computations which never resolve to any value at all. For example,
66/// the [`exit`] function `fn exit(code: i32) -> !` exits the process without ever returning, and
67/// so returns `!`.
68///
69/// `break`, `continue` and `return` expressions also have type `!`. For example we are allowed to
70/// write:
71///
72/// ```
73/// #![feature(never_type)]
74/// # fn foo() -> u32 {
75/// let x: ! = {
76/// return 123
77/// };
78/// # }
79/// ```
80///
81/// Although the `let` is pointless here, it illustrates the meaning of `!`. Since `x` is never
82/// assigned a value (because `return` returns from the entire function), `x` can be given type
83/// `!`. We could also replace `return 123` with a `panic!` or a never-ending `loop` and this code
84/// would still be valid.
85///
86/// A more realistic usage of `!` is in this code:
87///
88/// ```
89/// # fn get_a_number() -> Option<u32> { None }
90/// # loop {
91/// let num: u32 = match get_a_number() {
92/// Some(num) => num,
93/// None => break,
94/// };
95/// # }
96/// ```
97///
98/// Both match arms must produce values of type [`u32`], but since `break` never produces a value
99/// at all we know it can never produce a value which isn't a [`u32`]. This illustrates another
100/// behaviour of the `!` type - expressions with type `!` will coerce into any other type.
101///
1b1a35ee
XL
102/// [`u32`]: prim@u32
103/// [`exit`]: process::exit
ff7c6d11
XL
104///
105/// # `!` and generics
106///
94b46f34
XL
107/// ## Infallible errors
108///
ff7c6d11
XL
109/// The main place you'll see `!` used explicitly is in generic code. Consider the [`FromStr`]
110/// trait:
111///
112/// ```
113/// trait FromStr: Sized {
114/// type Err;
115/// fn from_str(s: &str) -> Result<Self, Self::Err>;
116/// }
117/// ```
118///
119/// When implementing this trait for [`String`] we need to pick a type for [`Err`]. And since
120/// converting a string into a string will never result in an error, the appropriate type is `!`.
121/// (Currently the type actually used is an enum with no variants, though this is only because `!`
dc9dc135 122/// was added to Rust at a later date and it may change in the future.) With an [`Err`] type of
ff7c6d11
XL
123/// `!`, if we have to call [`String::from_str`] for some reason the result will be a
124/// [`Result<String, !>`] which we can unpack like this:
125///
5869c6ff
XL
126/// ```
127/// #![feature(exhaustive_patterns)]
128/// use std::str::FromStr;
ff7c6d11
XL
129/// let Ok(s) = String::from_str("hello");
130/// ```
131///
0531ce1d
XL
132/// Since the [`Err`] variant contains a `!`, it can never occur. If the `exhaustive_patterns`
133/// feature is present this means we can exhaustively match on [`Result<T, !>`] by just taking the
134/// [`Ok`] variant. This illustrates another behaviour of `!` - it can be used to "delete" certain
135/// enum variants from generic types like `Result`.
ff7c6d11 136///
94b46f34
XL
137/// ## Infinite loops
138///
139/// While [`Result<T, !>`] is very useful for removing errors, `!` can also be used to remove
140/// successes as well. If we think of [`Result<T, !>`] as "if this function returns, it has not
141/// errored," we get a very intuitive idea of [`Result<!, E>`] as well: if the function returns, it
142/// *has* errored.
143///
144/// For example, consider the case of a simple web server, which can be simplified to:
145///
146/// ```ignore (hypothetical-example)
147/// loop {
148/// let (client, request) = get_request().expect("disconnected");
149/// let response = request.process();
150/// response.send(client);
151/// }
152/// ```
153///
154/// Currently, this isn't ideal, because we simply panic whenever we fail to get a new connection.
155/// Instead, we'd like to keep track of this error, like this:
156///
157/// ```ignore (hypothetical-example)
158/// loop {
159/// match get_request() {
160/// Err(err) => break err,
161/// Ok((client, request)) => {
162/// let response = request.process();
163/// response.send(client);
164/// },
165/// }
166/// }
167/// ```
168///
169/// Now, when the server disconnects, we exit the loop with an error instead of panicking. While it
170/// might be intuitive to simply return the error, we might want to wrap it in a [`Result<!, E>`]
171/// instead:
172///
173/// ```ignore (hypothetical-example)
174/// fn server_loop() -> Result<!, ConnectionError> {
175/// loop {
176/// let (client, request) = get_request()?;
177/// let response = request.process();
178/// response.send(client);
179/// }
180/// }
181/// ```
182///
183/// Now, we can use `?` instead of `match`, and the return type makes a lot more sense: if the loop
184/// ever stops, it means that an error occurred. We don't even have to wrap the loop in an `Ok`
185/// because `!` coerces to `Result<!, ConnectionError>` automatically.
186///
1b1a35ee 187/// [`String::from_str`]: str::FromStr::from_str
1b1a35ee
XL
188/// [`String`]: string::String
189/// [`FromStr`]: str::FromStr
ff7c6d11
XL
190///
191/// # `!` and traits
192///
193/// When writing your own traits, `!` should have an `impl` whenever there is an obvious `impl`
1b1a35ee
XL
194/// which doesn't `panic!`. The reason is that functions returning an `impl Trait` where `!`
195/// does not have an `impl` of `Trait` cannot diverge as their only possible code path. In other
196/// words, they can't return `!` from every code path. As an example, this code doesn't compile:
197///
198/// ```compile_fail
fc512014 199/// use std::ops::Add;
1b1a35ee
XL
200///
201/// fn foo() -> impl Add<u32> {
202/// unimplemented!()
203/// }
204/// ```
205///
206/// But this code does:
207///
208/// ```
fc512014 209/// use std::ops::Add;
1b1a35ee
XL
210///
211/// fn foo() -> impl Add<u32> {
212/// if true {
213/// unimplemented!()
214/// } else {
215/// 0
216/// }
217/// }
218/// ```
219///
220/// The reason is that, in the first example, there are many possible types that `!` could coerce
221/// to, because many types implement `Add<u32>`. However, in the second example,
222/// the `else` branch returns a `0`, which the compiler infers from the return type to be of type
223/// `u32`. Since `u32` is a concrete type, `!` can and will be coerced to it. See issue [#36375]
224/// for more information on this quirk of `!`.
225///
226/// [#36375]: https://github.com/rust-lang/rust/issues/36375
227///
228/// As it turns out, though, most traits can have an `impl` for `!`. Take [`Debug`]
ff7c6d11
XL
229/// for example:
230///
231/// ```
0531ce1d 232/// #![feature(never_type)]
ff7c6d11
XL
233/// # use std::fmt;
234/// # trait Debug {
1b1a35ee 235/// # fn fmt(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result;
ff7c6d11
XL
236/// # }
237/// impl Debug for ! {
532ac7d7 238/// fn fmt(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result {
ff7c6d11
XL
239/// *self
240/// }
241/// }
242/// ```
243///
244/// Once again we're using `!`'s ability to coerce into any other type, in this case
245/// [`fmt::Result`]. Since this method takes a `&!` as an argument we know that it can never be
246/// called (because there is no value of type `!` for it to be called with). Writing `*self`
247/// essentially tells the compiler "We know that this code can never be run, so just treat the
0bf4aa26 248/// entire function body as having type [`fmt::Result`]". This pattern can be used a lot when
ff7c6d11 249/// implementing traits for `!`. Generally, any trait which only has methods which take a `self`
0bf4aa26 250/// parameter should have such an impl.
ff7c6d11
XL
251///
252/// On the other hand, one trait which would not be appropriate to implement is [`Default`]:
253///
254/// ```
255/// trait Default {
256/// fn default() -> Self;
257/// }
258/// ```
259///
260/// Since `!` has no values, it has no default value either. It's true that we could write an
261/// `impl` for this which simply panics, but the same is true for any type (we could `impl
262/// Default` for (eg.) [`File`] by just making [`default()`] panic.)
263///
1b1a35ee
XL
264/// [`File`]: fs::File
265/// [`Debug`]: fmt::Debug
266/// [`default()`]: Default::default
ff7c6d11 267///
b7449926 268#[unstable(feature = "never_type", issue = "35121")]
dfeec247 269mod prim_never {}
ff7c6d11 270
c1a9b12d
SL
271#[doc(primitive = "char")]
272//
92a42be0 273/// A character type.
c1a9b12d 274///
92a42be0
SL
275/// The `char` type represents a single character. More specifically, since
276/// 'character' isn't a well-defined concept in Unicode, `char` is a '[Unicode
277/// scalar value]', which is similar to, but not the same as, a '[Unicode code
278/// point]'.
c1a9b12d 279///
92a42be0
SL
280/// [Unicode scalar value]: http://www.unicode.org/glossary/#unicode_scalar_value
281/// [Unicode code point]: http://www.unicode.org/glossary/#code_point
c1a9b12d 282///
92a42be0
SL
283/// This documentation describes a number of methods and trait implementations on the
284/// `char` type. For technical reasons, there is additional, separate
285/// documentation in [the `std::char` module](char/index.html) as well.
c1a9b12d 286///
92a42be0
SL
287/// # Representation
288///
289/// `char` is always four bytes in size. This is a different representation than
54a0048b 290/// a given character would have as part of a [`String`]. For example:
92a42be0
SL
291///
292/// ```
293/// let v = vec!['h', 'e', 'l', 'l', 'o'];
294///
295/// // five elements times four bytes for each element
296/// assert_eq!(20, v.len() * std::mem::size_of::<char>());
297///
298/// let s = String::from("hello");
299///
300/// // five elements times one byte per element
301/// assert_eq!(5, s.len() * std::mem::size_of::<u8>());
302/// ```
303///
304/// [`String`]: string/struct.String.html
305///
306/// As always, remember that a human intuition for 'character' may not map to
3b2f2976 307/// Unicode's definitions. For example, despite looking similar, the 'é'
48663c56 308/// character is one Unicode code point while 'é' is two Unicode code points:
92a42be0
SL
309///
310/// ```
3b2f2976
XL
311/// let mut chars = "é".chars();
312/// // U+00e9: 'latin small letter e with acute'
313/// assert_eq!(Some('\u{00e9}'), chars.next());
314/// assert_eq!(None, chars.next());
92a42be0 315///
3b2f2976
XL
316/// let mut chars = "é".chars();
317/// // U+0065: 'latin small letter e'
318/// assert_eq!(Some('\u{0065}'), chars.next());
319/// // U+0301: 'combining acute accent'
320/// assert_eq!(Some('\u{0301}'), chars.next());
321/// assert_eq!(None, chars.next());
92a42be0
SL
322/// ```
323///
3b2f2976
XL
324/// This means that the contents of the first string above _will_ fit into a
325/// `char` while the contents of the second string _will not_. Trying to create
326/// a `char` literal with the contents of the second string gives an error:
92a42be0
SL
327///
328/// ```text
3b2f2976
XL
329/// error: character literal may only contain one codepoint: 'é'
330/// let c = 'é';
0731742a 331/// ^^^
92a42be0
SL
332/// ```
333///
54a0048b
SL
334/// Another implication of the 4-byte fixed size of a `char` is that
335/// per-`char` processing can end up using a lot more memory:
92a42be0
SL
336///
337/// ```
338/// let s = String::from("love: ❤️");
339/// let v: Vec<char> = s.chars().collect();
340///
0bf4aa26
XL
341/// assert_eq!(12, std::mem::size_of_val(&s[..]));
342/// assert_eq!(32, std::mem::size_of_val(&v[..]));
92a42be0 343/// ```
32a655c1 344#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 345mod prim_char {}
c1a9b12d
SL
346
347#[doc(primitive = "unit")]
348//
ba9703b0 349/// The `()` type, also called "unit".
c1a9b12d
SL
350///
351/// The `()` type has exactly one value `()`, and is used when there
352/// is no other meaningful value that could be returned. `()` is most
353/// commonly seen implicitly: functions without a `-> ...` implicitly
354/// have return type `()`, that is, these are equivalent:
355///
356/// ```rust
357/// fn long() -> () {}
358///
359/// fn short() {}
360/// ```
361///
362/// The semicolon `;` can be used to discard the result of an
363/// expression at the end of a block, making the expression (and thus
364/// the block) evaluate to `()`. For example,
365///
366/// ```rust
367/// fn returns_i64() -> i64 {
368/// 1i64
369/// }
370/// fn returns_unit() {
371/// 1i64;
372/// }
373///
374/// let is_i64 = {
375/// returns_i64()
376/// };
377/// let is_unit = {
378/// returns_i64();
379/// };
380/// ```
381///
32a655c1 382#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 383mod prim_unit {}
c1a9b12d 384
1b1a35ee 385#[doc(alias = "ptr")]
c1a9b12d
SL
386#[doc(primitive = "pointer")]
387//
388/// Raw, unsafe pointers, `*const T`, and `*mut T`.
389///
29967ef6 390/// *[See also the `std::ptr` module](ptr).*
94b46f34 391///
416331ca
XL
392/// Working with raw pointers in Rust is uncommon, typically limited to a few patterns.
393/// Raw pointers can be unaligned or [`null`]. However, when a raw pointer is
394/// dereferenced (using the `*` operator), it must be non-null and aligned.
395///
396/// Storing through a raw pointer using `*ptr = data` calls `drop` on the old value, so
397/// [`write`] must be used if the type has drop glue and memory is not already
398/// initialized - otherwise `drop` would be called on the uninitialized memory.
c1a9b12d 399///
3b2f2976
XL
400/// Use the [`null`] and [`null_mut`] functions to create null pointers, and the
401/// [`is_null`] method of the `*const T` and `*mut T` types to check for null.
402/// The `*const T` and `*mut T` types also define the [`offset`] method, for
403/// pointer math.
c1a9b12d
SL
404///
405/// # Common ways to create raw pointers
406///
407/// ## 1. Coerce a reference (`&T`) or mutable reference (`&mut T`).
408///
409/// ```
410/// let my_num: i32 = 10;
411/// let my_num_ptr: *const i32 = &my_num;
412/// let mut my_speed: i32 = 88;
413/// let my_speed_ptr: *mut i32 = &mut my_speed;
414/// ```
415///
416/// To get a pointer to a boxed value, dereference the box:
417///
418/// ```
419/// let my_num: Box<i32> = Box::new(10);
420/// let my_num_ptr: *const i32 = &*my_num;
421/// let mut my_speed: Box<i32> = Box::new(88);
422/// let my_speed_ptr: *mut i32 = &mut *my_speed;
423/// ```
424///
425/// This does not take ownership of the original allocation
426/// and requires no resource management later,
427/// but you must not use the pointer after its lifetime.
428///
429/// ## 2. Consume a box (`Box<T>`).
430///
cc61c64b 431/// The [`into_raw`] function consumes a box and returns
c1a9b12d
SL
432/// the raw pointer. It doesn't destroy `T` or deallocate any memory.
433///
434/// ```
c1a9b12d
SL
435/// let my_speed: Box<i32> = Box::new(88);
436/// let my_speed: *mut i32 = Box::into_raw(my_speed);
437///
438/// // By taking ownership of the original `Box<T>` though
439/// // we are obligated to put it together later to be destroyed.
440/// unsafe {
441/// drop(Box::from_raw(my_speed));
442/// }
443/// ```
444///
cc61c64b 445/// Note that here the call to [`drop`] is for clarity - it indicates
c1a9b12d
SL
446/// that we are done with the given value and it should be destroyed.
447///
448/// ## 3. Get it from C.
449///
450/// ```
0731742a 451/// # #![feature(rustc_private)]
c1a9b12d
SL
452/// extern crate libc;
453///
454/// use std::mem;
455///
e74abb32
XL
456/// unsafe {
457/// let my_num: *mut i32 = libc::malloc(mem::size_of::<i32>()) as *mut i32;
458/// if my_num.is_null() {
459/// panic!("failed to allocate memory");
c1a9b12d 460/// }
e74abb32 461/// libc::free(my_num as *mut libc::c_void);
c1a9b12d
SL
462/// }
463/// ```
464///
465/// Usually you wouldn't literally use `malloc` and `free` from Rust,
466/// but C APIs hand out a lot of pointers generally, so are a common source
467/// of raw pointers in Rust.
468///
1b1a35ee
XL
469/// [`null`]: ptr::null
470/// [`null_mut`]: ptr::null_mut
6a06907d
XL
471/// [`is_null`]: pointer::is_null
472/// [`offset`]: pointer::offset
1b1a35ee
XL
473/// [`into_raw`]: Box::into_raw
474/// [`drop`]: mem::drop
475/// [`write`]: ptr::write
32a655c1 476#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 477mod prim_pointer {}
c1a9b12d 478
fc512014
XL
479#[doc(alias = "[]")]
480#[doc(alias = "[T;N]")] // unfortunately, rustdoc doesn't have fuzzy search for aliases
481#[doc(alias = "[T; N]")]
c1a9b12d 482#[doc(primitive = "array")]
92a42be0 483/// A fixed-size array, denoted `[T; N]`, for the element type, `T`, and the
9e0c209e 484/// non-negative compile-time constant size, `N`.
c1a9b12d 485///
9e0c209e 486/// There are two syntactic forms for creating an array:
c1a9b12d 487///
0731742a 488/// * A list with each element, i.e., `[x, y, z]`.
9e0c209e 489/// * A repeat expression `[x; N]`, which produces an array with `N` copies of `x`.
1b1a35ee 490/// The type of `x` must be [`Copy`].
c1a9b12d 491///
fc512014
XL
492/// Note that `[expr; 0]` is allowed, and produces an empty array.
493/// This will still evaluate `expr`, however, and immediately drop the resulting value, so
494/// be mindful of side effects.
495///
3dfed10e 496/// Arrays of *any* size implement the following traits if the element type allows it:
c1a9b12d 497///
29967ef6
XL
498/// - [`Copy`]
499/// - [`Clone`]
1b1a35ee
XL
500/// - [`Debug`]
501/// - [`IntoIterator`] (implemented for `&[T; N]` and `&mut [T; N]`)
502/// - [`PartialEq`], [`PartialOrd`], [`Eq`], [`Ord`]
503/// - [`Hash`]
504/// - [`AsRef`], [`AsMut`]
505/// - [`Borrow`], [`BorrowMut`]
c1a9b12d 506///
29967ef6 507/// Arrays of sizes from 0 to 32 (inclusive) implement the [`Default`] trait
3dfed10e 508/// if the element type allows it. As a stopgap, trait implementations are
9e0c209e 509/// statically generated up to size 32.
c1a9b12d 510///
9e0c209e
SL
511/// Arrays coerce to [slices (`[T]`)][slice], so a slice method may be called on
512/// an array. Indeed, this provides most of the API for working with arrays.
513/// Slices have a dynamic size and do not coerce to arrays.
c1a9b12d 514///
1b1a35ee
XL
515/// You can move elements out of an array with a [slice pattern]. If you want
516/// one element, see [`mem::replace`].
9e0c209e 517///
c1a9b12d
SL
518/// # Examples
519///
520/// ```
521/// let mut array: [i32; 3] = [0; 3];
522///
523/// array[1] = 1;
524/// array[2] = 2;
525///
526/// assert_eq!([1, 2], &array[1..]);
527///
528/// // This loop prints: 0 1 2
529/// for x in &array {
530/// print!("{} ", x);
531/// }
9e0c209e
SL
532/// ```
533///
534/// An array itself is not iterable:
535///
041b39d2 536/// ```compile_fail,E0277
9e0c209e
SL
537/// let array: [i32; 3] = [0; 3];
538///
539/// for x in array { }
540/// // error: the trait bound `[i32; 3]: std::iter::Iterator` is not satisfied
541/// ```
542///
543/// The solution is to coerce the array to a slice by calling a slice method:
544///
545/// ```
546/// # let array: [i32; 3] = [0; 3];
547/// for x in array.iter() { }
548/// ```
549///
3dfed10e 550/// You can also use the array reference's [`IntoIterator`] implementation:
c1a9b12d
SL
551///
552/// ```
9e0c209e
SL
553/// # let array: [i32; 3] = [0; 3];
554/// for x in &array { }
555/// ```
c1a9b12d 556///
1b1a35ee 557/// You can use a [slice pattern] to move elements out of an array:
dc9dc135
XL
558///
559/// ```
560/// fn move_away(_: String) { /* Do interesting things. */ }
561///
562/// let [john, roa] = ["John".to_string(), "Roa".to_string()];
563/// move_away(john);
564/// move_away(roa);
565/// ```
566///
6a06907d 567/// [slice]: prim@slice
1b1a35ee
XL
568/// [`Debug`]: fmt::Debug
569/// [`Hash`]: hash::Hash
570/// [`Borrow`]: borrow::Borrow
571/// [`BorrowMut`]: borrow::BorrowMut
572/// [slice pattern]: ../reference/patterns.html#slice-patterns
32a655c1 573#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 574mod prim_array {}
c1a9b12d
SL
575
576#[doc(primitive = "slice")]
83c7162d
XL
577#[doc(alias = "[")]
578#[doc(alias = "]")]
579#[doc(alias = "[]")]
e74abb32
XL
580/// A dynamically-sized view into a contiguous sequence, `[T]`. Contiguous here
581/// means that elements are laid out so that every element is the same
582/// distance from its neighbors.
c1a9b12d 583///
29967ef6 584/// *[See also the `std::slice` module](crate::slice).*
94b46f34 585///
c1a9b12d
SL
586/// Slices are a view into a block of memory represented as a pointer and a
587/// length.
588///
589/// ```
590/// // slicing a Vec
591/// let vec = vec![1, 2, 3];
592/// let int_slice = &vec[..];
593/// // coercing an array to a slice
594/// let str_slice: &[&str] = &["one", "two", "three"];
595/// ```
596///
597/// Slices are either mutable or shared. The shared slice type is `&[T]`,
598/// while the mutable slice type is `&mut [T]`, where `T` represents the element
599/// type. For example, you can mutate the block of memory that a mutable slice
600/// points to:
601///
602/// ```
0731742a
XL
603/// let mut x = [1, 2, 3];
604/// let x = &mut x[..]; // Take a full slice of `x`.
c1a9b12d
SL
605/// x[1] = 7;
606/// assert_eq!(x, &[1, 7, 3]);
607/// ```
3dfed10e
XL
608///
609/// As slices store the length of the sequence they refer to, they have twice
610/// the size of pointers to [`Sized`](marker/trait.Sized.html) types.
611/// Also see the reference on
612/// [dynamically sized types](../reference/dynamically-sized-types.html).
613///
614/// ```
615/// # use std::rc::Rc;
616/// let pointer_size = std::mem::size_of::<&u8>();
617/// assert_eq!(2 * pointer_size, std::mem::size_of::<&[u8]>());
618/// assert_eq!(2 * pointer_size, std::mem::size_of::<*const [u8]>());
619/// assert_eq!(2 * pointer_size, std::mem::size_of::<Box<[u8]>>());
620/// assert_eq!(2 * pointer_size, std::mem::size_of::<Rc<[u8]>>());
621/// ```
32a655c1 622#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 623mod prim_slice {}
c1a9b12d
SL
624
625#[doc(primitive = "str")]
626//
92a42be0
SL
627/// String slices.
628///
29967ef6 629/// *[See also the `std::str` module](crate::str).*
94b46f34 630///
92a42be0
SL
631/// The `str` type, also called a 'string slice', is the most primitive string
632/// type. It is usually seen in its borrowed form, `&str`. It is also the type
633/// of string literals, `&'static str`.
634///
94b46f34 635/// String slices are always valid UTF-8.
c1a9b12d
SL
636///
637/// # Examples
638///
92a42be0 639/// String literals are string slices:
c1a9b12d
SL
640///
641/// ```
92a42be0
SL
642/// let hello = "Hello, world!";
643///
644/// // with an explicit type annotation
645/// let hello: &'static str = "Hello, world!";
c1a9b12d
SL
646/// ```
647///
92a42be0
SL
648/// They are `'static` because they're stored directly in the final binary, and
649/// so will be valid for the `'static` duration.
c1a9b12d 650///
92a42be0
SL
651/// # Representation
652///
653/// A `&str` is made up of two components: a pointer to some bytes, and a
cc61c64b 654/// length. You can look at these with the [`as_ptr`] and [`len`] methods:
c1a9b12d
SL
655///
656/// ```
92a42be0
SL
657/// use std::slice;
658/// use std::str;
c1a9b12d 659///
92a42be0 660/// let story = "Once upon a time...";
c1a9b12d 661///
92a42be0
SL
662/// let ptr = story.as_ptr();
663/// let len = story.len();
c1a9b12d 664///
9cc50fc6 665/// // story has nineteen bytes
92a42be0 666/// assert_eq!(19, len);
c1a9b12d 667///
54a0048b 668/// // We can re-build a str out of ptr and len. This is all unsafe because
92a42be0
SL
669/// // we are responsible for making sure the two components are valid:
670/// let s = unsafe {
671/// // First, we build a &[u8]...
672/// let slice = slice::from_raw_parts(ptr, len);
673///
674/// // ... and then convert that slice into a string slice
675/// str::from_utf8(slice)
676/// };
677///
678/// assert_eq!(s, Ok(story));
679/// ```
c1a9b12d 680///
1b1a35ee
XL
681/// [`as_ptr`]: str::as_ptr
682/// [`len`]: str::len
9e0c209e
SL
683///
684/// Note: This example shows the internals of `&str`. `unsafe` should not be
e1599b0c 685/// used to get a string slice under normal circumstances. Use `as_str`
9e0c209e 686/// instead.
32a655c1 687#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 688mod prim_str {}
c1a9b12d
SL
689
690#[doc(primitive = "tuple")]
83c7162d
XL
691#[doc(alias = "(")]
692#[doc(alias = ")")]
693#[doc(alias = "()")]
c1a9b12d
SL
694//
695/// A finite heterogeneous sequence, `(T, U, ..)`.
696///
7453a54e
SL
697/// Let's cover each of those in turn:
698///
699/// Tuples are *finite*. In other words, a tuple has a length. Here's a tuple
700/// of length `3`:
701///
702/// ```
703/// ("hello", 5, 'c');
704/// ```
705///
706/// 'Length' is also sometimes called 'arity' here; each tuple of a different
707/// length is a different, distinct type.
708///
709/// Tuples are *heterogeneous*. This means that each element of the tuple can
710/// have a different type. In that tuple above, it has the type:
711///
041b39d2
XL
712/// ```
713/// # let _:
7453a54e 714/// (&'static str, i32, char)
041b39d2 715/// # = ("hello", 5, 'c');
7453a54e
SL
716/// ```
717///
718/// Tuples are a *sequence*. This means that they can be accessed by position;
719/// this is called 'tuple indexing', and it looks like this:
720///
721/// ```rust
722/// let tuple = ("hello", 5, 'c');
723///
724/// assert_eq!(tuple.0, "hello");
725/// assert_eq!(tuple.1, 5);
726/// assert_eq!(tuple.2, 'c');
727/// ```
728///
dc9dc135
XL
729/// The sequential nature of the tuple applies to its implementations of various
730/// traits. For example, in `PartialOrd` and `Ord`, the elements are compared
731/// sequentially until the first non-equal set is found.
732///
13cf67c4 733/// For more about tuples, see [the book](../book/ch03-02-data-types.html#the-tuple-type).
c1a9b12d 734///
7453a54e 735/// # Trait implementations
c1a9b12d 736///
54a0048b
SL
737/// If every type inside a tuple implements one of the following traits, then a
738/// tuple itself also implements it.
c1a9b12d 739///
7453a54e 740/// * [`Clone`]
54a0048b 741/// * [`Copy`]
7453a54e
SL
742/// * [`PartialEq`]
743/// * [`Eq`]
744/// * [`PartialOrd`]
745/// * [`Ord`]
746/// * [`Debug`]
747/// * [`Default`]
748/// * [`Hash`]
749///
1b1a35ee
XL
750/// [`Debug`]: fmt::Debug
751/// [`Hash`]: hash::Hash
7453a54e
SL
752///
753/// Due to a temporary restriction in Rust's type system, these traits are only
32a655c1 754/// implemented on tuples of arity 12 or less. In the future, this may change.
c1a9b12d
SL
755///
756/// # Examples
757///
7453a54e 758/// Basic usage:
c1a9b12d
SL
759///
760/// ```
7453a54e 761/// let tuple = ("hello", 5, 'c');
c1a9b12d 762///
7453a54e 763/// assert_eq!(tuple.0, "hello");
c1a9b12d
SL
764/// ```
765///
7453a54e
SL
766/// Tuples are often used as a return type when you want to return more than
767/// one value:
c1a9b12d
SL
768///
769/// ```
7453a54e
SL
770/// fn calculate_point() -> (i32, i32) {
771/// // Don't do a calculation, that's not the point of the example
772/// (4, 5)
773/// }
774///
775/// let point = calculate_point();
776///
777/// assert_eq!(point.0, 4);
778/// assert_eq!(point.1, 5);
779///
780/// // Combining this with patterns can be nicer.
c1a9b12d 781///
7453a54e 782/// let (x, y) = calculate_point();
c1a9b12d 783///
7453a54e
SL
784/// assert_eq!(x, 4);
785/// assert_eq!(y, 5);
c1a9b12d
SL
786/// ```
787///
32a655c1 788#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 789mod prim_tuple {}
c1a9b12d
SL
790
791#[doc(primitive = "f32")]
3dfed10e
XL
792/// A 32-bit floating point type (specifically, the "binary32" type defined in IEEE 754-2008).
793///
794/// This type can represent a wide range of decimal numbers, like `3.5`, `27`,
795/// `-113.75`, `0.0078125`, `34359738368`, `0`, `-1`. So unlike integer types
796/// (such as `i32`), floating point types can represent non-integer numbers,
797/// too.
798///
799/// However, being able to represent this wide range of numbers comes at the
800/// cost of precision: floats can only represent some of the real numbers and
801/// calculation with floats round to a nearby representable number. For example,
802/// `5.0` and `1.0` can be exactly represented as `f32`, but `1.0 / 5.0` results
803/// in `0.20000000298023223876953125` since `0.2` cannot be exactly represented
29967ef6 804/// as `f32`. Note, however, that printing floats with `println` and friends will
3dfed10e
XL
805/// often discard insignificant digits: `println!("{}", 1.0f32 / 5.0f32)` will
806/// print `0.2`.
807///
808/// Additionally, `f32` can represent a couple of special values:
809///
810/// - `-0`: this is just due to how floats are encoded. It is semantically
811/// equivalent to `0` and `-0.0 == 0.0` results in `true`.
812/// - [∞](#associatedconstant.INFINITY) and
813/// [−∞](#associatedconstant.NEG_INFINITY): these result from calculations
814/// like `1.0 / 0.0`.
815/// - [NaN (not a number)](#associatedconstant.NAN): this value results from
816/// calculations like `(-1.0).sqrt()`. NaN has some potentially unexpected
817/// behavior: it is unequal to any float, including itself! It is also neither
818/// smaller nor greater than any float, making it impossible to sort. Lastly,
819/// it is considered infectious as almost all calculations where one of the
820/// operands is NaN will also result in NaN.
821///
822/// For more information on floating point numbers, see [Wikipedia][wikipedia].
c1a9b12d 823///
29967ef6 824/// *[See also the `std::f32::consts` module](crate::f32::consts).*
c1a9b12d 825///
3dfed10e 826/// [wikipedia]: https://en.wikipedia.org/wiki/Single-precision_floating-point_format
32a655c1 827#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 828mod prim_f32 {}
c1a9b12d
SL
829
830#[doc(primitive = "f64")]
3dfed10e
XL
831/// A 64-bit floating point type (specifically, the "binary64" type defined in IEEE 754-2008).
832///
1b1a35ee 833/// This type is very similar to [`f32`], but has increased
3dfed10e 834/// precision by using twice as many bits. Please see [the documentation for
1b1a35ee 835/// `f32`][`f32`] or [Wikipedia on double precision
3dfed10e 836/// values][wikipedia] for more information.
c1a9b12d 837///
29967ef6 838/// *[See also the `std::f64::consts` module](crate::f64::consts).*
c1a9b12d 839///
1b1a35ee 840/// [`f32`]: prim@f32
3dfed10e 841/// [wikipedia]: https://en.wikipedia.org/wiki/Double-precision_floating-point_format
32a655c1 842#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 843mod prim_f64 {}
c1a9b12d
SL
844
845#[doc(primitive = "i8")]
846//
847/// The 8-bit signed integer type.
32a655c1 848#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 849mod prim_i8 {}
c1a9b12d
SL
850
851#[doc(primitive = "i16")]
852//
853/// The 16-bit signed integer type.
32a655c1 854#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 855mod prim_i16 {}
c1a9b12d
SL
856
857#[doc(primitive = "i32")]
858//
859/// The 32-bit signed integer type.
32a655c1 860#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 861mod prim_i32 {}
c1a9b12d
SL
862
863#[doc(primitive = "i64")]
864//
865/// The 64-bit signed integer type.
32a655c1 866#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 867mod prim_i64 {}
c1a9b12d 868
32a655c1
SL
869#[doc(primitive = "i128")]
870//
871/// The 128-bit signed integer type.
dfeec247
XL
872#[stable(feature = "i128", since = "1.26.0")]
873mod prim_i128 {}
32a655c1 874
c1a9b12d
SL
875#[doc(primitive = "u8")]
876//
877/// The 8-bit unsigned integer type.
32a655c1 878#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 879mod prim_u8 {}
c1a9b12d
SL
880
881#[doc(primitive = "u16")]
882//
883/// The 16-bit unsigned integer type.
32a655c1 884#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 885mod prim_u16 {}
c1a9b12d
SL
886
887#[doc(primitive = "u32")]
888//
889/// The 32-bit unsigned integer type.
32a655c1 890#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 891mod prim_u32 {}
c1a9b12d
SL
892
893#[doc(primitive = "u64")]
894//
895/// The 64-bit unsigned integer type.
32a655c1 896#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 897mod prim_u64 {}
c1a9b12d 898
32a655c1
SL
899#[doc(primitive = "u128")]
900//
901/// The 128-bit unsigned integer type.
dfeec247
XL
902#[stable(feature = "i128", since = "1.26.0")]
903mod prim_u128 {}
32a655c1 904
c1a9b12d
SL
905#[doc(primitive = "isize")]
906//
907/// The pointer-sized signed integer type.
908///
ea8adc8c
XL
909/// The size of this primitive is how many bytes it takes to reference any
910/// location in memory. For example, on a 32 bit target, this is 4 bytes
911/// and on a 64 bit target, this is 8 bytes.
32a655c1 912#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 913mod prim_isize {}
c1a9b12d
SL
914
915#[doc(primitive = "usize")]
916//
b039eaaf 917/// The pointer-sized unsigned integer type.
c1a9b12d 918///
ea8adc8c
XL
919/// The size of this primitive is how many bytes it takes to reference any
920/// location in memory. For example, on a 32 bit target, this is 4 bytes
921/// and on a 64 bit target, this is 8 bytes.
32a655c1 922#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 923mod prim_usize {}
3b2f2976
XL
924
925#[doc(primitive = "reference")]
83c7162d 926#[doc(alias = "&")]
fc512014 927#[doc(alias = "&mut")]
3b2f2976
XL
928//
929/// References, both shared and mutable.
930///
931/// A reference represents a borrow of some owned value. You can get one by using the `&` or `&mut`
932/// operators on a value, or by using a `ref` or `ref mut` pattern.
933///
416331ca
XL
934/// For those familiar with pointers, a reference is just a pointer that is assumed to be
935/// aligned, not null, and pointing to memory containing a valid value of `T` - for example,
936/// `&bool` can only point to an allocation containing the integer values `1` (`true`) or `0`
937/// (`false`), but creating a `&bool` that points to an allocation containing
938/// the value `3` causes undefined behaviour.
939/// In fact, `Option<&T>` has the same memory representation as a
940/// nullable but aligned pointer, and can be passed across FFI boundaries as such.
3b2f2976
XL
941///
942/// In most cases, references can be used much like the original value. Field access, method
943/// calling, and indexing work the same (save for mutability rules, of course). In addition, the
944/// comparison operators transparently defer to the referent's implementation, allowing references
945/// to be compared the same as owned values.
946///
947/// References have a lifetime attached to them, which represents the scope for which the borrow is
948/// valid. A lifetime is said to "outlive" another one if its representative scope is as long or
949/// longer than the other. The `'static` lifetime is the longest lifetime, which represents the
950/// total life of the program. For example, string literals have a `'static` lifetime because the
951/// text data is embedded into the binary of the program, rather than in an allocation that needs
952/// to be dynamically managed.
953///
954/// `&mut T` references can be freely coerced into `&T` references with the same referent type, and
955/// references with longer lifetimes can be freely coerced into references with shorter ones.
956///
0bf4aa26
XL
957/// Reference equality by address, instead of comparing the values pointed to, is accomplished via
958/// implicit reference-pointer coercion and raw pointer equality via [`ptr::eq`], while
959/// [`PartialEq`] compares values.
960///
0bf4aa26
XL
961/// ```
962/// use std::ptr;
963///
964/// let five = 5;
965/// let other_five = 5;
966/// let five_ref = &five;
967/// let same_five_ref = &five;
968/// let other_five_ref = &other_five;
969///
970/// assert!(five_ref == same_five_ref);
971/// assert!(five_ref == other_five_ref);
972///
973/// assert!(ptr::eq(five_ref, same_five_ref));
974/// assert!(!ptr::eq(five_ref, other_five_ref));
975/// ```
976///
3b2f2976
XL
977/// For more information on how to use references, see [the book's section on "References and
978/// Borrowing"][book-refs].
979///
0731742a 980/// [book-refs]: ../book/ch04-02-references-and-borrowing.html
3b2f2976 981///
0bf4aa26
XL
982/// # Trait implementations
983///
3b2f2976
XL
984/// The following traits are implemented for all `&T`, regardless of the type of its referent:
985///
986/// * [`Copy`]
987/// * [`Clone`] \(Note that this will not defer to `T`'s `Clone` implementation if it exists!)
988/// * [`Deref`]
989/// * [`Borrow`]
990/// * [`Pointer`]
991///
1b1a35ee
XL
992/// [`Deref`]: ops::Deref
993/// [`Borrow`]: borrow::Borrow
994/// [`Pointer`]: fmt::Pointer
3b2f2976
XL
995///
996/// `&mut T` references get all of the above except `Copy` and `Clone` (to prevent creating
997/// multiple simultaneous mutable borrows), plus the following, regardless of the type of its
998/// referent:
999///
1000/// * [`DerefMut`]
1001/// * [`BorrowMut`]
1002///
1b1a35ee
XL
1003/// [`DerefMut`]: ops::DerefMut
1004/// [`BorrowMut`]: borrow::BorrowMut
3b2f2976
XL
1005///
1006/// The following traits are implemented on `&T` references if the underlying `T` also implements
1007/// that trait:
1008///
1009/// * All the traits in [`std::fmt`] except [`Pointer`] and [`fmt::Write`]
1010/// * [`PartialOrd`]
1011/// * [`Ord`]
1012/// * [`PartialEq`]
1013/// * [`Eq`]
1014/// * [`AsRef`]
1015/// * [`Fn`] \(in addition, `&T` references get [`FnMut`] and [`FnOnce`] if `T: Fn`)
1016/// * [`Hash`]
1017/// * [`ToSocketAddrs`]
1018///
1b1a35ee
XL
1019/// [`std::fmt`]: fmt
1020/// ['Pointer`]: fmt::Pointer
1021/// [`Hash`]: hash::Hash
1022/// [`ToSocketAddrs`]: net::ToSocketAddrs
3b2f2976
XL
1023///
1024/// `&mut T` references get all of the above except `ToSocketAddrs`, plus the following, if `T`
1025/// implements that trait:
1026///
1027/// * [`AsMut`]
1028/// * [`FnMut`] \(in addition, `&mut T` references get [`FnOnce`] if `T: FnMut`)
1029/// * [`fmt::Write`]
1030/// * [`Iterator`]
1031/// * [`DoubleEndedIterator`]
1032/// * [`ExactSizeIterator`]
1033/// * [`FusedIterator`]
1034/// * [`TrustedLen`]
1035/// * [`Send`] \(note that `&T` references only get `Send` if `T: Sync`)
1036/// * [`io::Write`]
1037/// * [`Read`]
1038/// * [`Seek`]
1039/// * [`BufRead`]
1040///
1b1a35ee
XL
1041/// [`FusedIterator`]: iter::FusedIterator
1042/// [`TrustedLen`]: iter::TrustedLen
1043/// [`Seek`]: io::Seek
1044/// [`BufRead`]: io::BufRead
1045/// [`Read`]: io::Read
3b2f2976
XL
1046///
1047/// Note that due to method call deref coercion, simply calling a trait method will act like they
1048/// work on references as well as they do on owned values! The implementations described here are
1049/// meant for generic contexts, where the final type `T` is a type parameter or otherwise not
1050/// locally known.
1051#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 1052mod prim_ref {}
3b2f2976
XL
1053
1054#[doc(primitive = "fn")]
1055//
1056/// Function pointers, like `fn(usize) -> bool`.
1057///
1058/// *See also the traits [`Fn`], [`FnMut`], and [`FnOnce`].*
1059///
1b1a35ee
XL
1060/// [`Fn`]: ops::Fn
1061/// [`FnMut`]: ops::FnMut
1062/// [`FnOnce`]: ops::FnOnce
3b2f2976 1063///
416331ca
XL
1064/// Function pointers are pointers that point to *code*, not data. They can be called
1065/// just like functions. Like references, function pointers are, among other things, assumed to
1066/// not be null, so if you want to pass a function pointer over FFI and be able to accommodate null
1067/// pointers, make your type `Option<fn()>` with your required signature.
1068///
3dfed10e
XL
1069/// ### Safety
1070///
3b2f2976
XL
1071/// Plain function pointers are obtained by casting either plain functions, or closures that don't
1072/// capture an environment:
1073///
1074/// ```
1075/// fn add_one(x: usize) -> usize {
1076/// x + 1
1077/// }
1078///
1079/// let ptr: fn(usize) -> usize = add_one;
1080/// assert_eq!(ptr(5), 6);
1081///
1082/// let clos: fn(usize) -> usize = |x| x + 5;
1083/// assert_eq!(clos(5), 10);
1084/// ```
1085///
1086/// In addition to varying based on their signature, function pointers come in two flavors: safe
1087/// and unsafe. Plain `fn()` function pointers can only point to safe functions,
1088/// while `unsafe fn()` function pointers can point to safe or unsafe functions.
1089///
1090/// ```
1091/// fn add_one(x: usize) -> usize {
1092/// x + 1
1093/// }
1094///
1095/// unsafe fn add_one_unsafely(x: usize) -> usize {
1096/// x + 1
1097/// }
1098///
1099/// let safe_ptr: fn(usize) -> usize = add_one;
1100///
1101/// //ERROR: mismatched types: expected normal fn, found unsafe fn
1102/// //let bad_ptr: fn(usize) -> usize = add_one_unsafely;
1103///
1104/// let unsafe_ptr: unsafe fn(usize) -> usize = add_one_unsafely;
1105/// let really_safe_ptr: unsafe fn(usize) -> usize = add_one;
1106/// ```
1107///
3dfed10e
XL
1108/// ### ABI
1109///
1110/// On top of that, function pointers can vary based on what ABI they use. This
1111/// is achieved by adding the `extern` keyword before the type, followed by the
1112/// ABI in question. The default ABI is "Rust", i.e., `fn()` is the exact same
1113/// type as `extern "Rust" fn()`. A pointer to a function with C ABI would have
1114/// type `extern "C" fn()`.
1115///
1116/// `extern "ABI" { ... }` blocks declare functions with ABI "ABI". The default
1117/// here is "C", i.e., functions declared in an `extern {...}` block have "C"
1118/// ABI.
3b2f2976 1119///
3dfed10e
XL
1120/// For more information and a list of supported ABIs, see [the nomicon's
1121/// section on foreign calling conventions][nomicon-abi].
1122///
29967ef6
XL
1123/// [nomicon-abi]: ../nomicon/ffi.html#foreign-calling-conventions
1124///
3dfed10e 1125/// ### Variadic functions
3b2f2976
XL
1126///
1127/// Extern function declarations with the "C" or "cdecl" ABIs can also be *variadic*, allowing them
3dfed10e 1128/// to be called with a variable number of arguments. Normal Rust functions, even those with an
3b2f2976
XL
1129/// `extern "ABI"`, cannot be variadic. For more information, see [the nomicon's section on
1130/// variadic functions][nomicon-variadic].
1131///
1132/// [nomicon-variadic]: ../nomicon/ffi.html#variadic-functions
1133///
3dfed10e
XL
1134/// ### Creating function pointers
1135///
1136/// When `bar` is the name of a function, then the expression `bar` is *not* a
1137/// function pointer. Rather, it denotes a value of an unnameable type that
1138/// uniquely identifies the function `bar`. The value is zero-sized because the
1139/// type already identifies the function. This has the advantage that "calling"
1140/// the value (it implements the `Fn*` traits) does not require dynamic
1141/// dispatch.
1142///
1143/// This zero-sized type *coerces* to a regular function pointer. For example:
1144///
1145/// ```rust
1146/// use std::mem;
1147///
1148/// fn bar(x: i32) {}
1149///
1150/// let not_bar_ptr = bar; // `not_bar_ptr` is zero-sized, uniquely identifying `bar`
1151/// assert_eq!(mem::size_of_val(&not_bar_ptr), 0);
1152///
1153/// let bar_ptr: fn(i32) = not_bar_ptr; // force coercion to function pointer
1154/// assert_eq!(mem::size_of_val(&bar_ptr), mem::size_of::<usize>());
1155///
1156/// let footgun = &bar; // this is a shared reference to the zero-sized type identifying `bar`
1157/// ```
1158///
1159/// The last line shows that `&bar` is not a function pointer either. Rather, it
1160/// is a reference to the function-specific ZST. `&bar` is basically never what you
1161/// want when `bar` is a function.
1162///
1163/// ### Traits
3b2f2976 1164///
3b2f2976
XL
1165/// Function pointers implement the following traits:
1166///
1167/// * [`Clone`]
1168/// * [`PartialEq`]
1169/// * [`Eq`]
1170/// * [`PartialOrd`]
1171/// * [`Ord`]
1172/// * [`Hash`]
1173/// * [`Pointer`]
1174/// * [`Debug`]
1175///
1b1a35ee
XL
1176/// [`Hash`]: hash::Hash
1177/// [`Pointer`]: fmt::Pointer
3b2f2976
XL
1178///
1179/// Due to a temporary restriction in Rust's type system, these traits are only implemented on
1180/// functions that take 12 arguments or less, with the `"Rust"` and `"C"` ABIs. In the future, this
1181/// may change.
1182///
1183/// In addition, function pointers of *any* signature, ABI, or safety are [`Copy`], and all *safe*
1184/// function pointers implement [`Fn`], [`FnMut`], and [`FnOnce`]. This works because these traits
1185/// are specially known to the compiler.
3b2f2976 1186#[stable(feature = "rust1", since = "1.0.0")]
dfeec247 1187mod prim_fn {}