]> git.lizzy.rs Git - rust.git/blob - library/core/src/num/mod.rs
Make char methods const
[rust.git] / library / core / src / num / mod.rs
1 //! Numeric traits and functions for the built-in numeric types.
2
3 #![stable(feature = "rust1", since = "1.0.0")]
4
5 use crate::intrinsics;
6 use crate::mem;
7 use crate::str::FromStr;
8
9 // Used because the `?` operator is not allowed in a const context.
10 macro_rules! try_opt {
11     ($e:expr) => {
12         match $e {
13             Some(x) => x,
14             None => return None,
15         }
16     };
17 }
18
19 #[allow_internal_unstable(const_likely)]
20 macro_rules! unlikely {
21     ($e: expr) => {
22         intrinsics::unlikely($e)
23     };
24 }
25
26 // All these modules are technically private and only exposed for coretests:
27 pub mod bignum;
28 pub mod dec2flt;
29 pub mod diy_float;
30 pub mod flt2dec;
31
32 #[macro_use]
33 mod int_macros; // import int_impl!
34 #[macro_use]
35 mod uint_macros; // import uint_impl!
36
37 mod error;
38 mod nonzero;
39 mod wrapping;
40
41 #[stable(feature = "rust1", since = "1.0.0")]
42 pub use wrapping::Wrapping;
43
44 #[stable(feature = "rust1", since = "1.0.0")]
45 pub use dec2flt::ParseFloatError;
46
47 #[stable(feature = "rust1", since = "1.0.0")]
48 pub use error::ParseIntError;
49
50 #[stable(feature = "nonzero", since = "1.28.0")]
51 pub use nonzero::{NonZeroU128, NonZeroU16, NonZeroU32, NonZeroU64, NonZeroU8, NonZeroUsize};
52
53 #[stable(feature = "signed_nonzero", since = "1.34.0")]
54 pub use nonzero::{NonZeroI128, NonZeroI16, NonZeroI32, NonZeroI64, NonZeroI8, NonZeroIsize};
55
56 #[stable(feature = "try_from", since = "1.34.0")]
57 pub use error::TryFromIntError;
58
59 #[unstable(
60     feature = "int_error_matching",
61     reason = "it can be useful to match errors when making error messages \
62               for integer parsing",
63     issue = "22639"
64 )]
65 pub use error::IntErrorKind;
66
67 macro_rules! usize_isize_to_xe_bytes_doc {
68     () => {
69         "
70
71 **Note**: This function returns an array of length 2, 4 or 8 bytes
72 depending on the target pointer size.
73
74 "
75     };
76 }
77
78 macro_rules! usize_isize_from_xe_bytes_doc {
79     () => {
80         "
81
82 **Note**: This function takes an array of length 2, 4 or 8 bytes
83 depending on the target pointer size.
84
85 "
86     };
87 }
88
89 #[lang = "i8"]
90 impl i8 {
91     int_impl! { i8, i8, u8, 8, -128, 127, 2, "-0x7e", "0xa", "0x12", "0x12", "0x48",
92     "[0x12]", "[0x12]", "", "" }
93 }
94
95 #[lang = "i16"]
96 impl i16 {
97     int_impl! { i16, i16, u16, 16, -32768, 32767, 4, "-0x5ffd", "0x3a", "0x1234", "0x3412",
98     "0x2c48", "[0x34, 0x12]", "[0x12, 0x34]", "", "" }
99 }
100
101 #[lang = "i32"]
102 impl i32 {
103     int_impl! { i32, i32, u32, 32, -2147483648, 2147483647, 8, "0x10000b3", "0xb301",
104     "0x12345678", "0x78563412", "0x1e6a2c48", "[0x78, 0x56, 0x34, 0x12]",
105     "[0x12, 0x34, 0x56, 0x78]", "", "" }
106 }
107
108 #[lang = "i64"]
109 impl i64 {
110     int_impl! { i64, i64, u64, 64, -9223372036854775808, 9223372036854775807, 12,
111     "0xaa00000000006e1", "0x6e10aa", "0x1234567890123456", "0x5634129078563412",
112     "0x6a2c48091e6a2c48", "[0x56, 0x34, 0x12, 0x90, 0x78, 0x56, 0x34, 0x12]",
113     "[0x12, 0x34, 0x56, 0x78, 0x90, 0x12, 0x34, 0x56]", "", "" }
114 }
115
116 #[lang = "i128"]
117 impl i128 {
118     int_impl! { i128, i128, u128, 128, -170141183460469231731687303715884105728,
119     170141183460469231731687303715884105727, 16,
120     "0x13f40000000000000000000000004f76", "0x4f7613f4", "0x12345678901234567890123456789012",
121     "0x12907856341290785634129078563412", "0x48091e6a2c48091e6a2c48091e6a2c48",
122     "[0x12, 0x90, 0x78, 0x56, 0x34, 0x12, 0x90, 0x78, \
123       0x56, 0x34, 0x12, 0x90, 0x78, 0x56, 0x34, 0x12]",
124     "[0x12, 0x34, 0x56, 0x78, 0x90, 0x12, 0x34, 0x56, \
125       0x78, 0x90, 0x12, 0x34, 0x56, 0x78, 0x90, 0x12]", "", "" }
126 }
127
128 #[cfg(target_pointer_width = "16")]
129 #[lang = "isize"]
130 impl isize {
131     int_impl! { isize, i16, usize, 16, -32768, 32767, 4, "-0x5ffd", "0x3a", "0x1234",
132     "0x3412", "0x2c48", "[0x34, 0x12]", "[0x12, 0x34]",
133     usize_isize_to_xe_bytes_doc!(), usize_isize_from_xe_bytes_doc!() }
134 }
135
136 #[cfg(target_pointer_width = "32")]
137 #[lang = "isize"]
138 impl isize {
139     int_impl! { isize, i32, usize, 32, -2147483648, 2147483647, 8, "0x10000b3", "0xb301",
140     "0x12345678", "0x78563412", "0x1e6a2c48", "[0x78, 0x56, 0x34, 0x12]",
141     "[0x12, 0x34, 0x56, 0x78]",
142     usize_isize_to_xe_bytes_doc!(), usize_isize_from_xe_bytes_doc!() }
143 }
144
145 #[cfg(target_pointer_width = "64")]
146 #[lang = "isize"]
147 impl isize {
148     int_impl! { isize, i64, usize, 64, -9223372036854775808, 9223372036854775807,
149     12, "0xaa00000000006e1", "0x6e10aa",  "0x1234567890123456", "0x5634129078563412",
150      "0x6a2c48091e6a2c48", "[0x56, 0x34, 0x12, 0x90, 0x78, 0x56, 0x34, 0x12]",
151      "[0x12, 0x34, 0x56, 0x78, 0x90, 0x12, 0x34, 0x56]",
152      usize_isize_to_xe_bytes_doc!(), usize_isize_from_xe_bytes_doc!() }
153 }
154
155 /// If 6th bit set ascii is upper case.
156 const ASCII_CASE_MASK: u8 = 0b0010_0000;
157
158 #[lang = "u8"]
159 impl u8 {
160     uint_impl! { u8, u8, 8, 255, 2, "0x82", "0xa", "0x12", "0x12", "0x48", "[0x12]",
161     "[0x12]", "", "" }
162
163     /// Checks if the value is within the ASCII range.
164     ///
165     /// # Examples
166     ///
167     /// ```
168     /// let ascii = 97u8;
169     /// let non_ascii = 150u8;
170     ///
171     /// assert!(ascii.is_ascii());
172     /// assert!(!non_ascii.is_ascii());
173     /// ```
174     #[stable(feature = "ascii_methods_on_intrinsics", since = "1.23.0")]
175     #[rustc_const_stable(feature = "const_ascii_methods_on_intrinsics", since = "1.43.0")]
176     #[inline]
177     pub const fn is_ascii(&self) -> bool {
178         *self & 128 == 0
179     }
180
181     /// Makes a copy of the value in its ASCII upper case equivalent.
182     ///
183     /// ASCII letters 'a' to 'z' are mapped to 'A' to 'Z',
184     /// but non-ASCII letters are unchanged.
185     ///
186     /// To uppercase the value in-place, use [`make_ascii_uppercase`].
187     ///
188     /// # Examples
189     ///
190     /// ```
191     /// let lowercase_a = 97u8;
192     ///
193     /// assert_eq!(65, lowercase_a.to_ascii_uppercase());
194     /// ```
195     ///
196     /// [`make_ascii_uppercase`]: #method.make_ascii_uppercase
197     #[stable(feature = "ascii_methods_on_intrinsics", since = "1.23.0")]
198     #[rustc_const_stable(feature = "const_ascii_methods_on_intrinsics", since = "1.50.0")]
199     #[inline]
200     pub const fn to_ascii_uppercase(&self) -> u8 {
201         // Unset the fifth bit if this is a lowercase letter
202         *self & !((self.is_ascii_lowercase() as u8) * ASCII_CASE_MASK)
203     }
204
205     /// Makes a copy of the value in its ASCII lower case equivalent.
206     ///
207     /// ASCII letters 'A' to 'Z' are mapped to 'a' to 'z',
208     /// but non-ASCII letters are unchanged.
209     ///
210     /// To lowercase the value in-place, use [`make_ascii_lowercase`].
211     ///
212     /// # Examples
213     ///
214     /// ```
215     /// let uppercase_a = 65u8;
216     ///
217     /// assert_eq!(97, uppercase_a.to_ascii_lowercase());
218     /// ```
219     ///
220     /// [`make_ascii_lowercase`]: #method.make_ascii_lowercase
221     #[stable(feature = "ascii_methods_on_intrinsics", since = "1.23.0")]
222     #[rustc_const_stable(feature = "const_ascii_methods_on_intrinsics", since = "1.50.0")]
223     #[inline]
224     pub const fn to_ascii_lowercase(&self) -> u8 {
225         // Set the fifth bit if this is an uppercase letter
226         *self | (self.is_ascii_uppercase() as u8 * ASCII_CASE_MASK)
227     }
228
229     /// Assumes self is ascii
230     #[inline]
231     pub(crate) fn ascii_change_case_unchecked(&self) -> u8 {
232         *self ^ ASCII_CASE_MASK
233     }
234
235     /// Checks that two values are an ASCII case-insensitive match.
236     ///
237     /// This is equivalent to `to_ascii_lowercase(a) == to_ascii_lowercase(b)`.
238     ///
239     /// # Examples
240     ///
241     /// ```
242     /// let lowercase_a = 97u8;
243     /// let uppercase_a = 65u8;
244     ///
245     /// assert!(lowercase_a.eq_ignore_ascii_case(&uppercase_a));
246     /// ```
247     #[stable(feature = "ascii_methods_on_intrinsics", since = "1.23.0")]
248     #[rustc_const_stable(feature = "const_ascii_methods_on_intrinsics", since = "1.50.0")]
249     #[inline]
250     pub const fn eq_ignore_ascii_case(&self, other: &u8) -> bool {
251         self.to_ascii_lowercase() == other.to_ascii_lowercase()
252     }
253
254     /// Converts this value to its ASCII upper case equivalent in-place.
255     ///
256     /// ASCII letters 'a' to 'z' are mapped to 'A' to 'Z',
257     /// but non-ASCII letters are unchanged.
258     ///
259     /// To return a new uppercased value without modifying the existing one, use
260     /// [`to_ascii_uppercase`].
261     ///
262     /// # Examples
263     ///
264     /// ```
265     /// let mut byte = b'a';
266     ///
267     /// byte.make_ascii_uppercase();
268     ///
269     /// assert_eq!(b'A', byte);
270     /// ```
271     ///
272     /// [`to_ascii_uppercase`]: #method.to_ascii_uppercase
273     #[stable(feature = "ascii_methods_on_intrinsics", since = "1.23.0")]
274     #[inline]
275     pub fn make_ascii_uppercase(&mut self) {
276         *self = self.to_ascii_uppercase();
277     }
278
279     /// Converts this value to its ASCII lower case equivalent in-place.
280     ///
281     /// ASCII letters 'A' to 'Z' are mapped to 'a' to 'z',
282     /// but non-ASCII letters are unchanged.
283     ///
284     /// To return a new lowercased value without modifying the existing one, use
285     /// [`to_ascii_lowercase`].
286     ///
287     /// # Examples
288     ///
289     /// ```
290     /// let mut byte = b'A';
291     ///
292     /// byte.make_ascii_lowercase();
293     ///
294     /// assert_eq!(b'a', byte);
295     /// ```
296     ///
297     /// [`to_ascii_lowercase`]: #method.to_ascii_lowercase
298     #[stable(feature = "ascii_methods_on_intrinsics", since = "1.23.0")]
299     #[inline]
300     pub fn make_ascii_lowercase(&mut self) {
301         *self = self.to_ascii_lowercase();
302     }
303
304     /// Checks if the value is an ASCII alphabetic character:
305     ///
306     /// - U+0041 'A' ..= U+005A 'Z', or
307     /// - U+0061 'a' ..= U+007A 'z'.
308     ///
309     /// # Examples
310     ///
311     /// ```
312     /// let uppercase_a = b'A';
313     /// let uppercase_g = b'G';
314     /// let a = b'a';
315     /// let g = b'g';
316     /// let zero = b'0';
317     /// let percent = b'%';
318     /// let space = b' ';
319     /// let lf = b'\n';
320     /// let esc = 0x1b_u8;
321     ///
322     /// assert!(uppercase_a.is_ascii_alphabetic());
323     /// assert!(uppercase_g.is_ascii_alphabetic());
324     /// assert!(a.is_ascii_alphabetic());
325     /// assert!(g.is_ascii_alphabetic());
326     /// assert!(!zero.is_ascii_alphabetic());
327     /// assert!(!percent.is_ascii_alphabetic());
328     /// assert!(!space.is_ascii_alphabetic());
329     /// assert!(!lf.is_ascii_alphabetic());
330     /// assert!(!esc.is_ascii_alphabetic());
331     /// ```
332     #[stable(feature = "ascii_ctype_on_intrinsics", since = "1.24.0")]
333     #[rustc_const_stable(feature = "const_ascii_ctype_on_intrinsics", since = "1.47.0")]
334     #[inline]
335     pub const fn is_ascii_alphabetic(&self) -> bool {
336         matches!(*self, b'A'..=b'Z' | b'a'..=b'z')
337     }
338
339     /// Checks if the value is an ASCII uppercase character:
340     /// U+0041 'A' ..= U+005A 'Z'.
341     ///
342     /// # Examples
343     ///
344     /// ```
345     /// let uppercase_a = b'A';
346     /// let uppercase_g = b'G';
347     /// let a = b'a';
348     /// let g = b'g';
349     /// let zero = b'0';
350     /// let percent = b'%';
351     /// let space = b' ';
352     /// let lf = b'\n';
353     /// let esc = 0x1b_u8;
354     ///
355     /// assert!(uppercase_a.is_ascii_uppercase());
356     /// assert!(uppercase_g.is_ascii_uppercase());
357     /// assert!(!a.is_ascii_uppercase());
358     /// assert!(!g.is_ascii_uppercase());
359     /// assert!(!zero.is_ascii_uppercase());
360     /// assert!(!percent.is_ascii_uppercase());
361     /// assert!(!space.is_ascii_uppercase());
362     /// assert!(!lf.is_ascii_uppercase());
363     /// assert!(!esc.is_ascii_uppercase());
364     /// ```
365     #[stable(feature = "ascii_ctype_on_intrinsics", since = "1.24.0")]
366     #[rustc_const_stable(feature = "const_ascii_ctype_on_intrinsics", since = "1.47.0")]
367     #[inline]
368     pub const fn is_ascii_uppercase(&self) -> bool {
369         matches!(*self, b'A'..=b'Z')
370     }
371
372     /// Checks if the value is an ASCII lowercase character:
373     /// U+0061 'a' ..= U+007A 'z'.
374     ///
375     /// # Examples
376     ///
377     /// ```
378     /// let uppercase_a = b'A';
379     /// let uppercase_g = b'G';
380     /// let a = b'a';
381     /// let g = b'g';
382     /// let zero = b'0';
383     /// let percent = b'%';
384     /// let space = b' ';
385     /// let lf = b'\n';
386     /// let esc = 0x1b_u8;
387     ///
388     /// assert!(!uppercase_a.is_ascii_lowercase());
389     /// assert!(!uppercase_g.is_ascii_lowercase());
390     /// assert!(a.is_ascii_lowercase());
391     /// assert!(g.is_ascii_lowercase());
392     /// assert!(!zero.is_ascii_lowercase());
393     /// assert!(!percent.is_ascii_lowercase());
394     /// assert!(!space.is_ascii_lowercase());
395     /// assert!(!lf.is_ascii_lowercase());
396     /// assert!(!esc.is_ascii_lowercase());
397     /// ```
398     #[stable(feature = "ascii_ctype_on_intrinsics", since = "1.24.0")]
399     #[rustc_const_stable(feature = "const_ascii_ctype_on_intrinsics", since = "1.47.0")]
400     #[inline]
401     pub const fn is_ascii_lowercase(&self) -> bool {
402         matches!(*self, b'a'..=b'z')
403     }
404
405     /// Checks if the value is an ASCII alphanumeric character:
406     ///
407     /// - U+0041 'A' ..= U+005A 'Z', or
408     /// - U+0061 'a' ..= U+007A 'z', or
409     /// - U+0030 '0' ..= U+0039 '9'.
410     ///
411     /// # Examples
412     ///
413     /// ```
414     /// let uppercase_a = b'A';
415     /// let uppercase_g = b'G';
416     /// let a = b'a';
417     /// let g = b'g';
418     /// let zero = b'0';
419     /// let percent = b'%';
420     /// let space = b' ';
421     /// let lf = b'\n';
422     /// let esc = 0x1b_u8;
423     ///
424     /// assert!(uppercase_a.is_ascii_alphanumeric());
425     /// assert!(uppercase_g.is_ascii_alphanumeric());
426     /// assert!(a.is_ascii_alphanumeric());
427     /// assert!(g.is_ascii_alphanumeric());
428     /// assert!(zero.is_ascii_alphanumeric());
429     /// assert!(!percent.is_ascii_alphanumeric());
430     /// assert!(!space.is_ascii_alphanumeric());
431     /// assert!(!lf.is_ascii_alphanumeric());
432     /// assert!(!esc.is_ascii_alphanumeric());
433     /// ```
434     #[stable(feature = "ascii_ctype_on_intrinsics", since = "1.24.0")]
435     #[rustc_const_stable(feature = "const_ascii_ctype_on_intrinsics", since = "1.47.0")]
436     #[inline]
437     pub const fn is_ascii_alphanumeric(&self) -> bool {
438         matches!(*self, b'0'..=b'9' | b'A'..=b'Z' | b'a'..=b'z')
439     }
440
441     /// Checks if the value is an ASCII decimal digit:
442     /// U+0030 '0' ..= U+0039 '9'.
443     ///
444     /// # Examples
445     ///
446     /// ```
447     /// let uppercase_a = b'A';
448     /// let uppercase_g = b'G';
449     /// let a = b'a';
450     /// let g = b'g';
451     /// let zero = b'0';
452     /// let percent = b'%';
453     /// let space = b' ';
454     /// let lf = b'\n';
455     /// let esc = 0x1b_u8;
456     ///
457     /// assert!(!uppercase_a.is_ascii_digit());
458     /// assert!(!uppercase_g.is_ascii_digit());
459     /// assert!(!a.is_ascii_digit());
460     /// assert!(!g.is_ascii_digit());
461     /// assert!(zero.is_ascii_digit());
462     /// assert!(!percent.is_ascii_digit());
463     /// assert!(!space.is_ascii_digit());
464     /// assert!(!lf.is_ascii_digit());
465     /// assert!(!esc.is_ascii_digit());
466     /// ```
467     #[stable(feature = "ascii_ctype_on_intrinsics", since = "1.24.0")]
468     #[rustc_const_stable(feature = "const_ascii_ctype_on_intrinsics", since = "1.47.0")]
469     #[inline]
470     pub const fn is_ascii_digit(&self) -> bool {
471         matches!(*self, b'0'..=b'9')
472     }
473
474     /// Checks if the value is an ASCII hexadecimal digit:
475     ///
476     /// - U+0030 '0' ..= U+0039 '9', or
477     /// - U+0041 'A' ..= U+0046 'F', or
478     /// - U+0061 'a' ..= U+0066 'f'.
479     ///
480     /// # Examples
481     ///
482     /// ```
483     /// let uppercase_a = b'A';
484     /// let uppercase_g = b'G';
485     /// let a = b'a';
486     /// let g = b'g';
487     /// let zero = b'0';
488     /// let percent = b'%';
489     /// let space = b' ';
490     /// let lf = b'\n';
491     /// let esc = 0x1b_u8;
492     ///
493     /// assert!(uppercase_a.is_ascii_hexdigit());
494     /// assert!(!uppercase_g.is_ascii_hexdigit());
495     /// assert!(a.is_ascii_hexdigit());
496     /// assert!(!g.is_ascii_hexdigit());
497     /// assert!(zero.is_ascii_hexdigit());
498     /// assert!(!percent.is_ascii_hexdigit());
499     /// assert!(!space.is_ascii_hexdigit());
500     /// assert!(!lf.is_ascii_hexdigit());
501     /// assert!(!esc.is_ascii_hexdigit());
502     /// ```
503     #[stable(feature = "ascii_ctype_on_intrinsics", since = "1.24.0")]
504     #[rustc_const_stable(feature = "const_ascii_ctype_on_intrinsics", since = "1.47.0")]
505     #[inline]
506     pub const fn is_ascii_hexdigit(&self) -> bool {
507         matches!(*self, b'0'..=b'9' | b'A'..=b'F' | b'a'..=b'f')
508     }
509
510     /// Checks if the value is an ASCII punctuation character:
511     ///
512     /// - U+0021 ..= U+002F `! " # $ % & ' ( ) * + , - . /`, or
513     /// - U+003A ..= U+0040 `: ; < = > ? @`, or
514     /// - U+005B ..= U+0060 ``[ \ ] ^ _ ` ``, or
515     /// - U+007B ..= U+007E `{ | } ~`
516     ///
517     /// # Examples
518     ///
519     /// ```
520     /// let uppercase_a = b'A';
521     /// let uppercase_g = b'G';
522     /// let a = b'a';
523     /// let g = b'g';
524     /// let zero = b'0';
525     /// let percent = b'%';
526     /// let space = b' ';
527     /// let lf = b'\n';
528     /// let esc = 0x1b_u8;
529     ///
530     /// assert!(!uppercase_a.is_ascii_punctuation());
531     /// assert!(!uppercase_g.is_ascii_punctuation());
532     /// assert!(!a.is_ascii_punctuation());
533     /// assert!(!g.is_ascii_punctuation());
534     /// assert!(!zero.is_ascii_punctuation());
535     /// assert!(percent.is_ascii_punctuation());
536     /// assert!(!space.is_ascii_punctuation());
537     /// assert!(!lf.is_ascii_punctuation());
538     /// assert!(!esc.is_ascii_punctuation());
539     /// ```
540     #[stable(feature = "ascii_ctype_on_intrinsics", since = "1.24.0")]
541     #[rustc_const_stable(feature = "const_ascii_ctype_on_intrinsics", since = "1.47.0")]
542     #[inline]
543     pub const fn is_ascii_punctuation(&self) -> bool {
544         matches!(*self, b'!'..=b'/' | b':'..=b'@' | b'['..=b'`' | b'{'..=b'~')
545     }
546
547     /// Checks if the value is an ASCII graphic character:
548     /// U+0021 '!' ..= U+007E '~'.
549     ///
550     /// # Examples
551     ///
552     /// ```
553     /// let uppercase_a = b'A';
554     /// let uppercase_g = b'G';
555     /// let a = b'a';
556     /// let g = b'g';
557     /// let zero = b'0';
558     /// let percent = b'%';
559     /// let space = b' ';
560     /// let lf = b'\n';
561     /// let esc = 0x1b_u8;
562     ///
563     /// assert!(uppercase_a.is_ascii_graphic());
564     /// assert!(uppercase_g.is_ascii_graphic());
565     /// assert!(a.is_ascii_graphic());
566     /// assert!(g.is_ascii_graphic());
567     /// assert!(zero.is_ascii_graphic());
568     /// assert!(percent.is_ascii_graphic());
569     /// assert!(!space.is_ascii_graphic());
570     /// assert!(!lf.is_ascii_graphic());
571     /// assert!(!esc.is_ascii_graphic());
572     /// ```
573     #[stable(feature = "ascii_ctype_on_intrinsics", since = "1.24.0")]
574     #[rustc_const_stable(feature = "const_ascii_ctype_on_intrinsics", since = "1.47.0")]
575     #[inline]
576     pub const fn is_ascii_graphic(&self) -> bool {
577         matches!(*self, b'!'..=b'~')
578     }
579
580     /// Checks if the value is an ASCII whitespace character:
581     /// U+0020 SPACE, U+0009 HORIZONTAL TAB, U+000A LINE FEED,
582     /// U+000C FORM FEED, or U+000D CARRIAGE RETURN.
583     ///
584     /// Rust uses the WhatWG Infra Standard's [definition of ASCII
585     /// whitespace][infra-aw]. There are several other definitions in
586     /// wide use. For instance, [the POSIX locale][pct] includes
587     /// U+000B VERTICAL TAB as well as all the above characters,
588     /// but—from the very same specification—[the default rule for
589     /// "field splitting" in the Bourne shell][bfs] considers *only*
590     /// SPACE, HORIZONTAL TAB, and LINE FEED as whitespace.
591     ///
592     /// If you are writing a program that will process an existing
593     /// file format, check what that format's definition of whitespace is
594     /// before using this function.
595     ///
596     /// [infra-aw]: https://infra.spec.whatwg.org/#ascii-whitespace
597     /// [pct]: http://pubs.opengroup.org/onlinepubs/9699919799/basedefs/V1_chap07.html#tag_07_03_01
598     /// [bfs]: http://pubs.opengroup.org/onlinepubs/9699919799/utilities/V3_chap02.html#tag_18_06_05
599     ///
600     /// # Examples
601     ///
602     /// ```
603     /// let uppercase_a = b'A';
604     /// let uppercase_g = b'G';
605     /// let a = b'a';
606     /// let g = b'g';
607     /// let zero = b'0';
608     /// let percent = b'%';
609     /// let space = b' ';
610     /// let lf = b'\n';
611     /// let esc = 0x1b_u8;
612     ///
613     /// assert!(!uppercase_a.is_ascii_whitespace());
614     /// assert!(!uppercase_g.is_ascii_whitespace());
615     /// assert!(!a.is_ascii_whitespace());
616     /// assert!(!g.is_ascii_whitespace());
617     /// assert!(!zero.is_ascii_whitespace());
618     /// assert!(!percent.is_ascii_whitespace());
619     /// assert!(space.is_ascii_whitespace());
620     /// assert!(lf.is_ascii_whitespace());
621     /// assert!(!esc.is_ascii_whitespace());
622     /// ```
623     #[stable(feature = "ascii_ctype_on_intrinsics", since = "1.24.0")]
624     #[rustc_const_stable(feature = "const_ascii_ctype_on_intrinsics", since = "1.47.0")]
625     #[inline]
626     pub const fn is_ascii_whitespace(&self) -> bool {
627         matches!(*self, b'\t' | b'\n' | b'\x0C' | b'\r' | b' ')
628     }
629
630     /// Checks if the value is an ASCII control character:
631     /// U+0000 NUL ..= U+001F UNIT SEPARATOR, or U+007F DELETE.
632     /// Note that most ASCII whitespace characters are control
633     /// characters, but SPACE is not.
634     ///
635     /// # Examples
636     ///
637     /// ```
638     /// let uppercase_a = b'A';
639     /// let uppercase_g = b'G';
640     /// let a = b'a';
641     /// let g = b'g';
642     /// let zero = b'0';
643     /// let percent = b'%';
644     /// let space = b' ';
645     /// let lf = b'\n';
646     /// let esc = 0x1b_u8;
647     ///
648     /// assert!(!uppercase_a.is_ascii_control());
649     /// assert!(!uppercase_g.is_ascii_control());
650     /// assert!(!a.is_ascii_control());
651     /// assert!(!g.is_ascii_control());
652     /// assert!(!zero.is_ascii_control());
653     /// assert!(!percent.is_ascii_control());
654     /// assert!(!space.is_ascii_control());
655     /// assert!(lf.is_ascii_control());
656     /// assert!(esc.is_ascii_control());
657     /// ```
658     #[stable(feature = "ascii_ctype_on_intrinsics", since = "1.24.0")]
659     #[rustc_const_stable(feature = "const_ascii_ctype_on_intrinsics", since = "1.47.0")]
660     #[inline]
661     pub const fn is_ascii_control(&self) -> bool {
662         matches!(*self, b'\0'..=b'\x1F' | b'\x7F')
663     }
664 }
665
666 #[lang = "u16"]
667 impl u16 {
668     uint_impl! { u16, u16, 16, 65535, 4, "0xa003", "0x3a", "0x1234", "0x3412", "0x2c48",
669     "[0x34, 0x12]", "[0x12, 0x34]", "", "" }
670 }
671
672 #[lang = "u32"]
673 impl u32 {
674     uint_impl! { u32, u32, 32, 4294967295, 8, "0x10000b3", "0xb301", "0x12345678",
675     "0x78563412", "0x1e6a2c48", "[0x78, 0x56, 0x34, 0x12]", "[0x12, 0x34, 0x56, 0x78]", "", "" }
676 }
677
678 #[lang = "u64"]
679 impl u64 {
680     uint_impl! { u64, u64, 64, 18446744073709551615, 12, "0xaa00000000006e1", "0x6e10aa",
681     "0x1234567890123456", "0x5634129078563412", "0x6a2c48091e6a2c48",
682     "[0x56, 0x34, 0x12, 0x90, 0x78, 0x56, 0x34, 0x12]",
683     "[0x12, 0x34, 0x56, 0x78, 0x90, 0x12, 0x34, 0x56]",
684     "", ""}
685 }
686
687 #[lang = "u128"]
688 impl u128 {
689     uint_impl! { u128, u128, 128, 340282366920938463463374607431768211455, 16,
690     "0x13f40000000000000000000000004f76", "0x4f7613f4", "0x12345678901234567890123456789012",
691     "0x12907856341290785634129078563412", "0x48091e6a2c48091e6a2c48091e6a2c48",
692     "[0x12, 0x90, 0x78, 0x56, 0x34, 0x12, 0x90, 0x78, \
693       0x56, 0x34, 0x12, 0x90, 0x78, 0x56, 0x34, 0x12]",
694     "[0x12, 0x34, 0x56, 0x78, 0x90, 0x12, 0x34, 0x56, \
695       0x78, 0x90, 0x12, 0x34, 0x56, 0x78, 0x90, 0x12]",
696      "", ""}
697 }
698
699 #[cfg(target_pointer_width = "16")]
700 #[lang = "usize"]
701 impl usize {
702     uint_impl! { usize, u16, 16, 65535, 4, "0xa003", "0x3a", "0x1234", "0x3412", "0x2c48",
703     "[0x34, 0x12]", "[0x12, 0x34]",
704     usize_isize_to_xe_bytes_doc!(), usize_isize_from_xe_bytes_doc!() }
705 }
706 #[cfg(target_pointer_width = "32")]
707 #[lang = "usize"]
708 impl usize {
709     uint_impl! { usize, u32, 32, 4294967295, 8, "0x10000b3", "0xb301", "0x12345678",
710     "0x78563412", "0x1e6a2c48", "[0x78, 0x56, 0x34, 0x12]", "[0x12, 0x34, 0x56, 0x78]",
711     usize_isize_to_xe_bytes_doc!(), usize_isize_from_xe_bytes_doc!() }
712 }
713
714 #[cfg(target_pointer_width = "64")]
715 #[lang = "usize"]
716 impl usize {
717     uint_impl! { usize, u64, 64, 18446744073709551615, 12, "0xaa00000000006e1", "0x6e10aa",
718     "0x1234567890123456", "0x5634129078563412", "0x6a2c48091e6a2c48",
719     "[0x56, 0x34, 0x12, 0x90, 0x78, 0x56, 0x34, 0x12]",
720      "[0x12, 0x34, 0x56, 0x78, 0x90, 0x12, 0x34, 0x56]",
721     usize_isize_to_xe_bytes_doc!(), usize_isize_from_xe_bytes_doc!() }
722 }
723
724 /// A classification of floating point numbers.
725 ///
726 /// This `enum` is used as the return type for [`f32::classify`] and [`f64::classify`]. See
727 /// their documentation for more.
728 ///
729 /// [`f32::classify`]: ../../std/primitive.f32.html#method.classify
730 /// [`f64::classify`]: ../../std/primitive.f64.html#method.classify
731 ///
732 /// # Examples
733 ///
734 /// ```
735 /// use std::num::FpCategory;
736 ///
737 /// let num = 12.4_f32;
738 /// let inf = f32::INFINITY;
739 /// let zero = 0f32;
740 /// let sub: f32 = 1.1754942e-38;
741 /// let nan = f32::NAN;
742 ///
743 /// assert_eq!(num.classify(), FpCategory::Normal);
744 /// assert_eq!(inf.classify(), FpCategory::Infinite);
745 /// assert_eq!(zero.classify(), FpCategory::Zero);
746 /// assert_eq!(nan.classify(), FpCategory::Nan);
747 /// assert_eq!(sub.classify(), FpCategory::Subnormal);
748 /// ```
749 #[derive(Copy, Clone, PartialEq, Eq, Debug)]
750 #[stable(feature = "rust1", since = "1.0.0")]
751 pub enum FpCategory {
752     /// "Not a Number", often obtained by dividing by zero.
753     #[stable(feature = "rust1", since = "1.0.0")]
754     Nan,
755
756     /// Positive or negative infinity.
757     #[stable(feature = "rust1", since = "1.0.0")]
758     Infinite,
759
760     /// Positive or negative zero.
761     #[stable(feature = "rust1", since = "1.0.0")]
762     Zero,
763
764     /// De-normalized floating point representation (less precise than `Normal`).
765     #[stable(feature = "rust1", since = "1.0.0")]
766     Subnormal,
767
768     /// A regular floating point number.
769     #[stable(feature = "rust1", since = "1.0.0")]
770     Normal,
771 }
772
773 #[doc(hidden)]
774 trait FromStrRadixHelper: PartialOrd + Copy {
775     fn min_value() -> Self;
776     fn max_value() -> Self;
777     fn from_u32(u: u32) -> Self;
778     fn checked_mul(&self, other: u32) -> Option<Self>;
779     fn checked_sub(&self, other: u32) -> Option<Self>;
780     fn checked_add(&self, other: u32) -> Option<Self>;
781 }
782
783 macro_rules! from_str_radix_int_impl {
784     ($($t:ty)*) => {$(
785         #[stable(feature = "rust1", since = "1.0.0")]
786         impl FromStr for $t {
787             type Err = ParseIntError;
788             fn from_str(src: &str) -> Result<Self, ParseIntError> {
789                 from_str_radix(src, 10)
790             }
791         }
792     )*}
793 }
794 from_str_radix_int_impl! { isize i8 i16 i32 i64 i128 usize u8 u16 u32 u64 u128 }
795
796 macro_rules! doit {
797     ($($t:ty)*) => ($(impl FromStrRadixHelper for $t {
798         #[inline]
799         fn min_value() -> Self { Self::MIN }
800         #[inline]
801         fn max_value() -> Self { Self::MAX }
802         #[inline]
803         fn from_u32(u: u32) -> Self { u as Self }
804         #[inline]
805         fn checked_mul(&self, other: u32) -> Option<Self> {
806             Self::checked_mul(*self, other as Self)
807         }
808         #[inline]
809         fn checked_sub(&self, other: u32) -> Option<Self> {
810             Self::checked_sub(*self, other as Self)
811         }
812         #[inline]
813         fn checked_add(&self, other: u32) -> Option<Self> {
814             Self::checked_add(*self, other as Self)
815         }
816     })*)
817 }
818 doit! { i8 i16 i32 i64 i128 isize u8 u16 u32 u64 u128 usize }
819
820 fn from_str_radix<T: FromStrRadixHelper>(src: &str, radix: u32) -> Result<T, ParseIntError> {
821     use self::IntErrorKind::*;
822     use self::ParseIntError as PIE;
823
824     assert!(
825         radix >= 2 && radix <= 36,
826         "from_str_radix_int: must lie in the range `[2, 36]` - found {}",
827         radix
828     );
829
830     if src.is_empty() {
831         return Err(PIE { kind: Empty });
832     }
833
834     let is_signed_ty = T::from_u32(0) > T::min_value();
835
836     // all valid digits are ascii, so we will just iterate over the utf8 bytes
837     // and cast them to chars. .to_digit() will safely return None for anything
838     // other than a valid ascii digit for the given radix, including the first-byte
839     // of multi-byte sequences
840     let src = src.as_bytes();
841
842     let (is_positive, digits) = match src[0] {
843         b'+' | b'-' if src[1..].is_empty() => {
844             return Err(PIE { kind: InvalidDigit });
845         }
846         b'+' => (true, &src[1..]),
847         b'-' if is_signed_ty => (false, &src[1..]),
848         _ => (true, src),
849     };
850
851     let mut result = T::from_u32(0);
852     if is_positive {
853         // The number is positive
854         for &c in digits {
855             let x = match (c as char).to_digit(radix) {
856                 Some(x) => x,
857                 None => return Err(PIE { kind: InvalidDigit }),
858             };
859             result = match result.checked_mul(radix) {
860                 Some(result) => result,
861                 None => return Err(PIE { kind: PosOverflow }),
862             };
863             result = match result.checked_add(x) {
864                 Some(result) => result,
865                 None => return Err(PIE { kind: PosOverflow }),
866             };
867         }
868     } else {
869         // The number is negative
870         for &c in digits {
871             let x = match (c as char).to_digit(radix) {
872                 Some(x) => x,
873                 None => return Err(PIE { kind: InvalidDigit }),
874             };
875             result = match result.checked_mul(radix) {
876                 Some(result) => result,
877                 None => return Err(PIE { kind: NegOverflow }),
878             };
879             result = match result.checked_sub(x) {
880                 Some(result) => result,
881                 None => return Err(PIE { kind: NegOverflow }),
882             };
883         }
884     }
885     Ok(result)
886 }