core/str/mod.rs
1//! String manipulation.
2//!
3//! For more details, see the [`std::str`] module.
4//!
5//! [`std::str`]: ../../std/str/index.html
6
7#![stable(feature = "rust1", since = "1.0.0")]
8
9mod converts;
10#[cfg(not(feature = "ferrocene_subset"))]
11mod count;
12mod error;
13mod iter;
14mod traits;
15mod validations;
16
17#[cfg(not(feature = "ferrocene_subset"))]
18use self::pattern::{DoubleEndedSearcher, Pattern, ReverseSearcher, Searcher};
19#[cfg(not(feature = "ferrocene_subset"))]
20use crate::char::{self, EscapeDebugExtArgs};
21#[cfg(not(feature = "ferrocene_subset"))]
22use crate::ops::Range;
23#[cfg(not(feature = "ferrocene_subset"))]
24use crate::slice::{self, SliceIndex};
25#[cfg(not(feature = "ferrocene_subset"))]
26use crate::ub_checks::assert_unsafe_precondition;
27#[cfg(not(feature = "ferrocene_subset"))]
28use crate::{ascii, mem};
29
30// Ferrocene addition: imports for certified subset
31#[cfg(feature = "ferrocene_subset")]
32#[rustfmt::skip]
33use {
34 self::pattern::Pattern,
35 crate::{mem, slice::SliceIndex},
36};
37
38pub mod pattern;
39
40#[cfg(not(feature = "ferrocene_subset"))]
41mod lossy;
42#[unstable(feature = "str_from_raw_parts", issue = "119206")]
43#[cfg(not(feature = "ferrocene_subset"))]
44pub use converts::{from_raw_parts, from_raw_parts_mut};
45#[stable(feature = "rust1", since = "1.0.0")]
46pub use converts::{from_utf8, from_utf8_unchecked};
47#[stable(feature = "str_mut_extras", since = "1.20.0")]
48pub use converts::{from_utf8_mut, from_utf8_unchecked_mut};
49#[stable(feature = "rust1", since = "1.0.0")]
50#[cfg(not(feature = "ferrocene_subset"))]
51pub use error::{ParseBoolError, Utf8Error};
52#[stable(feature = "encode_utf16", since = "1.8.0")]
53#[cfg(not(feature = "ferrocene_subset"))]
54pub use iter::EncodeUtf16;
55#[stable(feature = "rust1", since = "1.0.0")]
56#[allow(deprecated)]
57#[cfg(not(feature = "ferrocene_subset"))]
58pub use iter::LinesAny;
59#[stable(feature = "split_ascii_whitespace", since = "1.34.0")]
60#[cfg(not(feature = "ferrocene_subset"))]
61pub use iter::SplitAsciiWhitespace;
62#[stable(feature = "split_inclusive", since = "1.51.0")]
63#[cfg(not(feature = "ferrocene_subset"))]
64pub use iter::SplitInclusive;
65#[stable(feature = "rust1", since = "1.0.0")]
66#[cfg(not(feature = "ferrocene_subset"))]
67pub use iter::{Bytes, CharIndices, Chars, Lines, SplitWhitespace};
68#[stable(feature = "str_escape", since = "1.34.0")]
69#[cfg(not(feature = "ferrocene_subset"))]
70pub use iter::{EscapeDebug, EscapeDefault, EscapeUnicode};
71#[stable(feature = "str_match_indices", since = "1.5.0")]
72#[cfg(not(feature = "ferrocene_subset"))]
73pub use iter::{MatchIndices, RMatchIndices};
74#[cfg(not(feature = "ferrocene_subset"))]
75use iter::{MatchIndicesInternal, MatchesInternal, SplitInternal, SplitNInternal};
76#[stable(feature = "str_matches", since = "1.2.0")]
77#[cfg(not(feature = "ferrocene_subset"))]
78pub use iter::{Matches, RMatches};
79#[stable(feature = "rust1", since = "1.0.0")]
80#[cfg(not(feature = "ferrocene_subset"))]
81pub use iter::{RSplit, RSplitTerminator, Split, SplitTerminator};
82#[stable(feature = "rust1", since = "1.0.0")]
83#[cfg(not(feature = "ferrocene_subset"))]
84pub use iter::{RSplitN, SplitN};
85#[stable(feature = "utf8_chunks", since = "1.79.0")]
86#[cfg(not(feature = "ferrocene_subset"))]
87pub use lossy::{Utf8Chunk, Utf8Chunks};
88#[stable(feature = "rust1", since = "1.0.0")]
89pub use traits::FromStr;
90#[unstable(feature = "str_internals", issue = "none")]
91pub use validations::{next_code_point, utf8_char_width};
92
93#[stable(feature = "rust1", since = "1.0.0")]
94#[cfg(feature = "ferrocene_subset")]
95#[rustfmt::skip]
96pub use {
97 error::Utf8Error,
98 iter::{Bytes, Chars},
99};
100
101#[inline(never)]
102#[cold]
103#[track_caller]
104#[rustc_allow_const_fn_unstable(const_eval_select)]
105#[cfg(not(panic = "immediate-abort"))]
106const fn slice_error_fail(s: &str, begin: usize, end: usize) -> ! {
107 crate::intrinsics::const_eval_select((s, begin, end), slice_error_fail_ct, slice_error_fail_rt)
108}
109
110#[cfg(panic = "immediate-abort")]
111#[cfg(not(feature = "ferrocene_subset"))]
112const fn slice_error_fail(s: &str, begin: usize, end: usize) -> ! {
113 slice_error_fail_ct(s, begin, end)
114}
115
116#[track_caller]
117const fn slice_error_fail_ct(_: &str, _: usize, _: usize) -> ! {
118 panic!("failed to slice string");
119}
120
121#[track_caller]
122fn slice_error_fail_rt(s: &str, begin: usize, end: usize) -> ! {
123 const MAX_DISPLAY_LENGTH: usize = 256;
124 let trunc_len = s.floor_char_boundary(MAX_DISPLAY_LENGTH);
125 let s_trunc = &s[..trunc_len];
126 let ellipsis = if trunc_len < s.len() { "[...]" } else { "" };
127
128 // 1. out of bounds
129 if begin > s.len() || end > s.len() {
130 let oob_index = if begin > s.len() { begin } else { end };
131 panic!("byte index {oob_index} is out of bounds of `{s_trunc}`{ellipsis}");
132 }
133
134 // 2. begin <= end
135 assert!(
136 begin <= end,
137 "begin <= end ({} <= {}) when slicing `{}`{}",
138 begin,
139 end,
140 s_trunc,
141 ellipsis
142 );
143
144 // 3. character boundary
145 let index = if !s.is_char_boundary(begin) { begin } else { end };
146 // find the character
147 let char_start = s.floor_char_boundary(index);
148 // `char_start` must be less than len and a char boundary
149 let ch = s[char_start..].chars().next().unwrap();
150 let char_range = char_start..char_start + ch.len_utf8();
151 panic!(
152 "byte index {} is not a char boundary; it is inside {:?} (bytes {:?}) of `{}`{}",
153 index, ch, char_range, s_trunc, ellipsis
154 );
155}
156
157impl str {
158 /// Returns the length of `self`.
159 ///
160 /// This length is in bytes, not [`char`]s or graphemes. In other words,
161 /// it might not be what a human considers the length of the string.
162 ///
163 /// [`char`]: prim@char
164 ///
165 /// # Examples
166 ///
167 /// ```
168 /// let len = "foo".len();
169 /// assert_eq!(3, len);
170 ///
171 /// assert_eq!("ƒoo".len(), 4); // fancy f!
172 /// assert_eq!("ƒoo".chars().count(), 3);
173 /// ```
174 #[stable(feature = "rust1", since = "1.0.0")]
175 #[rustc_const_stable(feature = "const_str_len", since = "1.39.0")]
176 #[rustc_diagnostic_item = "str_len"]
177 #[rustc_no_implicit_autorefs]
178 #[must_use]
179 #[inline]
180 pub const fn len(&self) -> usize {
181 self.as_bytes().len()
182 }
183
184 /// Returns `true` if `self` has a length of zero bytes.
185 ///
186 /// # Examples
187 ///
188 /// ```
189 /// let s = "";
190 /// assert!(s.is_empty());
191 ///
192 /// let s = "not empty";
193 /// assert!(!s.is_empty());
194 /// ```
195 #[stable(feature = "rust1", since = "1.0.0")]
196 #[rustc_const_stable(feature = "const_str_is_empty", since = "1.39.0")]
197 #[rustc_no_implicit_autorefs]
198 #[must_use]
199 #[inline]
200 pub const fn is_empty(&self) -> bool {
201 self.len() == 0
202 }
203
204 /// Converts a slice of bytes to a string slice.
205 ///
206 /// A string slice ([`&str`]) is made of bytes ([`u8`]), and a byte slice
207 /// ([`&[u8]`][byteslice]) is made of bytes, so this function converts between
208 /// the two. Not all byte slices are valid string slices, however: [`&str`] requires
209 /// that it is valid UTF-8. `from_utf8()` checks to ensure that the bytes are valid
210 /// UTF-8, and then does the conversion.
211 ///
212 /// [`&str`]: str
213 /// [byteslice]: prim@slice
214 ///
215 /// If you are sure that the byte slice is valid UTF-8, and you don't want to
216 /// incur the overhead of the validity check, there is an unsafe version of
217 /// this function, [`from_utf8_unchecked`], which has the same
218 /// behavior but skips the check.
219 ///
220 /// If you need a `String` instead of a `&str`, consider
221 /// [`String::from_utf8`][string].
222 ///
223 /// [string]: ../std/string/struct.String.html#method.from_utf8
224 ///
225 /// Because you can stack-allocate a `[u8; N]`, and you can take a
226 /// [`&[u8]`][byteslice] of it, this function is one way to have a
227 /// stack-allocated string. There is an example of this in the
228 /// examples section below.
229 ///
230 /// [byteslice]: slice
231 ///
232 /// # Errors
233 ///
234 /// Returns `Err` if the slice is not UTF-8 with a description as to why the
235 /// provided slice is not UTF-8.
236 ///
237 /// # Examples
238 ///
239 /// Basic usage:
240 ///
241 /// ```
242 /// // some bytes, in a vector
243 /// let sparkle_heart = vec![240, 159, 146, 150];
244 ///
245 /// // We can use the ? (try) operator to check if the bytes are valid
246 /// let sparkle_heart = str::from_utf8(&sparkle_heart)?;
247 ///
248 /// assert_eq!("💖", sparkle_heart);
249 /// # Ok::<_, std::str::Utf8Error>(())
250 /// ```
251 ///
252 /// Incorrect bytes:
253 ///
254 /// ```
255 /// // some invalid bytes, in a vector
256 /// let sparkle_heart = vec![0, 159, 146, 150];
257 ///
258 /// assert!(str::from_utf8(&sparkle_heart).is_err());
259 /// ```
260 ///
261 /// See the docs for [`Utf8Error`] for more details on the kinds of
262 /// errors that can be returned.
263 ///
264 /// A "stack allocated string":
265 ///
266 /// ```
267 /// // some bytes, in a stack-allocated array
268 /// let sparkle_heart = [240, 159, 146, 150];
269 ///
270 /// // We know these bytes are valid, so just use `unwrap()`.
271 /// let sparkle_heart: &str = str::from_utf8(&sparkle_heart).unwrap();
272 ///
273 /// assert_eq!("💖", sparkle_heart);
274 /// ```
275 #[stable(feature = "inherent_str_constructors", since = "1.87.0")]
276 #[rustc_const_stable(feature = "inherent_str_constructors", since = "1.87.0")]
277 #[rustc_diagnostic_item = "str_inherent_from_utf8"]
278 pub const fn from_utf8(v: &[u8]) -> Result<&str, Utf8Error> {
279 converts::from_utf8(v)
280 }
281
282 /// Converts a mutable slice of bytes to a mutable string slice.
283 ///
284 /// # Examples
285 ///
286 /// Basic usage:
287 ///
288 /// ```
289 /// // "Hello, Rust!" as a mutable vector
290 /// let mut hellorust = vec![72, 101, 108, 108, 111, 44, 32, 82, 117, 115, 116, 33];
291 ///
292 /// // As we know these bytes are valid, we can use `unwrap()`
293 /// let outstr = str::from_utf8_mut(&mut hellorust).unwrap();
294 ///
295 /// assert_eq!("Hello, Rust!", outstr);
296 /// ```
297 ///
298 /// Incorrect bytes:
299 ///
300 /// ```
301 /// // Some invalid bytes in a mutable vector
302 /// let mut invalid = vec![128, 223];
303 ///
304 /// assert!(str::from_utf8_mut(&mut invalid).is_err());
305 /// ```
306 /// See the docs for [`Utf8Error`] for more details on the kinds of
307 /// errors that can be returned.
308 #[stable(feature = "inherent_str_constructors", since = "1.87.0")]
309 #[rustc_const_stable(feature = "const_str_from_utf8", since = "1.87.0")]
310 #[rustc_diagnostic_item = "str_inherent_from_utf8_mut"]
311 pub const fn from_utf8_mut(v: &mut [u8]) -> Result<&mut str, Utf8Error> {
312 converts::from_utf8_mut(v)
313 }
314
315 /// Converts a slice of bytes to a string slice without checking
316 /// that the string contains valid UTF-8.
317 ///
318 /// See the safe version, [`from_utf8`], for more information.
319 ///
320 /// # Safety
321 ///
322 /// The bytes passed in must be valid UTF-8.
323 ///
324 /// # Examples
325 ///
326 /// Basic usage:
327 ///
328 /// ```
329 /// // some bytes, in a vector
330 /// let sparkle_heart = vec![240, 159, 146, 150];
331 ///
332 /// let sparkle_heart = unsafe {
333 /// str::from_utf8_unchecked(&sparkle_heart)
334 /// };
335 ///
336 /// assert_eq!("💖", sparkle_heart);
337 /// ```
338 #[inline]
339 #[must_use]
340 #[stable(feature = "inherent_str_constructors", since = "1.87.0")]
341 #[rustc_const_stable(feature = "inherent_str_constructors", since = "1.87.0")]
342 #[rustc_diagnostic_item = "str_inherent_from_utf8_unchecked"]
343 pub const unsafe fn from_utf8_unchecked(v: &[u8]) -> &str {
344 // SAFETY: converts::from_utf8_unchecked has the same safety requirements as this function.
345 unsafe { converts::from_utf8_unchecked(v) }
346 }
347
348 /// Converts a slice of bytes to a string slice without checking
349 /// that the string contains valid UTF-8; mutable version.
350 ///
351 /// See the immutable version, [`from_utf8_unchecked()`] for documentation and safety requirements.
352 ///
353 /// # Examples
354 ///
355 /// Basic usage:
356 ///
357 /// ```
358 /// let mut heart = vec![240, 159, 146, 150];
359 /// let heart = unsafe { str::from_utf8_unchecked_mut(&mut heart) };
360 ///
361 /// assert_eq!("💖", heart);
362 /// ```
363 #[inline]
364 #[must_use]
365 #[stable(feature = "inherent_str_constructors", since = "1.87.0")]
366 #[rustc_const_stable(feature = "inherent_str_constructors", since = "1.87.0")]
367 #[rustc_diagnostic_item = "str_inherent_from_utf8_unchecked_mut"]
368 pub const unsafe fn from_utf8_unchecked_mut(v: &mut [u8]) -> &mut str {
369 // SAFETY: converts::from_utf8_unchecked_mut has the same safety requirements as this function.
370 unsafe { converts::from_utf8_unchecked_mut(v) }
371 }
372
373 /// Checks that `index`-th byte is the first byte in a UTF-8 code point
374 /// sequence or the end of the string.
375 ///
376 /// The start and end of the string (when `index == self.len()`) are
377 /// considered to be boundaries.
378 ///
379 /// Returns `false` if `index` is greater than `self.len()`.
380 ///
381 /// # Examples
382 ///
383 /// ```
384 /// let s = "Löwe 老虎 Léopard";
385 /// assert!(s.is_char_boundary(0));
386 /// // start of `老`
387 /// assert!(s.is_char_boundary(6));
388 /// assert!(s.is_char_boundary(s.len()));
389 ///
390 /// // second byte of `ö`
391 /// assert!(!s.is_char_boundary(2));
392 ///
393 /// // third byte of `老`
394 /// assert!(!s.is_char_boundary(8));
395 /// ```
396 #[must_use]
397 #[stable(feature = "is_char_boundary", since = "1.9.0")]
398 #[rustc_const_stable(feature = "const_is_char_boundary", since = "1.86.0")]
399 #[inline]
400 pub const fn is_char_boundary(&self, index: usize) -> bool {
401 // 0 is always ok.
402 // Test for 0 explicitly so that it can optimize out the check
403 // easily and skip reading string data for that case.
404 // Note that optimizing `self.get(..index)` relies on this.
405 if index == 0 {
406 return true;
407 }
408
409 if index >= self.len() {
410 // For `true` we have two options:
411 //
412 // - index == self.len()
413 // Empty strings are valid, so return true
414 // - index > self.len()
415 // In this case return false
416 //
417 // The check is placed exactly here, because it improves generated
418 // code on higher opt-levels. See PR #84751 for more details.
419 index == self.len()
420 } else {
421 self.as_bytes()[index].is_utf8_char_boundary()
422 }
423 }
424
425 /// Finds the closest `x` not exceeding `index` where [`is_char_boundary(x)`] is `true`.
426 ///
427 /// This method can help you truncate a string so that it's still valid UTF-8, but doesn't
428 /// exceed a given number of bytes. Note that this is done purely at the character level
429 /// and can still visually split graphemes, even though the underlying characters aren't
430 /// split. For example, the emoji 🧑🔬 (scientist) could be split so that the string only
431 /// includes 🧑 (person) instead.
432 ///
433 /// [`is_char_boundary(x)`]: Self::is_char_boundary
434 ///
435 /// # Examples
436 ///
437 /// ```
438 /// let s = "❤️🧡💛💚💙💜";
439 /// assert_eq!(s.len(), 26);
440 /// assert!(!s.is_char_boundary(13));
441 ///
442 /// let closest = s.floor_char_boundary(13);
443 /// assert_eq!(closest, 10);
444 /// assert_eq!(&s[..closest], "❤️🧡");
445 /// ```
446 #[stable(feature = "round_char_boundary", since = "1.91.0")]
447 #[rustc_const_stable(feature = "round_char_boundary", since = "1.91.0")]
448 #[inline]
449 pub const fn floor_char_boundary(&self, index: usize) -> usize {
450 if index >= self.len() {
451 self.len()
452 } else {
453 let mut i = index;
454 while i > 0 {
455 if self.as_bytes()[i].is_utf8_char_boundary() {
456 break;
457 }
458 i -= 1;
459 }
460
461 // The character boundary will be within four bytes of the index
462 debug_assert!(i >= index.saturating_sub(3));
463
464 i
465 }
466 }
467
468 /// Finds the closest `x` not below `index` where [`is_char_boundary(x)`] is `true`.
469 ///
470 /// If `index` is greater than the length of the string, this returns the length of the string.
471 ///
472 /// This method is the natural complement to [`floor_char_boundary`]. See that method
473 /// for more details.
474 ///
475 /// [`floor_char_boundary`]: str::floor_char_boundary
476 /// [`is_char_boundary(x)`]: Self::is_char_boundary
477 ///
478 /// # Examples
479 ///
480 /// ```
481 /// let s = "❤️🧡💛💚💙💜";
482 /// assert_eq!(s.len(), 26);
483 /// assert!(!s.is_char_boundary(13));
484 ///
485 /// let closest = s.ceil_char_boundary(13);
486 /// assert_eq!(closest, 14);
487 /// assert_eq!(&s[..closest], "❤️🧡💛");
488 /// ```
489 #[stable(feature = "round_char_boundary", since = "1.91.0")]
490 #[rustc_const_stable(feature = "round_char_boundary", since = "1.91.0")]
491 #[inline]
492 #[cfg(not(feature = "ferrocene_subset"))]
493 pub const fn ceil_char_boundary(&self, index: usize) -> usize {
494 if index >= self.len() {
495 self.len()
496 } else {
497 let mut i = index;
498 while i < self.len() {
499 if self.as_bytes()[i].is_utf8_char_boundary() {
500 break;
501 }
502 i += 1;
503 }
504
505 // The character boundary will be within four bytes of the index
506 debug_assert!(i <= index + 3);
507
508 i
509 }
510 }
511
512 /// Converts a string slice to a byte slice. To convert the byte slice back
513 /// into a string slice, use the [`from_utf8`] function.
514 ///
515 /// # Examples
516 ///
517 /// ```
518 /// let bytes = "bors".as_bytes();
519 /// assert_eq!(b"bors", bytes);
520 /// ```
521 #[stable(feature = "rust1", since = "1.0.0")]
522 #[rustc_const_stable(feature = "str_as_bytes", since = "1.39.0")]
523 #[must_use]
524 #[inline(always)]
525 #[allow(unused_attributes)]
526 pub const fn as_bytes(&self) -> &[u8] {
527 // SAFETY: const sound because we transmute two types with the same layout
528 unsafe { mem::transmute(self) }
529 }
530
531 /// Converts a mutable string slice to a mutable byte slice.
532 ///
533 /// # Safety
534 ///
535 /// The caller must ensure that the content of the slice is valid UTF-8
536 /// before the borrow ends and the underlying `str` is used.
537 ///
538 /// Use of a `str` whose contents are not valid UTF-8 is undefined behavior.
539 ///
540 /// # Examples
541 ///
542 /// Basic usage:
543 ///
544 /// ```
545 /// let mut s = String::from("Hello");
546 /// let bytes = unsafe { s.as_bytes_mut() };
547 ///
548 /// assert_eq!(b"Hello", bytes);
549 /// ```
550 ///
551 /// Mutability:
552 ///
553 /// ```
554 /// let mut s = String::from("🗻∈🌏");
555 ///
556 /// unsafe {
557 /// let bytes = s.as_bytes_mut();
558 ///
559 /// bytes[0] = 0xF0;
560 /// bytes[1] = 0x9F;
561 /// bytes[2] = 0x8D;
562 /// bytes[3] = 0x94;
563 /// }
564 ///
565 /// assert_eq!("🍔∈🌏", s);
566 /// ```
567 #[stable(feature = "str_mut_extras", since = "1.20.0")]
568 #[rustc_const_stable(feature = "const_str_as_mut", since = "1.83.0")]
569 #[must_use]
570 #[inline(always)]
571 pub const unsafe fn as_bytes_mut(&mut self) -> &mut [u8] {
572 // SAFETY: the cast from `&str` to `&[u8]` is safe since `str`
573 // has the same layout as `&[u8]` (only std can make this guarantee).
574 // The pointer dereference is safe since it comes from a mutable reference which
575 // is guaranteed to be valid for writes.
576 unsafe { &mut *(self as *mut str as *mut [u8]) }
577 }
578
579 /// Converts a string slice to a raw pointer.
580 ///
581 /// As string slices are a slice of bytes, the raw pointer points to a
582 /// [`u8`]. This pointer will be pointing to the first byte of the string
583 /// slice.
584 ///
585 /// The caller must ensure that the returned pointer is never written to.
586 /// If you need to mutate the contents of the string slice, use [`as_mut_ptr`].
587 ///
588 /// [`as_mut_ptr`]: str::as_mut_ptr
589 ///
590 /// # Examples
591 ///
592 /// ```
593 /// let s = "Hello";
594 /// let ptr = s.as_ptr();
595 /// ```
596 #[stable(feature = "rust1", since = "1.0.0")]
597 #[rustc_const_stable(feature = "rustc_str_as_ptr", since = "1.32.0")]
598 #[rustc_never_returns_null_ptr]
599 #[rustc_as_ptr]
600 #[must_use]
601 #[inline(always)]
602 pub const fn as_ptr(&self) -> *const u8 {
603 self as *const str as *const u8
604 }
605
606 /// Converts a mutable string slice to a raw pointer.
607 ///
608 /// As string slices are a slice of bytes, the raw pointer points to a
609 /// [`u8`]. This pointer will be pointing to the first byte of the string
610 /// slice.
611 ///
612 /// It is your responsibility to make sure that the string slice only gets
613 /// modified in a way that it remains valid UTF-8.
614 #[stable(feature = "str_as_mut_ptr", since = "1.36.0")]
615 #[rustc_const_stable(feature = "const_str_as_mut", since = "1.83.0")]
616 #[rustc_never_returns_null_ptr]
617 #[rustc_as_ptr]
618 #[must_use]
619 #[inline(always)]
620 pub const fn as_mut_ptr(&mut self) -> *mut u8 {
621 self as *mut str as *mut u8
622 }
623
624 /// Returns a subslice of `str`.
625 ///
626 /// This is the non-panicking alternative to indexing the `str`. Returns
627 /// [`None`] whenever equivalent indexing operation would panic.
628 ///
629 /// # Examples
630 ///
631 /// ```
632 /// let v = String::from("🗻∈🌏");
633 ///
634 /// assert_eq!(Some("🗻"), v.get(0..4));
635 ///
636 /// // indices not on UTF-8 sequence boundaries
637 /// assert!(v.get(1..).is_none());
638 /// assert!(v.get(..8).is_none());
639 ///
640 /// // out of bounds
641 /// assert!(v.get(..42).is_none());
642 /// ```
643 #[stable(feature = "str_checked_slicing", since = "1.20.0")]
644 #[rustc_const_unstable(feature = "const_index", issue = "143775")]
645 #[inline]
646 #[cfg(not(feature = "ferrocene_subset"))]
647 pub const fn get<I: [const] SliceIndex<str>>(&self, i: I) -> Option<&I::Output> {
648 i.get(self)
649 }
650
651 /// Returns a mutable subslice of `str`.
652 ///
653 /// This is the non-panicking alternative to indexing the `str`. Returns
654 /// [`None`] whenever equivalent indexing operation would panic.
655 ///
656 /// # Examples
657 ///
658 /// ```
659 /// let mut v = String::from("hello");
660 /// // correct length
661 /// assert!(v.get_mut(0..5).is_some());
662 /// // out of bounds
663 /// assert!(v.get_mut(..42).is_none());
664 /// assert_eq!(Some("he"), v.get_mut(0..2).map(|v| &*v));
665 ///
666 /// assert_eq!("hello", v);
667 /// {
668 /// let s = v.get_mut(0..2);
669 /// let s = s.map(|s| {
670 /// s.make_ascii_uppercase();
671 /// &*s
672 /// });
673 /// assert_eq!(Some("HE"), s);
674 /// }
675 /// assert_eq!("HEllo", v);
676 /// ```
677 #[stable(feature = "str_checked_slicing", since = "1.20.0")]
678 #[rustc_const_unstable(feature = "const_index", issue = "143775")]
679 #[inline]
680 #[cfg(not(feature = "ferrocene_subset"))]
681 pub const fn get_mut<I: [const] SliceIndex<str>>(&mut self, i: I) -> Option<&mut I::Output> {
682 i.get_mut(self)
683 }
684
685 /// Returns an unchecked subslice of `str`.
686 ///
687 /// This is the unchecked alternative to indexing the `str`.
688 ///
689 /// # Safety
690 ///
691 /// Callers of this function are responsible that these preconditions are
692 /// satisfied:
693 ///
694 /// * The starting index must not exceed the ending index;
695 /// * Indexes must be within bounds of the original slice;
696 /// * Indexes must lie on UTF-8 sequence boundaries.
697 ///
698 /// Failing that, the returned string slice may reference invalid memory or
699 /// violate the invariants communicated by the `str` type.
700 ///
701 /// # Examples
702 ///
703 /// ```
704 /// let v = "🗻∈🌏";
705 /// unsafe {
706 /// assert_eq!("🗻", v.get_unchecked(0..4));
707 /// assert_eq!("∈", v.get_unchecked(4..7));
708 /// assert_eq!("🌏", v.get_unchecked(7..11));
709 /// }
710 /// ```
711 #[stable(feature = "str_checked_slicing", since = "1.20.0")]
712 #[inline]
713 pub unsafe fn get_unchecked<I: SliceIndex<str>>(&self, i: I) -> &I::Output {
714 // SAFETY: the caller must uphold the safety contract for `get_unchecked`;
715 // the slice is dereferenceable because `self` is a safe reference.
716 // The returned pointer is safe because impls of `SliceIndex` have to guarantee that it is.
717 unsafe { &*i.get_unchecked(self) }
718 }
719
720 /// Returns a mutable, unchecked subslice of `str`.
721 ///
722 /// This is the unchecked alternative to indexing the `str`.
723 ///
724 /// # Safety
725 ///
726 /// Callers of this function are responsible that these preconditions are
727 /// satisfied:
728 ///
729 /// * The starting index must not exceed the ending index;
730 /// * Indexes must be within bounds of the original slice;
731 /// * Indexes must lie on UTF-8 sequence boundaries.
732 ///
733 /// Failing that, the returned string slice may reference invalid memory or
734 /// violate the invariants communicated by the `str` type.
735 ///
736 /// # Examples
737 ///
738 /// ```
739 /// let mut v = String::from("🗻∈🌏");
740 /// unsafe {
741 /// assert_eq!("🗻", v.get_unchecked_mut(0..4));
742 /// assert_eq!("∈", v.get_unchecked_mut(4..7));
743 /// assert_eq!("🌏", v.get_unchecked_mut(7..11));
744 /// }
745 /// ```
746 #[stable(feature = "str_checked_slicing", since = "1.20.0")]
747 #[inline]
748 #[cfg(not(feature = "ferrocene_subset"))]
749 pub unsafe fn get_unchecked_mut<I: SliceIndex<str>>(&mut self, i: I) -> &mut I::Output {
750 // SAFETY: the caller must uphold the safety contract for `get_unchecked_mut`;
751 // the slice is dereferenceable because `self` is a safe reference.
752 // The returned pointer is safe because impls of `SliceIndex` have to guarantee that it is.
753 unsafe { &mut *i.get_unchecked_mut(self) }
754 }
755
756 /// Creates a string slice from another string slice, bypassing safety
757 /// checks.
758 ///
759 /// This is generally not recommended, use with caution! For a safe
760 /// alternative see [`str`] and [`Index`].
761 ///
762 /// [`Index`]: crate::ops::Index
763 ///
764 /// This new slice goes from `begin` to `end`, including `begin` but
765 /// excluding `end`.
766 ///
767 /// To get a mutable string slice instead, see the
768 /// [`slice_mut_unchecked`] method.
769 ///
770 /// [`slice_mut_unchecked`]: str::slice_mut_unchecked
771 ///
772 /// # Safety
773 ///
774 /// Callers of this function are responsible that three preconditions are
775 /// satisfied:
776 ///
777 /// * `begin` must not exceed `end`.
778 /// * `begin` and `end` must be byte positions within the string slice.
779 /// * `begin` and `end` must lie on UTF-8 sequence boundaries.
780 ///
781 /// # Examples
782 ///
783 /// ```
784 /// let s = "Löwe 老虎 Léopard";
785 ///
786 /// unsafe {
787 /// assert_eq!("Löwe 老虎 Léopard", s.slice_unchecked(0, 21));
788 /// }
789 ///
790 /// let s = "Hello, world!";
791 ///
792 /// unsafe {
793 /// assert_eq!("world", s.slice_unchecked(7, 12));
794 /// }
795 /// ```
796 #[stable(feature = "rust1", since = "1.0.0")]
797 #[deprecated(since = "1.29.0", note = "use `get_unchecked(begin..end)` instead")]
798 #[must_use]
799 #[inline]
800 #[cfg(not(feature = "ferrocene_subset"))]
801 pub unsafe fn slice_unchecked(&self, begin: usize, end: usize) -> &str {
802 // SAFETY: the caller must uphold the safety contract for `get_unchecked`;
803 // the slice is dereferenceable because `self` is a safe reference.
804 // The returned pointer is safe because impls of `SliceIndex` have to guarantee that it is.
805 unsafe { &*(begin..end).get_unchecked(self) }
806 }
807
808 /// Creates a string slice from another string slice, bypassing safety
809 /// checks.
810 ///
811 /// This is generally not recommended, use with caution! For a safe
812 /// alternative see [`str`] and [`IndexMut`].
813 ///
814 /// [`IndexMut`]: crate::ops::IndexMut
815 ///
816 /// This new slice goes from `begin` to `end`, including `begin` but
817 /// excluding `end`.
818 ///
819 /// To get an immutable string slice instead, see the
820 /// [`slice_unchecked`] method.
821 ///
822 /// [`slice_unchecked`]: str::slice_unchecked
823 ///
824 /// # Safety
825 ///
826 /// Callers of this function are responsible that three preconditions are
827 /// satisfied:
828 ///
829 /// * `begin` must not exceed `end`.
830 /// * `begin` and `end` must be byte positions within the string slice.
831 /// * `begin` and `end` must lie on UTF-8 sequence boundaries.
832 #[stable(feature = "str_slice_mut", since = "1.5.0")]
833 #[deprecated(since = "1.29.0", note = "use `get_unchecked_mut(begin..end)` instead")]
834 #[inline]
835 #[cfg(not(feature = "ferrocene_subset"))]
836 pub unsafe fn slice_mut_unchecked(&mut self, begin: usize, end: usize) -> &mut str {
837 // SAFETY: the caller must uphold the safety contract for `get_unchecked_mut`;
838 // the slice is dereferenceable because `self` is a safe reference.
839 // The returned pointer is safe because impls of `SliceIndex` have to guarantee that it is.
840 unsafe { &mut *(begin..end).get_unchecked_mut(self) }
841 }
842
843 /// Divides one string slice into two at an index.
844 ///
845 /// The argument, `mid`, should be a byte offset from the start of the
846 /// string. It must also be on the boundary of a UTF-8 code point.
847 ///
848 /// The two slices returned go from the start of the string slice to `mid`,
849 /// and from `mid` to the end of the string slice.
850 ///
851 /// To get mutable string slices instead, see the [`split_at_mut`]
852 /// method.
853 ///
854 /// [`split_at_mut`]: str::split_at_mut
855 ///
856 /// # Panics
857 ///
858 /// Panics if `mid` is not on a UTF-8 code point boundary, or if it is past
859 /// the end of the last code point of the string slice. For a non-panicking
860 /// alternative see [`split_at_checked`](str::split_at_checked).
861 ///
862 /// # Examples
863 ///
864 /// ```
865 /// let s = "Per Martin-Löf";
866 ///
867 /// let (first, last) = s.split_at(3);
868 ///
869 /// assert_eq!("Per", first);
870 /// assert_eq!(" Martin-Löf", last);
871 /// ```
872 #[inline]
873 #[must_use]
874 #[stable(feature = "str_split_at", since = "1.4.0")]
875 #[rustc_const_stable(feature = "const_str_split_at", since = "1.86.0")]
876 #[cfg(not(feature = "ferrocene_subset"))]
877 pub const fn split_at(&self, mid: usize) -> (&str, &str) {
878 match self.split_at_checked(mid) {
879 None => slice_error_fail(self, 0, mid),
880 Some(pair) => pair,
881 }
882 }
883
884 /// Divides one mutable string slice into two at an index.
885 ///
886 /// The argument, `mid`, should be a byte offset from the start of the
887 /// string. It must also be on the boundary of a UTF-8 code point.
888 ///
889 /// The two slices returned go from the start of the string slice to `mid`,
890 /// and from `mid` to the end of the string slice.
891 ///
892 /// To get immutable string slices instead, see the [`split_at`] method.
893 ///
894 /// [`split_at`]: str::split_at
895 ///
896 /// # Panics
897 ///
898 /// Panics if `mid` is not on a UTF-8 code point boundary, or if it is past
899 /// the end of the last code point of the string slice. For a non-panicking
900 /// alternative see [`split_at_mut_checked`](str::split_at_mut_checked).
901 ///
902 /// # Examples
903 ///
904 /// ```
905 /// let mut s = "Per Martin-Löf".to_string();
906 /// {
907 /// let (first, last) = s.split_at_mut(3);
908 /// first.make_ascii_uppercase();
909 /// assert_eq!("PER", first);
910 /// assert_eq!(" Martin-Löf", last);
911 /// }
912 /// assert_eq!("PER Martin-Löf", s);
913 /// ```
914 #[inline]
915 #[must_use]
916 #[stable(feature = "str_split_at", since = "1.4.0")]
917 #[rustc_const_stable(feature = "const_str_split_at", since = "1.86.0")]
918 #[cfg(not(feature = "ferrocene_subset"))]
919 pub const fn split_at_mut(&mut self, mid: usize) -> (&mut str, &mut str) {
920 // is_char_boundary checks that the index is in [0, .len()]
921 if self.is_char_boundary(mid) {
922 // SAFETY: just checked that `mid` is on a char boundary.
923 unsafe { self.split_at_mut_unchecked(mid) }
924 } else {
925 slice_error_fail(self, 0, mid)
926 }
927 }
928
929 /// Divides one string slice into two at an index.
930 ///
931 /// The argument, `mid`, should be a valid byte offset from the start of the
932 /// string. It must also be on the boundary of a UTF-8 code point. The
933 /// method returns `None` if that’s not the case.
934 ///
935 /// The two slices returned go from the start of the string slice to `mid`,
936 /// and from `mid` to the end of the string slice.
937 ///
938 /// To get mutable string slices instead, see the [`split_at_mut_checked`]
939 /// method.
940 ///
941 /// [`split_at_mut_checked`]: str::split_at_mut_checked
942 ///
943 /// # Examples
944 ///
945 /// ```
946 /// let s = "Per Martin-Löf";
947 ///
948 /// let (first, last) = s.split_at_checked(3).unwrap();
949 /// assert_eq!("Per", first);
950 /// assert_eq!(" Martin-Löf", last);
951 ///
952 /// assert_eq!(None, s.split_at_checked(13)); // Inside “ö”
953 /// assert_eq!(None, s.split_at_checked(16)); // Beyond the string length
954 /// ```
955 #[inline]
956 #[must_use]
957 #[stable(feature = "split_at_checked", since = "1.80.0")]
958 #[rustc_const_stable(feature = "const_str_split_at", since = "1.86.0")]
959 #[cfg(not(feature = "ferrocene_subset"))]
960 pub const fn split_at_checked(&self, mid: usize) -> Option<(&str, &str)> {
961 // is_char_boundary checks that the index is in [0, .len()]
962 if self.is_char_boundary(mid) {
963 // SAFETY: just checked that `mid` is on a char boundary.
964 Some(unsafe { self.split_at_unchecked(mid) })
965 } else {
966 None
967 }
968 }
969
970 /// Divides one mutable string slice into two at an index.
971 ///
972 /// The argument, `mid`, should be a valid byte offset from the start of the
973 /// string. It must also be on the boundary of a UTF-8 code point. The
974 /// method returns `None` if that’s not the case.
975 ///
976 /// The two slices returned go from the start of the string slice to `mid`,
977 /// and from `mid` to the end of the string slice.
978 ///
979 /// To get immutable string slices instead, see the [`split_at_checked`] method.
980 ///
981 /// [`split_at_checked`]: str::split_at_checked
982 ///
983 /// # Examples
984 ///
985 /// ```
986 /// let mut s = "Per Martin-Löf".to_string();
987 /// if let Some((first, last)) = s.split_at_mut_checked(3) {
988 /// first.make_ascii_uppercase();
989 /// assert_eq!("PER", first);
990 /// assert_eq!(" Martin-Löf", last);
991 /// }
992 /// assert_eq!("PER Martin-Löf", s);
993 ///
994 /// assert_eq!(None, s.split_at_mut_checked(13)); // Inside “ö”
995 /// assert_eq!(None, s.split_at_mut_checked(16)); // Beyond the string length
996 /// ```
997 #[inline]
998 #[must_use]
999 #[stable(feature = "split_at_checked", since = "1.80.0")]
1000 #[rustc_const_stable(feature = "const_str_split_at", since = "1.86.0")]
1001 #[cfg(not(feature = "ferrocene_subset"))]
1002 pub const fn split_at_mut_checked(&mut self, mid: usize) -> Option<(&mut str, &mut str)> {
1003 // is_char_boundary checks that the index is in [0, .len()]
1004 if self.is_char_boundary(mid) {
1005 // SAFETY: just checked that `mid` is on a char boundary.
1006 Some(unsafe { self.split_at_mut_unchecked(mid) })
1007 } else {
1008 None
1009 }
1010 }
1011
1012 /// Divides one string slice into two at an index.
1013 ///
1014 /// # Safety
1015 ///
1016 /// The caller must ensure that `mid` is a valid byte offset from the start
1017 /// of the string and falls on the boundary of a UTF-8 code point.
1018 #[inline]
1019 #[cfg(not(feature = "ferrocene_subset"))]
1020 const unsafe fn split_at_unchecked(&self, mid: usize) -> (&str, &str) {
1021 let len = self.len();
1022 let ptr = self.as_ptr();
1023 // SAFETY: caller guarantees `mid` is on a char boundary.
1024 unsafe {
1025 (
1026 from_utf8_unchecked(slice::from_raw_parts(ptr, mid)),
1027 from_utf8_unchecked(slice::from_raw_parts(ptr.add(mid), len - mid)),
1028 )
1029 }
1030 }
1031
1032 /// Divides one string slice into two at an index.
1033 ///
1034 /// # Safety
1035 ///
1036 /// The caller must ensure that `mid` is a valid byte offset from the start
1037 /// of the string and falls on the boundary of a UTF-8 code point.
1038 #[cfg(not(feature = "ferrocene_subset"))]
1039 const unsafe fn split_at_mut_unchecked(&mut self, mid: usize) -> (&mut str, &mut str) {
1040 let len = self.len();
1041 let ptr = self.as_mut_ptr();
1042 // SAFETY: caller guarantees `mid` is on a char boundary.
1043 unsafe {
1044 (
1045 from_utf8_unchecked_mut(slice::from_raw_parts_mut(ptr, mid)),
1046 from_utf8_unchecked_mut(slice::from_raw_parts_mut(ptr.add(mid), len - mid)),
1047 )
1048 }
1049 }
1050
1051 /// Returns an iterator over the [`char`]s of a string slice.
1052 ///
1053 /// As a string slice consists of valid UTF-8, we can iterate through a
1054 /// string slice by [`char`]. This method returns such an iterator.
1055 ///
1056 /// It's important to remember that [`char`] represents a Unicode Scalar
1057 /// Value, and might not match your idea of what a 'character' is. Iteration
1058 /// over grapheme clusters may be what you actually want. This functionality
1059 /// is not provided by Rust's standard library, check crates.io instead.
1060 ///
1061 /// # Examples
1062 ///
1063 /// Basic usage:
1064 ///
1065 /// ```
1066 /// let word = "goodbye";
1067 ///
1068 /// let count = word.chars().count();
1069 /// assert_eq!(7, count);
1070 ///
1071 /// let mut chars = word.chars();
1072 ///
1073 /// assert_eq!(Some('g'), chars.next());
1074 /// assert_eq!(Some('o'), chars.next());
1075 /// assert_eq!(Some('o'), chars.next());
1076 /// assert_eq!(Some('d'), chars.next());
1077 /// assert_eq!(Some('b'), chars.next());
1078 /// assert_eq!(Some('y'), chars.next());
1079 /// assert_eq!(Some('e'), chars.next());
1080 ///
1081 /// assert_eq!(None, chars.next());
1082 /// ```
1083 ///
1084 /// Remember, [`char`]s might not match your intuition about characters:
1085 ///
1086 /// [`char`]: prim@char
1087 ///
1088 /// ```
1089 /// let y = "y̆";
1090 ///
1091 /// let mut chars = y.chars();
1092 ///
1093 /// assert_eq!(Some('y'), chars.next()); // not 'y̆'
1094 /// assert_eq!(Some('\u{0306}'), chars.next());
1095 ///
1096 /// assert_eq!(None, chars.next());
1097 /// ```
1098 #[stable(feature = "rust1", since = "1.0.0")]
1099 #[inline]
1100 #[rustc_diagnostic_item = "str_chars"]
1101 pub fn chars(&self) -> Chars<'_> {
1102 Chars { iter: self.as_bytes().iter() }
1103 }
1104
1105 /// Returns an iterator over the [`char`]s of a string slice, and their
1106 /// positions.
1107 ///
1108 /// As a string slice consists of valid UTF-8, we can iterate through a
1109 /// string slice by [`char`]. This method returns an iterator of both
1110 /// these [`char`]s, as well as their byte positions.
1111 ///
1112 /// The iterator yields tuples. The position is first, the [`char`] is
1113 /// second.
1114 ///
1115 /// # Examples
1116 ///
1117 /// Basic usage:
1118 ///
1119 /// ```
1120 /// let word = "goodbye";
1121 ///
1122 /// let count = word.char_indices().count();
1123 /// assert_eq!(7, count);
1124 ///
1125 /// let mut char_indices = word.char_indices();
1126 ///
1127 /// assert_eq!(Some((0, 'g')), char_indices.next());
1128 /// assert_eq!(Some((1, 'o')), char_indices.next());
1129 /// assert_eq!(Some((2, 'o')), char_indices.next());
1130 /// assert_eq!(Some((3, 'd')), char_indices.next());
1131 /// assert_eq!(Some((4, 'b')), char_indices.next());
1132 /// assert_eq!(Some((5, 'y')), char_indices.next());
1133 /// assert_eq!(Some((6, 'e')), char_indices.next());
1134 ///
1135 /// assert_eq!(None, char_indices.next());
1136 /// ```
1137 ///
1138 /// Remember, [`char`]s might not match your intuition about characters:
1139 ///
1140 /// [`char`]: prim@char
1141 ///
1142 /// ```
1143 /// let yes = "y̆es";
1144 ///
1145 /// let mut char_indices = yes.char_indices();
1146 ///
1147 /// assert_eq!(Some((0, 'y')), char_indices.next()); // not (0, 'y̆')
1148 /// assert_eq!(Some((1, '\u{0306}')), char_indices.next());
1149 ///
1150 /// // note the 3 here - the previous character took up two bytes
1151 /// assert_eq!(Some((3, 'e')), char_indices.next());
1152 /// assert_eq!(Some((4, 's')), char_indices.next());
1153 ///
1154 /// assert_eq!(None, char_indices.next());
1155 /// ```
1156 #[stable(feature = "rust1", since = "1.0.0")]
1157 #[inline]
1158 #[cfg(not(feature = "ferrocene_subset"))]
1159 pub fn char_indices(&self) -> CharIndices<'_> {
1160 CharIndices { front_offset: 0, iter: self.chars() }
1161 }
1162
1163 /// Returns an iterator over the bytes of a string slice.
1164 ///
1165 /// As a string slice consists of a sequence of bytes, we can iterate
1166 /// through a string slice by byte. This method returns such an iterator.
1167 ///
1168 /// # Examples
1169 ///
1170 /// ```
1171 /// let mut bytes = "bors".bytes();
1172 ///
1173 /// assert_eq!(Some(b'b'), bytes.next());
1174 /// assert_eq!(Some(b'o'), bytes.next());
1175 /// assert_eq!(Some(b'r'), bytes.next());
1176 /// assert_eq!(Some(b's'), bytes.next());
1177 ///
1178 /// assert_eq!(None, bytes.next());
1179 /// ```
1180 #[stable(feature = "rust1", since = "1.0.0")]
1181 #[inline]
1182 pub fn bytes(&self) -> Bytes<'_> {
1183 Bytes(self.as_bytes().iter().copied())
1184 }
1185
1186 /// Splits a string slice by whitespace.
1187 ///
1188 /// The iterator returned will return string slices that are sub-slices of
1189 /// the original string slice, separated by any amount of whitespace.
1190 ///
1191 /// 'Whitespace' is defined according to the terms of the Unicode Derived
1192 /// Core Property `White_Space`. If you only want to split on ASCII whitespace
1193 /// instead, use [`split_ascii_whitespace`].
1194 ///
1195 /// [`split_ascii_whitespace`]: str::split_ascii_whitespace
1196 ///
1197 /// # Examples
1198 ///
1199 /// Basic usage:
1200 ///
1201 /// ```
1202 /// let mut iter = "A few words".split_whitespace();
1203 ///
1204 /// assert_eq!(Some("A"), iter.next());
1205 /// assert_eq!(Some("few"), iter.next());
1206 /// assert_eq!(Some("words"), iter.next());
1207 ///
1208 /// assert_eq!(None, iter.next());
1209 /// ```
1210 ///
1211 /// All kinds of whitespace are considered:
1212 ///
1213 /// ```
1214 /// let mut iter = " Mary had\ta\u{2009}little \n\t lamb".split_whitespace();
1215 /// assert_eq!(Some("Mary"), iter.next());
1216 /// assert_eq!(Some("had"), iter.next());
1217 /// assert_eq!(Some("a"), iter.next());
1218 /// assert_eq!(Some("little"), iter.next());
1219 /// assert_eq!(Some("lamb"), iter.next());
1220 ///
1221 /// assert_eq!(None, iter.next());
1222 /// ```
1223 ///
1224 /// If the string is empty or all whitespace, the iterator yields no string slices:
1225 /// ```
1226 /// assert_eq!("".split_whitespace().next(), None);
1227 /// assert_eq!(" ".split_whitespace().next(), None);
1228 /// ```
1229 #[must_use = "this returns the split string as an iterator, \
1230 without modifying the original"]
1231 #[stable(feature = "split_whitespace", since = "1.1.0")]
1232 #[rustc_diagnostic_item = "str_split_whitespace"]
1233 #[inline]
1234 #[cfg(not(feature = "ferrocene_subset"))]
1235 pub fn split_whitespace(&self) -> SplitWhitespace<'_> {
1236 SplitWhitespace { inner: self.split(IsWhitespace).filter(IsNotEmpty) }
1237 }
1238
1239 /// Splits a string slice by ASCII whitespace.
1240 ///
1241 /// The iterator returned will return string slices that are sub-slices of
1242 /// the original string slice, separated by any amount of ASCII whitespace.
1243 ///
1244 /// This uses the same definition as [`char::is_ascii_whitespace`].
1245 /// To split by Unicode `Whitespace` instead, use [`split_whitespace`].
1246 ///
1247 /// [`split_whitespace`]: str::split_whitespace
1248 ///
1249 /// # Examples
1250 ///
1251 /// Basic usage:
1252 ///
1253 /// ```
1254 /// let mut iter = "A few words".split_ascii_whitespace();
1255 ///
1256 /// assert_eq!(Some("A"), iter.next());
1257 /// assert_eq!(Some("few"), iter.next());
1258 /// assert_eq!(Some("words"), iter.next());
1259 ///
1260 /// assert_eq!(None, iter.next());
1261 /// ```
1262 ///
1263 /// Various kinds of ASCII whitespace are considered
1264 /// (see [`char::is_ascii_whitespace`]):
1265 ///
1266 /// ```
1267 /// let mut iter = " Mary had\ta little \n\t lamb".split_ascii_whitespace();
1268 /// assert_eq!(Some("Mary"), iter.next());
1269 /// assert_eq!(Some("had"), iter.next());
1270 /// assert_eq!(Some("a"), iter.next());
1271 /// assert_eq!(Some("little"), iter.next());
1272 /// assert_eq!(Some("lamb"), iter.next());
1273 ///
1274 /// assert_eq!(None, iter.next());
1275 /// ```
1276 ///
1277 /// If the string is empty or all ASCII whitespace, the iterator yields no string slices:
1278 /// ```
1279 /// assert_eq!("".split_ascii_whitespace().next(), None);
1280 /// assert_eq!(" ".split_ascii_whitespace().next(), None);
1281 /// ```
1282 #[must_use = "this returns the split string as an iterator, \
1283 without modifying the original"]
1284 #[stable(feature = "split_ascii_whitespace", since = "1.34.0")]
1285 #[inline]
1286 #[cfg(not(feature = "ferrocene_subset"))]
1287 pub fn split_ascii_whitespace(&self) -> SplitAsciiWhitespace<'_> {
1288 let inner =
1289 self.as_bytes().split(IsAsciiWhitespace).filter(BytesIsNotEmpty).map(UnsafeBytesToStr);
1290 SplitAsciiWhitespace { inner }
1291 }
1292
1293 /// Returns an iterator over the lines of a string, as string slices.
1294 ///
1295 /// Lines are split at line endings that are either newlines (`\n`) or
1296 /// sequences of a carriage return followed by a line feed (`\r\n`).
1297 ///
1298 /// Line terminators are not included in the lines returned by the iterator.
1299 ///
1300 /// Note that any carriage return (`\r`) not immediately followed by a
1301 /// line feed (`\n`) does not split a line. These carriage returns are
1302 /// thereby included in the produced lines.
1303 ///
1304 /// The final line ending is optional. A string that ends with a final line
1305 /// ending will return the same lines as an otherwise identical string
1306 /// without a final line ending.
1307 ///
1308 /// An empty string returns an empty iterator.
1309 ///
1310 /// # Examples
1311 ///
1312 /// Basic usage:
1313 ///
1314 /// ```
1315 /// let text = "foo\r\nbar\n\nbaz\r";
1316 /// let mut lines = text.lines();
1317 ///
1318 /// assert_eq!(Some("foo"), lines.next());
1319 /// assert_eq!(Some("bar"), lines.next());
1320 /// assert_eq!(Some(""), lines.next());
1321 /// // Trailing carriage return is included in the last line
1322 /// assert_eq!(Some("baz\r"), lines.next());
1323 ///
1324 /// assert_eq!(None, lines.next());
1325 /// ```
1326 ///
1327 /// The final line does not require any ending:
1328 ///
1329 /// ```
1330 /// let text = "foo\nbar\n\r\nbaz";
1331 /// let mut lines = text.lines();
1332 ///
1333 /// assert_eq!(Some("foo"), lines.next());
1334 /// assert_eq!(Some("bar"), lines.next());
1335 /// assert_eq!(Some(""), lines.next());
1336 /// assert_eq!(Some("baz"), lines.next());
1337 ///
1338 /// assert_eq!(None, lines.next());
1339 /// ```
1340 ///
1341 /// An empty string returns an empty iterator:
1342 ///
1343 /// ```
1344 /// let text = "";
1345 /// let mut lines = text.lines();
1346 ///
1347 /// assert_eq!(lines.next(), None);
1348 /// ```
1349 #[stable(feature = "rust1", since = "1.0.0")]
1350 #[inline]
1351 #[cfg(not(feature = "ferrocene_subset"))]
1352 pub fn lines(&self) -> Lines<'_> {
1353 Lines(self.split_inclusive('\n').map(LinesMap))
1354 }
1355
1356 /// Returns an iterator over the lines of a string.
1357 #[stable(feature = "rust1", since = "1.0.0")]
1358 #[deprecated(since = "1.4.0", note = "use lines() instead now", suggestion = "lines")]
1359 #[inline]
1360 #[allow(deprecated)]
1361 #[cfg(not(feature = "ferrocene_subset"))]
1362 pub fn lines_any(&self) -> LinesAny<'_> {
1363 LinesAny(self.lines())
1364 }
1365
1366 /// Returns an iterator of `u16` over the string encoded
1367 /// as native endian UTF-16 (without byte-order mark).
1368 ///
1369 /// # Examples
1370 ///
1371 /// ```
1372 /// let text = "Zażółć gęślą jaźń";
1373 ///
1374 /// let utf8_len = text.len();
1375 /// let utf16_len = text.encode_utf16().count();
1376 ///
1377 /// assert!(utf16_len <= utf8_len);
1378 /// ```
1379 #[must_use = "this returns the encoded string as an iterator, \
1380 without modifying the original"]
1381 #[stable(feature = "encode_utf16", since = "1.8.0")]
1382 #[cfg(not(feature = "ferrocene_subset"))]
1383 pub fn encode_utf16(&self) -> EncodeUtf16<'_> {
1384 EncodeUtf16 { chars: self.chars(), extra: 0 }
1385 }
1386
1387 /// Returns `true` if the given pattern matches a sub-slice of
1388 /// this string slice.
1389 ///
1390 /// Returns `false` if it does not.
1391 ///
1392 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
1393 /// function or closure that determines if a character matches.
1394 ///
1395 /// [`char`]: prim@char
1396 /// [pattern]: self::pattern
1397 ///
1398 /// # Examples
1399 ///
1400 /// ```
1401 /// let bananas = "bananas";
1402 ///
1403 /// assert!(bananas.contains("nana"));
1404 /// assert!(!bananas.contains("apples"));
1405 /// ```
1406 #[stable(feature = "rust1", since = "1.0.0")]
1407 #[inline]
1408 #[cfg(not(feature = "ferrocene_subset"))]
1409 pub fn contains<P: Pattern>(&self, pat: P) -> bool {
1410 pat.is_contained_in(self)
1411 }
1412
1413 /// Returns `true` if the given pattern matches a prefix of this
1414 /// string slice.
1415 ///
1416 /// Returns `false` if it does not.
1417 ///
1418 /// The [pattern] can be a `&str`, in which case this function will return true if
1419 /// the `&str` is a prefix of this string slice.
1420 ///
1421 /// The [pattern] can also be a [`char`], a slice of [`char`]s, or a
1422 /// function or closure that determines if a character matches.
1423 /// These will only be checked against the first character of this string slice.
1424 /// Look at the second example below regarding behavior for slices of [`char`]s.
1425 ///
1426 /// [`char`]: prim@char
1427 /// [pattern]: self::pattern
1428 ///
1429 /// # Examples
1430 ///
1431 /// ```
1432 /// let bananas = "bananas";
1433 ///
1434 /// assert!(bananas.starts_with("bana"));
1435 /// assert!(!bananas.starts_with("nana"));
1436 /// ```
1437 ///
1438 /// ```
1439 /// let bananas = "bananas";
1440 ///
1441 /// // Note that both of these assert successfully.
1442 /// assert!(bananas.starts_with(&['b', 'a', 'n', 'a']));
1443 /// assert!(bananas.starts_with(&['a', 'b', 'c', 'd']));
1444 /// ```
1445 #[stable(feature = "rust1", since = "1.0.0")]
1446 #[rustc_diagnostic_item = "str_starts_with"]
1447 pub fn starts_with<P: Pattern>(&self, pat: P) -> bool {
1448 pat.is_prefix_of(self)
1449 }
1450
1451 /// Returns `true` if the given pattern matches a suffix of this
1452 /// string slice.
1453 ///
1454 /// Returns `false` if it does not.
1455 ///
1456 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
1457 /// function or closure that determines if a character matches.
1458 ///
1459 /// [`char`]: prim@char
1460 /// [pattern]: self::pattern
1461 ///
1462 /// # Examples
1463 ///
1464 /// ```
1465 /// let bananas = "bananas";
1466 ///
1467 /// assert!(bananas.ends_with("anas"));
1468 /// assert!(!bananas.ends_with("nana"));
1469 /// ```
1470 #[stable(feature = "rust1", since = "1.0.0")]
1471 #[rustc_diagnostic_item = "str_ends_with"]
1472 #[cfg(not(feature = "ferrocene_subset"))]
1473 pub fn ends_with<P: Pattern>(&self, pat: P) -> bool
1474 where
1475 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
1476 {
1477 pat.is_suffix_of(self)
1478 }
1479
1480 /// Returns the byte index of the first character of this string slice that
1481 /// matches the pattern.
1482 ///
1483 /// Returns [`None`] if the pattern doesn't match.
1484 ///
1485 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
1486 /// function or closure that determines if a character matches.
1487 ///
1488 /// [`char`]: prim@char
1489 /// [pattern]: self::pattern
1490 ///
1491 /// # Examples
1492 ///
1493 /// Simple patterns:
1494 ///
1495 /// ```
1496 /// let s = "Löwe 老虎 Léopard Gepardi";
1497 ///
1498 /// assert_eq!(s.find('L'), Some(0));
1499 /// assert_eq!(s.find('é'), Some(14));
1500 /// assert_eq!(s.find("pard"), Some(17));
1501 /// ```
1502 ///
1503 /// More complex patterns using point-free style and closures:
1504 ///
1505 /// ```
1506 /// let s = "Löwe 老虎 Léopard";
1507 ///
1508 /// assert_eq!(s.find(char::is_whitespace), Some(5));
1509 /// assert_eq!(s.find(char::is_lowercase), Some(1));
1510 /// assert_eq!(s.find(|c: char| c.is_whitespace() || c.is_lowercase()), Some(1));
1511 /// assert_eq!(s.find(|c: char| (c < 'o') && (c > 'a')), Some(4));
1512 /// ```
1513 ///
1514 /// Not finding the pattern:
1515 ///
1516 /// ```
1517 /// let s = "Löwe 老虎 Léopard";
1518 /// let x: &[_] = &['1', '2'];
1519 ///
1520 /// assert_eq!(s.find(x), None);
1521 /// ```
1522 #[stable(feature = "rust1", since = "1.0.0")]
1523 #[inline]
1524 #[cfg(not(feature = "ferrocene_subset"))]
1525 pub fn find<P: Pattern>(&self, pat: P) -> Option<usize> {
1526 pat.into_searcher(self).next_match().map(|(i, _)| i)
1527 }
1528
1529 /// Returns the byte index for the first character of the last match of the pattern in
1530 /// this string slice.
1531 ///
1532 /// Returns [`None`] if the pattern doesn't match.
1533 ///
1534 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
1535 /// function or closure that determines if a character matches.
1536 ///
1537 /// [`char`]: prim@char
1538 /// [pattern]: self::pattern
1539 ///
1540 /// # Examples
1541 ///
1542 /// Simple patterns:
1543 ///
1544 /// ```
1545 /// let s = "Löwe 老虎 Léopard Gepardi";
1546 ///
1547 /// assert_eq!(s.rfind('L'), Some(13));
1548 /// assert_eq!(s.rfind('é'), Some(14));
1549 /// assert_eq!(s.rfind("pard"), Some(24));
1550 /// ```
1551 ///
1552 /// More complex patterns with closures:
1553 ///
1554 /// ```
1555 /// let s = "Löwe 老虎 Léopard";
1556 ///
1557 /// assert_eq!(s.rfind(char::is_whitespace), Some(12));
1558 /// assert_eq!(s.rfind(char::is_lowercase), Some(20));
1559 /// ```
1560 ///
1561 /// Not finding the pattern:
1562 ///
1563 /// ```
1564 /// let s = "Löwe 老虎 Léopard";
1565 /// let x: &[_] = &['1', '2'];
1566 ///
1567 /// assert_eq!(s.rfind(x), None);
1568 /// ```
1569 #[stable(feature = "rust1", since = "1.0.0")]
1570 #[inline]
1571 #[cfg(not(feature = "ferrocene_subset"))]
1572 pub fn rfind<P: Pattern>(&self, pat: P) -> Option<usize>
1573 where
1574 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
1575 {
1576 pat.into_searcher(self).next_match_back().map(|(i, _)| i)
1577 }
1578
1579 /// Returns an iterator over substrings of this string slice, separated by
1580 /// characters matched by a pattern.
1581 ///
1582 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
1583 /// function or closure that determines if a character matches.
1584 ///
1585 /// If there are no matches the full string slice is returned as the only
1586 /// item in the iterator.
1587 ///
1588 /// [`char`]: prim@char
1589 /// [pattern]: self::pattern
1590 ///
1591 /// # Iterator behavior
1592 ///
1593 /// The returned iterator will be a [`DoubleEndedIterator`] if the pattern
1594 /// allows a reverse search and forward/reverse search yields the same
1595 /// elements. This is true for, e.g., [`char`], but not for `&str`.
1596 ///
1597 /// If the pattern allows a reverse search but its results might differ
1598 /// from a forward search, the [`rsplit`] method can be used.
1599 ///
1600 /// [`rsplit`]: str::rsplit
1601 ///
1602 /// # Examples
1603 ///
1604 /// Simple patterns:
1605 ///
1606 /// ```
1607 /// let v: Vec<&str> = "Mary had a little lamb".split(' ').collect();
1608 /// assert_eq!(v, ["Mary", "had", "a", "little", "lamb"]);
1609 ///
1610 /// let v: Vec<&str> = "".split('X').collect();
1611 /// assert_eq!(v, [""]);
1612 ///
1613 /// let v: Vec<&str> = "lionXXtigerXleopard".split('X').collect();
1614 /// assert_eq!(v, ["lion", "", "tiger", "leopard"]);
1615 ///
1616 /// let v: Vec<&str> = "lion::tiger::leopard".split("::").collect();
1617 /// assert_eq!(v, ["lion", "tiger", "leopard"]);
1618 ///
1619 /// let v: Vec<&str> = "AABBCC".split("DD").collect();
1620 /// assert_eq!(v, ["AABBCC"]);
1621 ///
1622 /// let v: Vec<&str> = "abc1def2ghi".split(char::is_numeric).collect();
1623 /// assert_eq!(v, ["abc", "def", "ghi"]);
1624 ///
1625 /// let v: Vec<&str> = "lionXtigerXleopard".split(char::is_uppercase).collect();
1626 /// assert_eq!(v, ["lion", "tiger", "leopard"]);
1627 /// ```
1628 ///
1629 /// If the pattern is a slice of chars, split on each occurrence of any of the characters:
1630 ///
1631 /// ```
1632 /// let v: Vec<&str> = "2020-11-03 23:59".split(&['-', ' ', ':', '@'][..]).collect();
1633 /// assert_eq!(v, ["2020", "11", "03", "23", "59"]);
1634 /// ```
1635 ///
1636 /// A more complex pattern, using a closure:
1637 ///
1638 /// ```
1639 /// let v: Vec<&str> = "abc1defXghi".split(|c| c == '1' || c == 'X').collect();
1640 /// assert_eq!(v, ["abc", "def", "ghi"]);
1641 /// ```
1642 ///
1643 /// If a string contains multiple contiguous separators, you will end up
1644 /// with empty strings in the output:
1645 ///
1646 /// ```
1647 /// let x = "||||a||b|c".to_string();
1648 /// let d: Vec<_> = x.split('|').collect();
1649 ///
1650 /// assert_eq!(d, &["", "", "", "", "a", "", "b", "c"]);
1651 /// ```
1652 ///
1653 /// Contiguous separators are separated by the empty string.
1654 ///
1655 /// ```
1656 /// let x = "(///)".to_string();
1657 /// let d: Vec<_> = x.split('/').collect();
1658 ///
1659 /// assert_eq!(d, &["(", "", "", ")"]);
1660 /// ```
1661 ///
1662 /// Separators at the start or end of a string are neighbored
1663 /// by empty strings.
1664 ///
1665 /// ```
1666 /// let d: Vec<_> = "010".split("0").collect();
1667 /// assert_eq!(d, &["", "1", ""]);
1668 /// ```
1669 ///
1670 /// When the empty string is used as a separator, it separates
1671 /// every character in the string, along with the beginning
1672 /// and end of the string.
1673 ///
1674 /// ```
1675 /// let f: Vec<_> = "rust".split("").collect();
1676 /// assert_eq!(f, &["", "r", "u", "s", "t", ""]);
1677 /// ```
1678 ///
1679 /// Contiguous separators can lead to possibly surprising behavior
1680 /// when whitespace is used as the separator. This code is correct:
1681 ///
1682 /// ```
1683 /// let x = " a b c".to_string();
1684 /// let d: Vec<_> = x.split(' ').collect();
1685 ///
1686 /// assert_eq!(d, &["", "", "", "", "a", "", "b", "c"]);
1687 /// ```
1688 ///
1689 /// It does _not_ give you:
1690 ///
1691 /// ```,ignore
1692 /// assert_eq!(d, &["a", "b", "c"]);
1693 /// ```
1694 ///
1695 /// Use [`split_whitespace`] for this behavior.
1696 ///
1697 /// [`split_whitespace`]: str::split_whitespace
1698 #[stable(feature = "rust1", since = "1.0.0")]
1699 #[inline]
1700 #[cfg(not(feature = "ferrocene_subset"))]
1701 pub fn split<P: Pattern>(&self, pat: P) -> Split<'_, P> {
1702 Split(SplitInternal {
1703 start: 0,
1704 end: self.len(),
1705 matcher: pat.into_searcher(self),
1706 allow_trailing_empty: true,
1707 finished: false,
1708 })
1709 }
1710
1711 /// Returns an iterator over substrings of this string slice, separated by
1712 /// characters matched by a pattern.
1713 ///
1714 /// Differs from the iterator produced by `split` in that `split_inclusive`
1715 /// leaves the matched part as the terminator of the substring.
1716 ///
1717 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
1718 /// function or closure that determines if a character matches.
1719 ///
1720 /// [`char`]: prim@char
1721 /// [pattern]: self::pattern
1722 ///
1723 /// # Examples
1724 ///
1725 /// ```
1726 /// let v: Vec<&str> = "Mary had a little lamb\nlittle lamb\nlittle lamb."
1727 /// .split_inclusive('\n').collect();
1728 /// assert_eq!(v, ["Mary had a little lamb\n", "little lamb\n", "little lamb."]);
1729 /// ```
1730 ///
1731 /// If the last element of the string is matched,
1732 /// that element will be considered the terminator of the preceding substring.
1733 /// That substring will be the last item returned by the iterator.
1734 ///
1735 /// ```
1736 /// let v: Vec<&str> = "Mary had a little lamb\nlittle lamb\nlittle lamb.\n"
1737 /// .split_inclusive('\n').collect();
1738 /// assert_eq!(v, ["Mary had a little lamb\n", "little lamb\n", "little lamb.\n"]);
1739 /// ```
1740 #[stable(feature = "split_inclusive", since = "1.51.0")]
1741 #[inline]
1742 #[cfg(not(feature = "ferrocene_subset"))]
1743 pub fn split_inclusive<P: Pattern>(&self, pat: P) -> SplitInclusive<'_, P> {
1744 SplitInclusive(SplitInternal {
1745 start: 0,
1746 end: self.len(),
1747 matcher: pat.into_searcher(self),
1748 allow_trailing_empty: false,
1749 finished: false,
1750 })
1751 }
1752
1753 /// Returns an iterator over substrings of the given string slice, separated
1754 /// by characters matched by a pattern and yielded in reverse order.
1755 ///
1756 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
1757 /// function or closure that determines if a character matches.
1758 ///
1759 /// [`char`]: prim@char
1760 /// [pattern]: self::pattern
1761 ///
1762 /// # Iterator behavior
1763 ///
1764 /// The returned iterator requires that the pattern supports a reverse
1765 /// search, and it will be a [`DoubleEndedIterator`] if a forward/reverse
1766 /// search yields the same elements.
1767 ///
1768 /// For iterating from the front, the [`split`] method can be used.
1769 ///
1770 /// [`split`]: str::split
1771 ///
1772 /// # Examples
1773 ///
1774 /// Simple patterns:
1775 ///
1776 /// ```
1777 /// let v: Vec<&str> = "Mary had a little lamb".rsplit(' ').collect();
1778 /// assert_eq!(v, ["lamb", "little", "a", "had", "Mary"]);
1779 ///
1780 /// let v: Vec<&str> = "".rsplit('X').collect();
1781 /// assert_eq!(v, [""]);
1782 ///
1783 /// let v: Vec<&str> = "lionXXtigerXleopard".rsplit('X').collect();
1784 /// assert_eq!(v, ["leopard", "tiger", "", "lion"]);
1785 ///
1786 /// let v: Vec<&str> = "lion::tiger::leopard".rsplit("::").collect();
1787 /// assert_eq!(v, ["leopard", "tiger", "lion"]);
1788 /// ```
1789 ///
1790 /// A more complex pattern, using a closure:
1791 ///
1792 /// ```
1793 /// let v: Vec<&str> = "abc1defXghi".rsplit(|c| c == '1' || c == 'X').collect();
1794 /// assert_eq!(v, ["ghi", "def", "abc"]);
1795 /// ```
1796 #[stable(feature = "rust1", since = "1.0.0")]
1797 #[inline]
1798 #[cfg(not(feature = "ferrocene_subset"))]
1799 pub fn rsplit<P: Pattern>(&self, pat: P) -> RSplit<'_, P>
1800 where
1801 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
1802 {
1803 RSplit(self.split(pat).0)
1804 }
1805
1806 /// Returns an iterator over substrings of the given string slice, separated
1807 /// by characters matched by a pattern.
1808 ///
1809 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
1810 /// function or closure that determines if a character matches.
1811 ///
1812 /// [`char`]: prim@char
1813 /// [pattern]: self::pattern
1814 ///
1815 /// Equivalent to [`split`], except that the trailing substring
1816 /// is skipped if empty.
1817 ///
1818 /// [`split`]: str::split
1819 ///
1820 /// This method can be used for string data that is _terminated_,
1821 /// rather than _separated_ by a pattern.
1822 ///
1823 /// # Iterator behavior
1824 ///
1825 /// The returned iterator will be a [`DoubleEndedIterator`] if the pattern
1826 /// allows a reverse search and forward/reverse search yields the same
1827 /// elements. This is true for, e.g., [`char`], but not for `&str`.
1828 ///
1829 /// If the pattern allows a reverse search but its results might differ
1830 /// from a forward search, the [`rsplit_terminator`] method can be used.
1831 ///
1832 /// [`rsplit_terminator`]: str::rsplit_terminator
1833 ///
1834 /// # Examples
1835 ///
1836 /// ```
1837 /// let v: Vec<&str> = "A.B.".split_terminator('.').collect();
1838 /// assert_eq!(v, ["A", "B"]);
1839 ///
1840 /// let v: Vec<&str> = "A..B..".split_terminator(".").collect();
1841 /// assert_eq!(v, ["A", "", "B", ""]);
1842 ///
1843 /// let v: Vec<&str> = "A.B:C.D".split_terminator(&['.', ':'][..]).collect();
1844 /// assert_eq!(v, ["A", "B", "C", "D"]);
1845 /// ```
1846 #[stable(feature = "rust1", since = "1.0.0")]
1847 #[inline]
1848 #[cfg(not(feature = "ferrocene_subset"))]
1849 pub fn split_terminator<P: Pattern>(&self, pat: P) -> SplitTerminator<'_, P> {
1850 SplitTerminator(SplitInternal { allow_trailing_empty: false, ..self.split(pat).0 })
1851 }
1852
1853 /// Returns an iterator over substrings of `self`, separated by characters
1854 /// matched by a pattern and yielded in reverse order.
1855 ///
1856 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
1857 /// function or closure that determines if a character matches.
1858 ///
1859 /// [`char`]: prim@char
1860 /// [pattern]: self::pattern
1861 ///
1862 /// Equivalent to [`split`], except that the trailing substring is
1863 /// skipped if empty.
1864 ///
1865 /// [`split`]: str::split
1866 ///
1867 /// This method can be used for string data that is _terminated_,
1868 /// rather than _separated_ by a pattern.
1869 ///
1870 /// # Iterator behavior
1871 ///
1872 /// The returned iterator requires that the pattern supports a
1873 /// reverse search, and it will be double ended if a forward/reverse
1874 /// search yields the same elements.
1875 ///
1876 /// For iterating from the front, the [`split_terminator`] method can be
1877 /// used.
1878 ///
1879 /// [`split_terminator`]: str::split_terminator
1880 ///
1881 /// # Examples
1882 ///
1883 /// ```
1884 /// let v: Vec<&str> = "A.B.".rsplit_terminator('.').collect();
1885 /// assert_eq!(v, ["B", "A"]);
1886 ///
1887 /// let v: Vec<&str> = "A..B..".rsplit_terminator(".").collect();
1888 /// assert_eq!(v, ["", "B", "", "A"]);
1889 ///
1890 /// let v: Vec<&str> = "A.B:C.D".rsplit_terminator(&['.', ':'][..]).collect();
1891 /// assert_eq!(v, ["D", "C", "B", "A"]);
1892 /// ```
1893 #[stable(feature = "rust1", since = "1.0.0")]
1894 #[inline]
1895 #[cfg(not(feature = "ferrocene_subset"))]
1896 pub fn rsplit_terminator<P: Pattern>(&self, pat: P) -> RSplitTerminator<'_, P>
1897 where
1898 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
1899 {
1900 RSplitTerminator(self.split_terminator(pat).0)
1901 }
1902
1903 /// Returns an iterator over substrings of the given string slice, separated
1904 /// by a pattern, restricted to returning at most `n` items.
1905 ///
1906 /// If `n` substrings are returned, the last substring (the `n`th substring)
1907 /// will contain the remainder of the string.
1908 ///
1909 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
1910 /// function or closure that determines if a character matches.
1911 ///
1912 /// [`char`]: prim@char
1913 /// [pattern]: self::pattern
1914 ///
1915 /// # Iterator behavior
1916 ///
1917 /// The returned iterator will not be double ended, because it is
1918 /// not efficient to support.
1919 ///
1920 /// If the pattern allows a reverse search, the [`rsplitn`] method can be
1921 /// used.
1922 ///
1923 /// [`rsplitn`]: str::rsplitn
1924 ///
1925 /// # Examples
1926 ///
1927 /// Simple patterns:
1928 ///
1929 /// ```
1930 /// let v: Vec<&str> = "Mary had a little lambda".splitn(3, ' ').collect();
1931 /// assert_eq!(v, ["Mary", "had", "a little lambda"]);
1932 ///
1933 /// let v: Vec<&str> = "lionXXtigerXleopard".splitn(3, "X").collect();
1934 /// assert_eq!(v, ["lion", "", "tigerXleopard"]);
1935 ///
1936 /// let v: Vec<&str> = "abcXdef".splitn(1, 'X').collect();
1937 /// assert_eq!(v, ["abcXdef"]);
1938 ///
1939 /// let v: Vec<&str> = "".splitn(1, 'X').collect();
1940 /// assert_eq!(v, [""]);
1941 /// ```
1942 ///
1943 /// A more complex pattern, using a closure:
1944 ///
1945 /// ```
1946 /// let v: Vec<&str> = "abc1defXghi".splitn(2, |c| c == '1' || c == 'X').collect();
1947 /// assert_eq!(v, ["abc", "defXghi"]);
1948 /// ```
1949 #[stable(feature = "rust1", since = "1.0.0")]
1950 #[inline]
1951 #[cfg(not(feature = "ferrocene_subset"))]
1952 pub fn splitn<P: Pattern>(&self, n: usize, pat: P) -> SplitN<'_, P> {
1953 SplitN(SplitNInternal { iter: self.split(pat).0, count: n })
1954 }
1955
1956 /// Returns an iterator over substrings of this string slice, separated by a
1957 /// pattern, starting from the end of the string, restricted to returning at
1958 /// most `n` items.
1959 ///
1960 /// If `n` substrings are returned, the last substring (the `n`th substring)
1961 /// will contain the remainder of the string.
1962 ///
1963 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
1964 /// function or closure that determines if a character matches.
1965 ///
1966 /// [`char`]: prim@char
1967 /// [pattern]: self::pattern
1968 ///
1969 /// # Iterator behavior
1970 ///
1971 /// The returned iterator will not be double ended, because it is not
1972 /// efficient to support.
1973 ///
1974 /// For splitting from the front, the [`splitn`] method can be used.
1975 ///
1976 /// [`splitn`]: str::splitn
1977 ///
1978 /// # Examples
1979 ///
1980 /// Simple patterns:
1981 ///
1982 /// ```
1983 /// let v: Vec<&str> = "Mary had a little lamb".rsplitn(3, ' ').collect();
1984 /// assert_eq!(v, ["lamb", "little", "Mary had a"]);
1985 ///
1986 /// let v: Vec<&str> = "lionXXtigerXleopard".rsplitn(3, 'X').collect();
1987 /// assert_eq!(v, ["leopard", "tiger", "lionX"]);
1988 ///
1989 /// let v: Vec<&str> = "lion::tiger::leopard".rsplitn(2, "::").collect();
1990 /// assert_eq!(v, ["leopard", "lion::tiger"]);
1991 /// ```
1992 ///
1993 /// A more complex pattern, using a closure:
1994 ///
1995 /// ```
1996 /// let v: Vec<&str> = "abc1defXghi".rsplitn(2, |c| c == '1' || c == 'X').collect();
1997 /// assert_eq!(v, ["ghi", "abc1def"]);
1998 /// ```
1999 #[stable(feature = "rust1", since = "1.0.0")]
2000 #[inline]
2001 #[cfg(not(feature = "ferrocene_subset"))]
2002 pub fn rsplitn<P: Pattern>(&self, n: usize, pat: P) -> RSplitN<'_, P>
2003 where
2004 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
2005 {
2006 RSplitN(self.splitn(n, pat).0)
2007 }
2008
2009 /// Splits the string on the first occurrence of the specified delimiter and
2010 /// returns prefix before delimiter and suffix after delimiter.
2011 ///
2012 /// # Examples
2013 ///
2014 /// ```
2015 /// assert_eq!("cfg".split_once('='), None);
2016 /// assert_eq!("cfg=".split_once('='), Some(("cfg", "")));
2017 /// assert_eq!("cfg=foo".split_once('='), Some(("cfg", "foo")));
2018 /// assert_eq!("cfg=foo=bar".split_once('='), Some(("cfg", "foo=bar")));
2019 /// ```
2020 #[stable(feature = "str_split_once", since = "1.52.0")]
2021 #[inline]
2022 #[cfg(not(feature = "ferrocene_subset"))]
2023 pub fn split_once<P: Pattern>(&self, delimiter: P) -> Option<(&'_ str, &'_ str)> {
2024 let (start, end) = delimiter.into_searcher(self).next_match()?;
2025 // SAFETY: `Searcher` is known to return valid indices.
2026 unsafe { Some((self.get_unchecked(..start), self.get_unchecked(end..))) }
2027 }
2028
2029 /// Splits the string on the last occurrence of the specified delimiter and
2030 /// returns prefix before delimiter and suffix after delimiter.
2031 ///
2032 /// # Examples
2033 ///
2034 /// ```
2035 /// assert_eq!("cfg".rsplit_once('='), None);
2036 /// assert_eq!("cfg=".rsplit_once('='), Some(("cfg", "")));
2037 /// assert_eq!("cfg=foo".rsplit_once('='), Some(("cfg", "foo")));
2038 /// assert_eq!("cfg=foo=bar".rsplit_once('='), Some(("cfg=foo", "bar")));
2039 /// ```
2040 #[stable(feature = "str_split_once", since = "1.52.0")]
2041 #[inline]
2042 #[cfg(not(feature = "ferrocene_subset"))]
2043 pub fn rsplit_once<P: Pattern>(&self, delimiter: P) -> Option<(&'_ str, &'_ str)>
2044 where
2045 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
2046 {
2047 let (start, end) = delimiter.into_searcher(self).next_match_back()?;
2048 // SAFETY: `Searcher` is known to return valid indices.
2049 unsafe { Some((self.get_unchecked(..start), self.get_unchecked(end..))) }
2050 }
2051
2052 /// Returns an iterator over the disjoint matches of a pattern within the
2053 /// given string slice.
2054 ///
2055 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2056 /// function or closure that determines if a character matches.
2057 ///
2058 /// [`char`]: prim@char
2059 /// [pattern]: self::pattern
2060 ///
2061 /// # Iterator behavior
2062 ///
2063 /// The returned iterator will be a [`DoubleEndedIterator`] if the pattern
2064 /// allows a reverse search and forward/reverse search yields the same
2065 /// elements. This is true for, e.g., [`char`], but not for `&str`.
2066 ///
2067 /// If the pattern allows a reverse search but its results might differ
2068 /// from a forward search, the [`rmatches`] method can be used.
2069 ///
2070 /// [`rmatches`]: str::rmatches
2071 ///
2072 /// # Examples
2073 ///
2074 /// ```
2075 /// let v: Vec<&str> = "abcXXXabcYYYabc".matches("abc").collect();
2076 /// assert_eq!(v, ["abc", "abc", "abc"]);
2077 ///
2078 /// let v: Vec<&str> = "1abc2abc3".matches(char::is_numeric).collect();
2079 /// assert_eq!(v, ["1", "2", "3"]);
2080 /// ```
2081 #[stable(feature = "str_matches", since = "1.2.0")]
2082 #[inline]
2083 #[cfg(not(feature = "ferrocene_subset"))]
2084 pub fn matches<P: Pattern>(&self, pat: P) -> Matches<'_, P> {
2085 Matches(MatchesInternal(pat.into_searcher(self)))
2086 }
2087
2088 /// Returns an iterator over the disjoint matches of a pattern within this
2089 /// string slice, yielded in reverse order.
2090 ///
2091 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2092 /// function or closure that determines if a character matches.
2093 ///
2094 /// [`char`]: prim@char
2095 /// [pattern]: self::pattern
2096 ///
2097 /// # Iterator behavior
2098 ///
2099 /// The returned iterator requires that the pattern supports a reverse
2100 /// search, and it will be a [`DoubleEndedIterator`] if a forward/reverse
2101 /// search yields the same elements.
2102 ///
2103 /// For iterating from the front, the [`matches`] method can be used.
2104 ///
2105 /// [`matches`]: str::matches
2106 ///
2107 /// # Examples
2108 ///
2109 /// ```
2110 /// let v: Vec<&str> = "abcXXXabcYYYabc".rmatches("abc").collect();
2111 /// assert_eq!(v, ["abc", "abc", "abc"]);
2112 ///
2113 /// let v: Vec<&str> = "1abc2abc3".rmatches(char::is_numeric).collect();
2114 /// assert_eq!(v, ["3", "2", "1"]);
2115 /// ```
2116 #[stable(feature = "str_matches", since = "1.2.0")]
2117 #[inline]
2118 #[cfg(not(feature = "ferrocene_subset"))]
2119 pub fn rmatches<P: Pattern>(&self, pat: P) -> RMatches<'_, P>
2120 where
2121 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
2122 {
2123 RMatches(self.matches(pat).0)
2124 }
2125
2126 /// Returns an iterator over the disjoint matches of a pattern within this string
2127 /// slice as well as the index that the match starts at.
2128 ///
2129 /// For matches of `pat` within `self` that overlap, only the indices
2130 /// corresponding to the first match are returned.
2131 ///
2132 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2133 /// function or closure that determines if a character matches.
2134 ///
2135 /// [`char`]: prim@char
2136 /// [pattern]: self::pattern
2137 ///
2138 /// # Iterator behavior
2139 ///
2140 /// The returned iterator will be a [`DoubleEndedIterator`] if the pattern
2141 /// allows a reverse search and forward/reverse search yields the same
2142 /// elements. This is true for, e.g., [`char`], but not for `&str`.
2143 ///
2144 /// If the pattern allows a reverse search but its results might differ
2145 /// from a forward search, the [`rmatch_indices`] method can be used.
2146 ///
2147 /// [`rmatch_indices`]: str::rmatch_indices
2148 ///
2149 /// # Examples
2150 ///
2151 /// ```
2152 /// let v: Vec<_> = "abcXXXabcYYYabc".match_indices("abc").collect();
2153 /// assert_eq!(v, [(0, "abc"), (6, "abc"), (12, "abc")]);
2154 ///
2155 /// let v: Vec<_> = "1abcabc2".match_indices("abc").collect();
2156 /// assert_eq!(v, [(1, "abc"), (4, "abc")]);
2157 ///
2158 /// let v: Vec<_> = "ababa".match_indices("aba").collect();
2159 /// assert_eq!(v, [(0, "aba")]); // only the first `aba`
2160 /// ```
2161 #[stable(feature = "str_match_indices", since = "1.5.0")]
2162 #[inline]
2163 #[cfg(not(feature = "ferrocene_subset"))]
2164 pub fn match_indices<P: Pattern>(&self, pat: P) -> MatchIndices<'_, P> {
2165 MatchIndices(MatchIndicesInternal(pat.into_searcher(self)))
2166 }
2167
2168 /// Returns an iterator over the disjoint matches of a pattern within `self`,
2169 /// yielded in reverse order along with the index of the match.
2170 ///
2171 /// For matches of `pat` within `self` that overlap, only the indices
2172 /// corresponding to the last match are returned.
2173 ///
2174 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2175 /// function or closure that determines if a character matches.
2176 ///
2177 /// [`char`]: prim@char
2178 /// [pattern]: self::pattern
2179 ///
2180 /// # Iterator behavior
2181 ///
2182 /// The returned iterator requires that the pattern supports a reverse
2183 /// search, and it will be a [`DoubleEndedIterator`] if a forward/reverse
2184 /// search yields the same elements.
2185 ///
2186 /// For iterating from the front, the [`match_indices`] method can be used.
2187 ///
2188 /// [`match_indices`]: str::match_indices
2189 ///
2190 /// # Examples
2191 ///
2192 /// ```
2193 /// let v: Vec<_> = "abcXXXabcYYYabc".rmatch_indices("abc").collect();
2194 /// assert_eq!(v, [(12, "abc"), (6, "abc"), (0, "abc")]);
2195 ///
2196 /// let v: Vec<_> = "1abcabc2".rmatch_indices("abc").collect();
2197 /// assert_eq!(v, [(4, "abc"), (1, "abc")]);
2198 ///
2199 /// let v: Vec<_> = "ababa".rmatch_indices("aba").collect();
2200 /// assert_eq!(v, [(2, "aba")]); // only the last `aba`
2201 /// ```
2202 #[stable(feature = "str_match_indices", since = "1.5.0")]
2203 #[inline]
2204 #[cfg(not(feature = "ferrocene_subset"))]
2205 pub fn rmatch_indices<P: Pattern>(&self, pat: P) -> RMatchIndices<'_, P>
2206 where
2207 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
2208 {
2209 RMatchIndices(self.match_indices(pat).0)
2210 }
2211
2212 /// Returns a string slice with leading and trailing whitespace removed.
2213 ///
2214 /// 'Whitespace' is defined according to the terms of the Unicode Derived
2215 /// Core Property `White_Space`, which includes newlines.
2216 ///
2217 /// # Examples
2218 ///
2219 /// ```
2220 /// let s = "\n Hello\tworld\t\n";
2221 ///
2222 /// assert_eq!("Hello\tworld", s.trim());
2223 /// ```
2224 #[inline]
2225 #[must_use = "this returns the trimmed string as a slice, \
2226 without modifying the original"]
2227 #[stable(feature = "rust1", since = "1.0.0")]
2228 #[rustc_diagnostic_item = "str_trim"]
2229 #[cfg(not(feature = "ferrocene_subset"))]
2230 pub fn trim(&self) -> &str {
2231 self.trim_matches(char::is_whitespace)
2232 }
2233
2234 /// Returns a string slice with leading whitespace removed.
2235 ///
2236 /// 'Whitespace' is defined according to the terms of the Unicode Derived
2237 /// Core Property `White_Space`, which includes newlines.
2238 ///
2239 /// # Text directionality
2240 ///
2241 /// A string is a sequence of bytes. `start` in this context means the first
2242 /// position of that byte string; for a left-to-right language like English or
2243 /// Russian, this will be left side, and for right-to-left languages like
2244 /// Arabic or Hebrew, this will be the right side.
2245 ///
2246 /// # Examples
2247 ///
2248 /// Basic usage:
2249 ///
2250 /// ```
2251 /// let s = "\n Hello\tworld\t\n";
2252 /// assert_eq!("Hello\tworld\t\n", s.trim_start());
2253 /// ```
2254 ///
2255 /// Directionality:
2256 ///
2257 /// ```
2258 /// let s = " English ";
2259 /// assert!(Some('E') == s.trim_start().chars().next());
2260 ///
2261 /// let s = " עברית ";
2262 /// assert!(Some('ע') == s.trim_start().chars().next());
2263 /// ```
2264 #[inline]
2265 #[must_use = "this returns the trimmed string as a new slice, \
2266 without modifying the original"]
2267 #[stable(feature = "trim_direction", since = "1.30.0")]
2268 #[rustc_diagnostic_item = "str_trim_start"]
2269 #[cfg(not(feature = "ferrocene_subset"))]
2270 pub fn trim_start(&self) -> &str {
2271 self.trim_start_matches(char::is_whitespace)
2272 }
2273
2274 /// Returns a string slice with trailing whitespace removed.
2275 ///
2276 /// 'Whitespace' is defined according to the terms of the Unicode Derived
2277 /// Core Property `White_Space`, which includes newlines.
2278 ///
2279 /// # Text directionality
2280 ///
2281 /// A string is a sequence of bytes. `end` in this context means the last
2282 /// position of that byte string; for a left-to-right language like English or
2283 /// Russian, this will be right side, and for right-to-left languages like
2284 /// Arabic or Hebrew, this will be the left side.
2285 ///
2286 /// # Examples
2287 ///
2288 /// Basic usage:
2289 ///
2290 /// ```
2291 /// let s = "\n Hello\tworld\t\n";
2292 /// assert_eq!("\n Hello\tworld", s.trim_end());
2293 /// ```
2294 ///
2295 /// Directionality:
2296 ///
2297 /// ```
2298 /// let s = " English ";
2299 /// assert!(Some('h') == s.trim_end().chars().rev().next());
2300 ///
2301 /// let s = " עברית ";
2302 /// assert!(Some('ת') == s.trim_end().chars().rev().next());
2303 /// ```
2304 #[inline]
2305 #[must_use = "this returns the trimmed string as a new slice, \
2306 without modifying the original"]
2307 #[stable(feature = "trim_direction", since = "1.30.0")]
2308 #[rustc_diagnostic_item = "str_trim_end"]
2309 #[cfg(not(feature = "ferrocene_subset"))]
2310 pub fn trim_end(&self) -> &str {
2311 self.trim_end_matches(char::is_whitespace)
2312 }
2313
2314 /// Returns a string slice with leading whitespace removed.
2315 ///
2316 /// 'Whitespace' is defined according to the terms of the Unicode Derived
2317 /// Core Property `White_Space`.
2318 ///
2319 /// # Text directionality
2320 ///
2321 /// A string is a sequence of bytes. 'Left' in this context means the first
2322 /// position of that byte string; for a language like Arabic or Hebrew
2323 /// which are 'right to left' rather than 'left to right', this will be
2324 /// the _right_ side, not the left.
2325 ///
2326 /// # Examples
2327 ///
2328 /// Basic usage:
2329 ///
2330 /// ```
2331 /// let s = " Hello\tworld\t";
2332 ///
2333 /// assert_eq!("Hello\tworld\t", s.trim_left());
2334 /// ```
2335 ///
2336 /// Directionality:
2337 ///
2338 /// ```
2339 /// let s = " English";
2340 /// assert!(Some('E') == s.trim_left().chars().next());
2341 ///
2342 /// let s = " עברית";
2343 /// assert!(Some('ע') == s.trim_left().chars().next());
2344 /// ```
2345 #[must_use = "this returns the trimmed string as a new slice, \
2346 without modifying the original"]
2347 #[inline]
2348 #[stable(feature = "rust1", since = "1.0.0")]
2349 #[deprecated(since = "1.33.0", note = "superseded by `trim_start`", suggestion = "trim_start")]
2350 #[cfg(not(feature = "ferrocene_subset"))]
2351 pub fn trim_left(&self) -> &str {
2352 self.trim_start()
2353 }
2354
2355 /// Returns a string slice with trailing whitespace removed.
2356 ///
2357 /// 'Whitespace' is defined according to the terms of the Unicode Derived
2358 /// Core Property `White_Space`.
2359 ///
2360 /// # Text directionality
2361 ///
2362 /// A string is a sequence of bytes. 'Right' in this context means the last
2363 /// position of that byte string; for a language like Arabic or Hebrew
2364 /// which are 'right to left' rather than 'left to right', this will be
2365 /// the _left_ side, not the right.
2366 ///
2367 /// # Examples
2368 ///
2369 /// Basic usage:
2370 ///
2371 /// ```
2372 /// let s = " Hello\tworld\t";
2373 ///
2374 /// assert_eq!(" Hello\tworld", s.trim_right());
2375 /// ```
2376 ///
2377 /// Directionality:
2378 ///
2379 /// ```
2380 /// let s = "English ";
2381 /// assert!(Some('h') == s.trim_right().chars().rev().next());
2382 ///
2383 /// let s = "עברית ";
2384 /// assert!(Some('ת') == s.trim_right().chars().rev().next());
2385 /// ```
2386 #[must_use = "this returns the trimmed string as a new slice, \
2387 without modifying the original"]
2388 #[inline]
2389 #[stable(feature = "rust1", since = "1.0.0")]
2390 #[deprecated(since = "1.33.0", note = "superseded by `trim_end`", suggestion = "trim_end")]
2391 #[cfg(not(feature = "ferrocene_subset"))]
2392 pub fn trim_right(&self) -> &str {
2393 self.trim_end()
2394 }
2395
2396 /// Returns a string slice with all prefixes and suffixes that match a
2397 /// pattern repeatedly removed.
2398 ///
2399 /// The [pattern] can be a [`char`], a slice of [`char`]s, or a function
2400 /// or closure that determines if a character matches.
2401 ///
2402 /// [`char`]: prim@char
2403 /// [pattern]: self::pattern
2404 ///
2405 /// # Examples
2406 ///
2407 /// Simple patterns:
2408 ///
2409 /// ```
2410 /// assert_eq!("11foo1bar11".trim_matches('1'), "foo1bar");
2411 /// assert_eq!("123foo1bar123".trim_matches(char::is_numeric), "foo1bar");
2412 ///
2413 /// let x: &[_] = &['1', '2'];
2414 /// assert_eq!("12foo1bar12".trim_matches(x), "foo1bar");
2415 /// ```
2416 ///
2417 /// A more complex pattern, using a closure:
2418 ///
2419 /// ```
2420 /// assert_eq!("1foo1barXX".trim_matches(|c| c == '1' || c == 'X'), "foo1bar");
2421 /// ```
2422 #[must_use = "this returns the trimmed string as a new slice, \
2423 without modifying the original"]
2424 #[stable(feature = "rust1", since = "1.0.0")]
2425 #[cfg(not(feature = "ferrocene_subset"))]
2426 pub fn trim_matches<P: Pattern>(&self, pat: P) -> &str
2427 where
2428 for<'a> P::Searcher<'a>: DoubleEndedSearcher<'a>,
2429 {
2430 let mut i = 0;
2431 let mut j = 0;
2432 let mut matcher = pat.into_searcher(self);
2433 if let Some((a, b)) = matcher.next_reject() {
2434 i = a;
2435 j = b; // Remember earliest known match, correct it below if
2436 // last match is different
2437 }
2438 if let Some((_, b)) = matcher.next_reject_back() {
2439 j = b;
2440 }
2441 // SAFETY: `Searcher` is known to return valid indices.
2442 unsafe { self.get_unchecked(i..j) }
2443 }
2444
2445 /// Returns a string slice with all prefixes that match a pattern
2446 /// repeatedly removed.
2447 ///
2448 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2449 /// function or closure that determines if a character matches.
2450 ///
2451 /// [`char`]: prim@char
2452 /// [pattern]: self::pattern
2453 ///
2454 /// # Text directionality
2455 ///
2456 /// A string is a sequence of bytes. `start` in this context means the first
2457 /// position of that byte string; for a left-to-right language like English or
2458 /// Russian, this will be left side, and for right-to-left languages like
2459 /// Arabic or Hebrew, this will be the right side.
2460 ///
2461 /// # Examples
2462 ///
2463 /// ```
2464 /// assert_eq!("11foo1bar11".trim_start_matches('1'), "foo1bar11");
2465 /// assert_eq!("123foo1bar123".trim_start_matches(char::is_numeric), "foo1bar123");
2466 ///
2467 /// let x: &[_] = &['1', '2'];
2468 /// assert_eq!("12foo1bar12".trim_start_matches(x), "foo1bar12");
2469 /// ```
2470 #[must_use = "this returns the trimmed string as a new slice, \
2471 without modifying the original"]
2472 #[stable(feature = "trim_direction", since = "1.30.0")]
2473 #[cfg(not(feature = "ferrocene_subset"))]
2474 pub fn trim_start_matches<P: Pattern>(&self, pat: P) -> &str {
2475 let mut i = self.len();
2476 let mut matcher = pat.into_searcher(self);
2477 if let Some((a, _)) = matcher.next_reject() {
2478 i = a;
2479 }
2480 // SAFETY: `Searcher` is known to return valid indices.
2481 unsafe { self.get_unchecked(i..self.len()) }
2482 }
2483
2484 /// Returns a string slice with the prefix removed.
2485 ///
2486 /// If the string starts with the pattern `prefix`, returns the substring after the prefix,
2487 /// wrapped in `Some`. Unlike [`trim_start_matches`], this method removes the prefix exactly once.
2488 ///
2489 /// If the string does not start with `prefix`, returns `None`.
2490 ///
2491 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2492 /// function or closure that determines if a character matches.
2493 ///
2494 /// [`char`]: prim@char
2495 /// [pattern]: self::pattern
2496 /// [`trim_start_matches`]: Self::trim_start_matches
2497 ///
2498 /// # Examples
2499 ///
2500 /// ```
2501 /// assert_eq!("foo:bar".strip_prefix("foo:"), Some("bar"));
2502 /// assert_eq!("foo:bar".strip_prefix("bar"), None);
2503 /// assert_eq!("foofoo".strip_prefix("foo"), Some("foo"));
2504 /// ```
2505 #[must_use = "this returns the remaining substring as a new slice, \
2506 without modifying the original"]
2507 #[stable(feature = "str_strip", since = "1.45.0")]
2508 #[cfg(not(feature = "ferrocene_subset"))]
2509 pub fn strip_prefix<P: Pattern>(&self, prefix: P) -> Option<&str> {
2510 prefix.strip_prefix_of(self)
2511 }
2512
2513 /// Returns a string slice with the suffix removed.
2514 ///
2515 /// If the string ends with the pattern `suffix`, returns the substring before the suffix,
2516 /// wrapped in `Some`. Unlike [`trim_end_matches`], this method removes the suffix exactly once.
2517 ///
2518 /// If the string does not end with `suffix`, returns `None`.
2519 ///
2520 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2521 /// function or closure that determines if a character matches.
2522 ///
2523 /// [`char`]: prim@char
2524 /// [pattern]: self::pattern
2525 /// [`trim_end_matches`]: Self::trim_end_matches
2526 ///
2527 /// # Examples
2528 ///
2529 /// ```
2530 /// assert_eq!("bar:foo".strip_suffix(":foo"), Some("bar"));
2531 /// assert_eq!("bar:foo".strip_suffix("bar"), None);
2532 /// assert_eq!("foofoo".strip_suffix("foo"), Some("foo"));
2533 /// ```
2534 #[must_use = "this returns the remaining substring as a new slice, \
2535 without modifying the original"]
2536 #[stable(feature = "str_strip", since = "1.45.0")]
2537 #[cfg(not(feature = "ferrocene_subset"))]
2538 pub fn strip_suffix<P: Pattern>(&self, suffix: P) -> Option<&str>
2539 where
2540 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
2541 {
2542 suffix.strip_suffix_of(self)
2543 }
2544
2545 /// Returns a string slice with the prefix and suffix removed.
2546 ///
2547 /// If the string starts with the pattern `prefix` and ends with the pattern `suffix`, returns
2548 /// the substring after the prefix and before the suffix, wrapped in `Some`.
2549 /// Unlike [`trim_start_matches`] and [`trim_end_matches`], this method removes both the prefix
2550 /// and suffix exactly once.
2551 ///
2552 /// If the string does not start with `prefix` or does not end with `suffix`, returns `None`.
2553 ///
2554 /// Each [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2555 /// function or closure that determines if a character matches.
2556 ///
2557 /// [`char`]: prim@char
2558 /// [pattern]: self::pattern
2559 /// [`trim_start_matches`]: Self::trim_start_matches
2560 /// [`trim_end_matches`]: Self::trim_end_matches
2561 ///
2562 /// # Examples
2563 ///
2564 /// ```
2565 /// #![feature(strip_circumfix)]
2566 ///
2567 /// assert_eq!("bar:hello:foo".strip_circumfix("bar:", ":foo"), Some("hello"));
2568 /// assert_eq!("bar:foo".strip_circumfix("foo", "foo"), None);
2569 /// assert_eq!("foo:bar;".strip_circumfix("foo:", ';'), Some("bar"));
2570 /// ```
2571 #[must_use = "this returns the remaining substring as a new slice, \
2572 without modifying the original"]
2573 #[unstable(feature = "strip_circumfix", issue = "147946")]
2574 #[cfg(not(feature = "ferrocene_subset"))]
2575 pub fn strip_circumfix<P: Pattern, S: Pattern>(&self, prefix: P, suffix: S) -> Option<&str>
2576 where
2577 for<'a> S::Searcher<'a>: ReverseSearcher<'a>,
2578 {
2579 self.strip_prefix(prefix)?.strip_suffix(suffix)
2580 }
2581
2582 /// Returns a string slice with the optional prefix removed.
2583 ///
2584 /// If the string starts with the pattern `prefix`, returns the substring after the prefix.
2585 /// Unlike [`strip_prefix`], this method always returns `&str` for easy method chaining,
2586 /// instead of returning [`Option<&str>`].
2587 ///
2588 /// If the string does not start with `prefix`, returns the original string unchanged.
2589 ///
2590 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2591 /// function or closure that determines if a character matches.
2592 ///
2593 /// [`char`]: prim@char
2594 /// [pattern]: self::pattern
2595 /// [`strip_prefix`]: Self::strip_prefix
2596 ///
2597 /// # Examples
2598 ///
2599 /// ```
2600 /// #![feature(trim_prefix_suffix)]
2601 ///
2602 /// // Prefix present - removes it
2603 /// assert_eq!("foo:bar".trim_prefix("foo:"), "bar");
2604 /// assert_eq!("foofoo".trim_prefix("foo"), "foo");
2605 ///
2606 /// // Prefix absent - returns original string
2607 /// assert_eq!("foo:bar".trim_prefix("bar"), "foo:bar");
2608 ///
2609 /// // Method chaining example
2610 /// assert_eq!("<https://example.com/>".trim_prefix('<').trim_suffix('>'), "https://example.com/");
2611 /// ```
2612 #[must_use = "this returns the remaining substring as a new slice, \
2613 without modifying the original"]
2614 #[unstable(feature = "trim_prefix_suffix", issue = "142312")]
2615 #[cfg(not(feature = "ferrocene_subset"))]
2616 pub fn trim_prefix<P: Pattern>(&self, prefix: P) -> &str {
2617 prefix.strip_prefix_of(self).unwrap_or(self)
2618 }
2619
2620 /// Returns a string slice with the optional suffix removed.
2621 ///
2622 /// If the string ends with the pattern `suffix`, returns the substring before the suffix.
2623 /// Unlike [`strip_suffix`], this method always returns `&str` for easy method chaining,
2624 /// instead of returning [`Option<&str>`].
2625 ///
2626 /// If the string does not end with `suffix`, returns the original string unchanged.
2627 ///
2628 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2629 /// function or closure that determines if a character matches.
2630 ///
2631 /// [`char`]: prim@char
2632 /// [pattern]: self::pattern
2633 /// [`strip_suffix`]: Self::strip_suffix
2634 ///
2635 /// # Examples
2636 ///
2637 /// ```
2638 /// #![feature(trim_prefix_suffix)]
2639 ///
2640 /// // Suffix present - removes it
2641 /// assert_eq!("bar:foo".trim_suffix(":foo"), "bar");
2642 /// assert_eq!("foofoo".trim_suffix("foo"), "foo");
2643 ///
2644 /// // Suffix absent - returns original string
2645 /// assert_eq!("bar:foo".trim_suffix("bar"), "bar:foo");
2646 ///
2647 /// // Method chaining example
2648 /// assert_eq!("<https://example.com/>".trim_prefix('<').trim_suffix('>'), "https://example.com/");
2649 /// ```
2650 #[must_use = "this returns the remaining substring as a new slice, \
2651 without modifying the original"]
2652 #[unstable(feature = "trim_prefix_suffix", issue = "142312")]
2653 #[cfg(not(feature = "ferrocene_subset"))]
2654 pub fn trim_suffix<P: Pattern>(&self, suffix: P) -> &str
2655 where
2656 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
2657 {
2658 suffix.strip_suffix_of(self).unwrap_or(self)
2659 }
2660
2661 /// Returns a string slice with all suffixes that match a pattern
2662 /// repeatedly removed.
2663 ///
2664 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2665 /// function or closure that determines if a character matches.
2666 ///
2667 /// [`char`]: prim@char
2668 /// [pattern]: self::pattern
2669 ///
2670 /// # Text directionality
2671 ///
2672 /// A string is a sequence of bytes. `end` in this context means the last
2673 /// position of that byte string; for a left-to-right language like English or
2674 /// Russian, this will be right side, and for right-to-left languages like
2675 /// Arabic or Hebrew, this will be the left side.
2676 ///
2677 /// # Examples
2678 ///
2679 /// Simple patterns:
2680 ///
2681 /// ```
2682 /// assert_eq!("11foo1bar11".trim_end_matches('1'), "11foo1bar");
2683 /// assert_eq!("123foo1bar123".trim_end_matches(char::is_numeric), "123foo1bar");
2684 ///
2685 /// let x: &[_] = &['1', '2'];
2686 /// assert_eq!("12foo1bar12".trim_end_matches(x), "12foo1bar");
2687 /// ```
2688 ///
2689 /// A more complex pattern, using a closure:
2690 ///
2691 /// ```
2692 /// assert_eq!("1fooX".trim_end_matches(|c| c == '1' || c == 'X'), "1foo");
2693 /// ```
2694 #[must_use = "this returns the trimmed string as a new slice, \
2695 without modifying the original"]
2696 #[stable(feature = "trim_direction", since = "1.30.0")]
2697 #[cfg(not(feature = "ferrocene_subset"))]
2698 pub fn trim_end_matches<P: Pattern>(&self, pat: P) -> &str
2699 where
2700 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
2701 {
2702 let mut j = 0;
2703 let mut matcher = pat.into_searcher(self);
2704 if let Some((_, b)) = matcher.next_reject_back() {
2705 j = b;
2706 }
2707 // SAFETY: `Searcher` is known to return valid indices.
2708 unsafe { self.get_unchecked(0..j) }
2709 }
2710
2711 /// Returns a string slice with all prefixes that match a pattern
2712 /// repeatedly removed.
2713 ///
2714 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2715 /// function or closure that determines if a character matches.
2716 ///
2717 /// [`char`]: prim@char
2718 /// [pattern]: self::pattern
2719 ///
2720 /// # Text directionality
2721 ///
2722 /// A string is a sequence of bytes. 'Left' in this context means the first
2723 /// position of that byte string; for a language like Arabic or Hebrew
2724 /// which are 'right to left' rather than 'left to right', this will be
2725 /// the _right_ side, not the left.
2726 ///
2727 /// # Examples
2728 ///
2729 /// ```
2730 /// assert_eq!("11foo1bar11".trim_left_matches('1'), "foo1bar11");
2731 /// assert_eq!("123foo1bar123".trim_left_matches(char::is_numeric), "foo1bar123");
2732 ///
2733 /// let x: &[_] = &['1', '2'];
2734 /// assert_eq!("12foo1bar12".trim_left_matches(x), "foo1bar12");
2735 /// ```
2736 #[stable(feature = "rust1", since = "1.0.0")]
2737 #[deprecated(
2738 since = "1.33.0",
2739 note = "superseded by `trim_start_matches`",
2740 suggestion = "trim_start_matches"
2741 )]
2742 #[cfg(not(feature = "ferrocene_subset"))]
2743 pub fn trim_left_matches<P: Pattern>(&self, pat: P) -> &str {
2744 self.trim_start_matches(pat)
2745 }
2746
2747 /// Returns a string slice with all suffixes that match a pattern
2748 /// repeatedly removed.
2749 ///
2750 /// The [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
2751 /// function or closure that determines if a character matches.
2752 ///
2753 /// [`char`]: prim@char
2754 /// [pattern]: self::pattern
2755 ///
2756 /// # Text directionality
2757 ///
2758 /// A string is a sequence of bytes. 'Right' in this context means the last
2759 /// position of that byte string; for a language like Arabic or Hebrew
2760 /// which are 'right to left' rather than 'left to right', this will be
2761 /// the _left_ side, not the right.
2762 ///
2763 /// # Examples
2764 ///
2765 /// Simple patterns:
2766 ///
2767 /// ```
2768 /// assert_eq!("11foo1bar11".trim_right_matches('1'), "11foo1bar");
2769 /// assert_eq!("123foo1bar123".trim_right_matches(char::is_numeric), "123foo1bar");
2770 ///
2771 /// let x: &[_] = &['1', '2'];
2772 /// assert_eq!("12foo1bar12".trim_right_matches(x), "12foo1bar");
2773 /// ```
2774 ///
2775 /// A more complex pattern, using a closure:
2776 ///
2777 /// ```
2778 /// assert_eq!("1fooX".trim_right_matches(|c| c == '1' || c == 'X'), "1foo");
2779 /// ```
2780 #[stable(feature = "rust1", since = "1.0.0")]
2781 #[deprecated(
2782 since = "1.33.0",
2783 note = "superseded by `trim_end_matches`",
2784 suggestion = "trim_end_matches"
2785 )]
2786 #[cfg(not(feature = "ferrocene_subset"))]
2787 pub fn trim_right_matches<P: Pattern>(&self, pat: P) -> &str
2788 where
2789 for<'a> P::Searcher<'a>: ReverseSearcher<'a>,
2790 {
2791 self.trim_end_matches(pat)
2792 }
2793
2794 /// Parses this string slice into another type.
2795 ///
2796 /// Because `parse` is so general, it can cause problems with type
2797 /// inference. As such, `parse` is one of the few times you'll see
2798 /// the syntax affectionately known as the 'turbofish': `::<>`. This
2799 /// helps the inference algorithm understand specifically which type
2800 /// you're trying to parse into.
2801 ///
2802 /// `parse` can parse into any type that implements the [`FromStr`] trait.
2803 ///
2804 /// # Errors
2805 ///
2806 /// Will return [`Err`] if it's not possible to parse this string slice into
2807 /// the desired type.
2808 ///
2809 /// [`Err`]: FromStr::Err
2810 ///
2811 /// # Examples
2812 ///
2813 /// Basic usage:
2814 ///
2815 /// ```
2816 /// let four: u32 = "4".parse().unwrap();
2817 ///
2818 /// assert_eq!(4, four);
2819 /// ```
2820 ///
2821 /// Using the 'turbofish' instead of annotating `four`:
2822 ///
2823 /// ```
2824 /// let four = "4".parse::<u32>();
2825 ///
2826 /// assert_eq!(Ok(4), four);
2827 /// ```
2828 ///
2829 /// Failing to parse:
2830 ///
2831 /// ```
2832 /// let nope = "j".parse::<u32>();
2833 ///
2834 /// assert!(nope.is_err());
2835 /// ```
2836 #[inline]
2837 #[stable(feature = "rust1", since = "1.0.0")]
2838 pub fn parse<F: FromStr>(&self) -> Result<F, F::Err> {
2839 FromStr::from_str(self)
2840 }
2841
2842 /// Checks if all characters in this string are within the ASCII range.
2843 ///
2844 /// An empty string returns `true`.
2845 ///
2846 /// # Examples
2847 ///
2848 /// ```
2849 /// let ascii = "hello!\n";
2850 /// let non_ascii = "Grüße, Jürgen ❤";
2851 ///
2852 /// assert!(ascii.is_ascii());
2853 /// assert!(!non_ascii.is_ascii());
2854 /// ```
2855 #[stable(feature = "ascii_methods_on_intrinsics", since = "1.23.0")]
2856 #[rustc_const_stable(feature = "const_slice_is_ascii", since = "1.74.0")]
2857 #[must_use]
2858 #[inline]
2859 #[cfg(not(feature = "ferrocene_subset"))]
2860 pub const fn is_ascii(&self) -> bool {
2861 // We can treat each byte as character here: all multibyte characters
2862 // start with a byte that is not in the ASCII range, so we will stop
2863 // there already.
2864 self.as_bytes().is_ascii()
2865 }
2866
2867 /// If this string slice [`is_ascii`](Self::is_ascii), returns it as a slice
2868 /// of [ASCII characters](`ascii::Char`), otherwise returns `None`.
2869 #[unstable(feature = "ascii_char", issue = "110998")]
2870 #[must_use]
2871 #[inline]
2872 #[cfg(not(feature = "ferrocene_subset"))]
2873 pub const fn as_ascii(&self) -> Option<&[ascii::Char]> {
2874 // Like in `is_ascii`, we can work on the bytes directly.
2875 self.as_bytes().as_ascii()
2876 }
2877
2878 /// Converts this string slice into a slice of [ASCII characters](ascii::Char),
2879 /// without checking whether they are valid.
2880 ///
2881 /// # Safety
2882 ///
2883 /// Every character in this string must be ASCII, or else this is UB.
2884 #[unstable(feature = "ascii_char", issue = "110998")]
2885 #[must_use]
2886 #[inline]
2887 #[cfg(not(feature = "ferrocene_subset"))]
2888 pub const unsafe fn as_ascii_unchecked(&self) -> &[ascii::Char] {
2889 assert_unsafe_precondition!(
2890 check_library_ub,
2891 "as_ascii_unchecked requires that the string is valid ASCII",
2892 (it: &str = self) => it.is_ascii()
2893 );
2894
2895 // SAFETY: the caller promised that every byte of this string slice
2896 // is ASCII.
2897 unsafe { self.as_bytes().as_ascii_unchecked() }
2898 }
2899
2900 /// Checks that two strings are an ASCII case-insensitive match.
2901 ///
2902 /// Same as `to_ascii_lowercase(a) == to_ascii_lowercase(b)`,
2903 /// but without allocating and copying temporaries.
2904 ///
2905 /// # Examples
2906 ///
2907 /// ```
2908 /// assert!("Ferris".eq_ignore_ascii_case("FERRIS"));
2909 /// assert!("Ferrös".eq_ignore_ascii_case("FERRöS"));
2910 /// assert!(!"Ferrös".eq_ignore_ascii_case("FERRÖS"));
2911 /// ```
2912 #[stable(feature = "ascii_methods_on_intrinsics", since = "1.23.0")]
2913 #[rustc_const_stable(feature = "const_eq_ignore_ascii_case", since = "1.89.0")]
2914 #[must_use]
2915 #[inline]
2916 pub const fn eq_ignore_ascii_case(&self, other: &str) -> bool {
2917 self.as_bytes().eq_ignore_ascii_case(other.as_bytes())
2918 }
2919
2920 /// Converts this string to its ASCII upper case equivalent in-place.
2921 ///
2922 /// ASCII letters 'a' to 'z' are mapped to 'A' to 'Z',
2923 /// but non-ASCII letters are unchanged.
2924 ///
2925 /// To return a new uppercased value without modifying the existing one, use
2926 /// [`to_ascii_uppercase()`].
2927 ///
2928 /// [`to_ascii_uppercase()`]: #method.to_ascii_uppercase
2929 ///
2930 /// # Examples
2931 ///
2932 /// ```
2933 /// let mut s = String::from("Grüße, Jürgen ❤");
2934 ///
2935 /// s.make_ascii_uppercase();
2936 ///
2937 /// assert_eq!("GRüßE, JüRGEN ❤", s);
2938 /// ```
2939 #[stable(feature = "ascii_methods_on_intrinsics", since = "1.23.0")]
2940 #[rustc_const_stable(feature = "const_make_ascii", since = "1.84.0")]
2941 #[inline]
2942 #[cfg(not(feature = "ferrocene_subset"))]
2943 pub const fn make_ascii_uppercase(&mut self) {
2944 // SAFETY: changing ASCII letters only does not invalidate UTF-8.
2945 let me = unsafe { self.as_bytes_mut() };
2946 me.make_ascii_uppercase()
2947 }
2948
2949 /// Converts this string to its ASCII lower case equivalent in-place.
2950 ///
2951 /// ASCII letters 'A' to 'Z' are mapped to 'a' to 'z',
2952 /// but non-ASCII letters are unchanged.
2953 ///
2954 /// To return a new lowercased value without modifying the existing one, use
2955 /// [`to_ascii_lowercase()`].
2956 ///
2957 /// [`to_ascii_lowercase()`]: #method.to_ascii_lowercase
2958 ///
2959 /// # Examples
2960 ///
2961 /// ```
2962 /// let mut s = String::from("GRÜßE, JÜRGEN ❤");
2963 ///
2964 /// s.make_ascii_lowercase();
2965 ///
2966 /// assert_eq!("grÜße, jÜrgen ❤", s);
2967 /// ```
2968 #[stable(feature = "ascii_methods_on_intrinsics", since = "1.23.0")]
2969 #[rustc_const_stable(feature = "const_make_ascii", since = "1.84.0")]
2970 #[inline]
2971 #[cfg(not(feature = "ferrocene_subset"))]
2972 pub const fn make_ascii_lowercase(&mut self) {
2973 // SAFETY: changing ASCII letters only does not invalidate UTF-8.
2974 let me = unsafe { self.as_bytes_mut() };
2975 me.make_ascii_lowercase()
2976 }
2977
2978 /// Returns a string slice with leading ASCII whitespace removed.
2979 ///
2980 /// 'Whitespace' refers to the definition used by
2981 /// [`u8::is_ascii_whitespace`].
2982 ///
2983 /// [`u8::is_ascii_whitespace`]: u8::is_ascii_whitespace
2984 ///
2985 /// # Examples
2986 ///
2987 /// ```
2988 /// assert_eq!(" \t \u{3000}hello world\n".trim_ascii_start(), "\u{3000}hello world\n");
2989 /// assert_eq!(" ".trim_ascii_start(), "");
2990 /// assert_eq!("".trim_ascii_start(), "");
2991 /// ```
2992 #[must_use = "this returns the trimmed string as a new slice, \
2993 without modifying the original"]
2994 #[stable(feature = "byte_slice_trim_ascii", since = "1.80.0")]
2995 #[rustc_const_stable(feature = "byte_slice_trim_ascii", since = "1.80.0")]
2996 #[inline]
2997 #[cfg(not(feature = "ferrocene_subset"))]
2998 pub const fn trim_ascii_start(&self) -> &str {
2999 // SAFETY: Removing ASCII characters from a `&str` does not invalidate
3000 // UTF-8.
3001 unsafe { core::str::from_utf8_unchecked(self.as_bytes().trim_ascii_start()) }
3002 }
3003
3004 /// Returns a string slice with trailing ASCII whitespace removed.
3005 ///
3006 /// 'Whitespace' refers to the definition used by
3007 /// [`u8::is_ascii_whitespace`].
3008 ///
3009 /// [`u8::is_ascii_whitespace`]: u8::is_ascii_whitespace
3010 ///
3011 /// # Examples
3012 ///
3013 /// ```
3014 /// assert_eq!("\r hello world\u{3000}\n ".trim_ascii_end(), "\r hello world\u{3000}");
3015 /// assert_eq!(" ".trim_ascii_end(), "");
3016 /// assert_eq!("".trim_ascii_end(), "");
3017 /// ```
3018 #[must_use = "this returns the trimmed string as a new slice, \
3019 without modifying the original"]
3020 #[stable(feature = "byte_slice_trim_ascii", since = "1.80.0")]
3021 #[rustc_const_stable(feature = "byte_slice_trim_ascii", since = "1.80.0")]
3022 #[inline]
3023 #[cfg(not(feature = "ferrocene_subset"))]
3024 pub const fn trim_ascii_end(&self) -> &str {
3025 // SAFETY: Removing ASCII characters from a `&str` does not invalidate
3026 // UTF-8.
3027 unsafe { core::str::from_utf8_unchecked(self.as_bytes().trim_ascii_end()) }
3028 }
3029
3030 /// Returns a string slice with leading and trailing ASCII whitespace
3031 /// removed.
3032 ///
3033 /// 'Whitespace' refers to the definition used by
3034 /// [`u8::is_ascii_whitespace`].
3035 ///
3036 /// [`u8::is_ascii_whitespace`]: u8::is_ascii_whitespace
3037 ///
3038 /// # Examples
3039 ///
3040 /// ```
3041 /// assert_eq!("\r hello world\n ".trim_ascii(), "hello world");
3042 /// assert_eq!(" ".trim_ascii(), "");
3043 /// assert_eq!("".trim_ascii(), "");
3044 /// ```
3045 #[must_use = "this returns the trimmed string as a new slice, \
3046 without modifying the original"]
3047 #[stable(feature = "byte_slice_trim_ascii", since = "1.80.0")]
3048 #[rustc_const_stable(feature = "byte_slice_trim_ascii", since = "1.80.0")]
3049 #[inline]
3050 #[cfg(not(feature = "ferrocene_subset"))]
3051 pub const fn trim_ascii(&self) -> &str {
3052 // SAFETY: Removing ASCII characters from a `&str` does not invalidate
3053 // UTF-8.
3054 unsafe { core::str::from_utf8_unchecked(self.as_bytes().trim_ascii()) }
3055 }
3056
3057 /// Returns an iterator that escapes each char in `self` with [`char::escape_debug`].
3058 ///
3059 /// Note: only extended grapheme codepoints that begin the string will be
3060 /// escaped.
3061 ///
3062 /// # Examples
3063 ///
3064 /// As an iterator:
3065 ///
3066 /// ```
3067 /// for c in "❤\n!".escape_debug() {
3068 /// print!("{c}");
3069 /// }
3070 /// println!();
3071 /// ```
3072 ///
3073 /// Using `println!` directly:
3074 ///
3075 /// ```
3076 /// println!("{}", "❤\n!".escape_debug());
3077 /// ```
3078 ///
3079 ///
3080 /// Both are equivalent to:
3081 ///
3082 /// ```
3083 /// println!("❤\\n!");
3084 /// ```
3085 ///
3086 /// Using `to_string`:
3087 ///
3088 /// ```
3089 /// assert_eq!("❤\n!".escape_debug().to_string(), "❤\\n!");
3090 /// ```
3091 #[must_use = "this returns the escaped string as an iterator, \
3092 without modifying the original"]
3093 #[stable(feature = "str_escape", since = "1.34.0")]
3094 #[cfg(not(feature = "ferrocene_subset"))]
3095 pub fn escape_debug(&self) -> EscapeDebug<'_> {
3096 let mut chars = self.chars();
3097 EscapeDebug {
3098 inner: chars
3099 .next()
3100 .map(|first| first.escape_debug_ext(EscapeDebugExtArgs::ESCAPE_ALL))
3101 .into_iter()
3102 .flatten()
3103 .chain(chars.flat_map(CharEscapeDebugContinue)),
3104 }
3105 }
3106
3107 /// Returns an iterator that escapes each char in `self` with [`char::escape_default`].
3108 ///
3109 /// # Examples
3110 ///
3111 /// As an iterator:
3112 ///
3113 /// ```
3114 /// for c in "❤\n!".escape_default() {
3115 /// print!("{c}");
3116 /// }
3117 /// println!();
3118 /// ```
3119 ///
3120 /// Using `println!` directly:
3121 ///
3122 /// ```
3123 /// println!("{}", "❤\n!".escape_default());
3124 /// ```
3125 ///
3126 ///
3127 /// Both are equivalent to:
3128 ///
3129 /// ```
3130 /// println!("\\u{{2764}}\\n!");
3131 /// ```
3132 ///
3133 /// Using `to_string`:
3134 ///
3135 /// ```
3136 /// assert_eq!("❤\n!".escape_default().to_string(), "\\u{2764}\\n!");
3137 /// ```
3138 #[must_use = "this returns the escaped string as an iterator, \
3139 without modifying the original"]
3140 #[stable(feature = "str_escape", since = "1.34.0")]
3141 #[cfg(not(feature = "ferrocene_subset"))]
3142 pub fn escape_default(&self) -> EscapeDefault<'_> {
3143 EscapeDefault { inner: self.chars().flat_map(CharEscapeDefault) }
3144 }
3145
3146 /// Returns an iterator that escapes each char in `self` with [`char::escape_unicode`].
3147 ///
3148 /// # Examples
3149 ///
3150 /// As an iterator:
3151 ///
3152 /// ```
3153 /// for c in "❤\n!".escape_unicode() {
3154 /// print!("{c}");
3155 /// }
3156 /// println!();
3157 /// ```
3158 ///
3159 /// Using `println!` directly:
3160 ///
3161 /// ```
3162 /// println!("{}", "❤\n!".escape_unicode());
3163 /// ```
3164 ///
3165 ///
3166 /// Both are equivalent to:
3167 ///
3168 /// ```
3169 /// println!("\\u{{2764}}\\u{{a}}\\u{{21}}");
3170 /// ```
3171 ///
3172 /// Using `to_string`:
3173 ///
3174 /// ```
3175 /// assert_eq!("❤\n!".escape_unicode().to_string(), "\\u{2764}\\u{a}\\u{21}");
3176 /// ```
3177 #[must_use = "this returns the escaped string as an iterator, \
3178 without modifying the original"]
3179 #[stable(feature = "str_escape", since = "1.34.0")]
3180 #[cfg(not(feature = "ferrocene_subset"))]
3181 pub fn escape_unicode(&self) -> EscapeUnicode<'_> {
3182 EscapeUnicode { inner: self.chars().flat_map(CharEscapeUnicode) }
3183 }
3184
3185 /// Returns the range that a substring points to.
3186 ///
3187 /// Returns `None` if `substr` does not point within `self`.
3188 ///
3189 /// Unlike [`str::find`], **this does not search through the string**.
3190 /// Instead, it uses pointer arithmetic to find where in the string
3191 /// `substr` is derived from.
3192 ///
3193 /// This is useful for extending [`str::split`] and similar methods.
3194 ///
3195 /// Note that this method may return false positives (typically either
3196 /// `Some(0..0)` or `Some(self.len()..self.len())`) if `substr` is a
3197 /// zero-length `str` that points at the beginning or end of another,
3198 /// independent, `str`.
3199 ///
3200 /// # Examples
3201 /// ```
3202 /// #![feature(substr_range)]
3203 ///
3204 /// let data = "a, b, b, a";
3205 /// let mut iter = data.split(", ").map(|s| data.substr_range(s).unwrap());
3206 ///
3207 /// assert_eq!(iter.next(), Some(0..1));
3208 /// assert_eq!(iter.next(), Some(3..4));
3209 /// assert_eq!(iter.next(), Some(6..7));
3210 /// assert_eq!(iter.next(), Some(9..10));
3211 /// ```
3212 #[must_use]
3213 #[unstable(feature = "substr_range", issue = "126769")]
3214 #[cfg(not(feature = "ferrocene_subset"))]
3215 pub fn substr_range(&self, substr: &str) -> Option<Range<usize>> {
3216 self.as_bytes().subslice_range(substr.as_bytes())
3217 }
3218
3219 /// Returns the same string as a string slice `&str`.
3220 ///
3221 /// This method is redundant when used directly on `&str`, but
3222 /// it helps dereferencing other string-like types to string slices,
3223 /// for example references to `Box<str>` or `Arc<str>`.
3224 #[inline]
3225 #[unstable(feature = "str_as_str", issue = "130366")]
3226 pub const fn as_str(&self) -> &str {
3227 self
3228 }
3229}
3230
3231#[stable(feature = "rust1", since = "1.0.0")]
3232#[rustc_const_unstable(feature = "const_convert", issue = "143773")]
3233impl const AsRef<[u8]> for str {
3234 #[inline]
3235 fn as_ref(&self) -> &[u8] {
3236 self.as_bytes()
3237 }
3238}
3239
3240#[stable(feature = "rust1", since = "1.0.0")]
3241#[rustc_const_unstable(feature = "const_default", issue = "143894")]
3242impl const Default for &str {
3243 /// Creates an empty str
3244 #[inline]
3245 fn default() -> Self {
3246 ""
3247 }
3248}
3249
3250#[stable(feature = "default_mut_str", since = "1.28.0")]
3251#[rustc_const_unstable(feature = "const_default", issue = "143894")]
3252#[cfg(not(feature = "ferrocene_subset"))]
3253impl const Default for &mut str {
3254 /// Creates an empty mutable str
3255 #[inline]
3256 fn default() -> Self {
3257 // SAFETY: The empty string is valid UTF-8.
3258 unsafe { from_utf8_unchecked_mut(&mut []) }
3259 }
3260}
3261
3262#[cfg(not(feature = "ferrocene_subset"))]
3263impl_fn_for_zst! {
3264 /// A nameable, cloneable fn type
3265 #[derive(Clone)]
3266 struct LinesMap impl<'a> Fn = |line: &'a str| -> &'a str {
3267 let Some(line) = line.strip_suffix('\n') else { return line };
3268 let Some(line) = line.strip_suffix('\r') else { return line };
3269 line
3270 };
3271
3272 #[derive(Clone)]
3273 struct CharEscapeDebugContinue impl Fn = |c: char| -> char::EscapeDebug {
3274 c.escape_debug_ext(EscapeDebugExtArgs {
3275 escape_grapheme_extended: false,
3276 escape_single_quote: true,
3277 escape_double_quote: true
3278 })
3279 };
3280
3281 #[derive(Clone)]
3282 struct CharEscapeUnicode impl Fn = |c: char| -> char::EscapeUnicode {
3283 c.escape_unicode()
3284 };
3285 #[derive(Clone)]
3286 struct CharEscapeDefault impl Fn = |c: char| -> char::EscapeDefault {
3287 c.escape_default()
3288 };
3289
3290 #[derive(Clone)]
3291 struct IsWhitespace impl Fn = |c: char| -> bool {
3292 c.is_whitespace()
3293 };
3294
3295 #[derive(Clone)]
3296 struct IsAsciiWhitespace impl Fn = |byte: &u8| -> bool {
3297 byte.is_ascii_whitespace()
3298 };
3299
3300 #[derive(Clone)]
3301 struct IsNotEmpty impl<'a, 'b> Fn = |s: &'a &'b str| -> bool {
3302 !s.is_empty()
3303 };
3304
3305 #[derive(Clone)]
3306 struct BytesIsNotEmpty impl<'a, 'b> Fn = |s: &'a &'b [u8]| -> bool {
3307 !s.is_empty()
3308 };
3309
3310 #[derive(Clone)]
3311 struct UnsafeBytesToStr impl<'a> Fn = |bytes: &'a [u8]| -> &'a str {
3312 // SAFETY: not safe
3313 unsafe { from_utf8_unchecked(bytes) }
3314 };
3315}
3316
3317// This is required to make `impl From<&str> for Box<dyn Error>` and `impl<E> From<E> for Box<dyn Error>` not overlap.
3318#[stable(feature = "error_in_core_neg_impl", since = "1.65.0")]
3319#[cfg(not(feature = "ferrocene_subset"))]
3320impl !crate::error::Error for &str {}