Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 32 additions & 0 deletions library/core/src/slice/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2725,6 +2725,38 @@ impl<T> [T] {
None
}

/// Returns a subslice with the prefix and suffix removed.
///
/// If the slice starts with `prefix` and ends with `suffix`, returns the subslice after the
/// prefix and before the suffix, wrapped in `Some`.
///
/// If the slice does not start with `prefix` or does not end with `suffix`, returns `None`.
///
/// # Examples
///
/// ```
/// #![feature(strip_circumfix)]
///
/// let v = &[10, 50, 40, 30];
/// assert_eq!(v.strip_circumfix(&[10], &[30]), Some(&[50, 40][..]));
/// assert_eq!(v.strip_circumfix(&[10], &[40, 30]), Some(&[50][..]));
/// assert_eq!(v.strip_circumfix(&[10, 50], &[40, 30]), Some(&[][..]));
/// assert_eq!(v.strip_circumfix(&[50], &[30]), None);
/// assert_eq!(v.strip_circumfix(&[10], &[40]), None);
/// assert_eq!(v.strip_circumfix(&[], &[40, 30]), Some(&[10, 50][..]));
/// assert_eq!(v.strip_circumfix(&[10, 50], &[]), Some(&[40, 30][..]));
/// ```
#[must_use = "returns the subslice without modifying the original"]
#[unstable(feature = "strip_circumfix", issue = "147946")]
pub fn strip_circumfix<S, P>(&self, prefix: &P, suffix: &S) -> Option<&[T]>
where
T: PartialEq,
S: SlicePattern<Item = T> + ?Sized,
P: SlicePattern<Item = T> + ?Sized,
{
self.strip_prefix(prefix)?.strip_suffix(suffix)
}

/// Returns a subslice with the optional prefix removed.
///
/// If the slice starts with `prefix`, returns the subslice after the prefix. If `prefix`
Expand Down
36 changes: 36 additions & 0 deletions library/core/src/str/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2447,6 +2447,42 @@ impl str {
suffix.strip_suffix_of(self)
}

/// Returns a string slice with the prefix and suffix removed.
///
/// If the string starts with the pattern `prefix` and ends with the pattern `suffix`, returns
/// the substring after the prefix and before the suffix, wrapped in `Some`.
/// Unlike [`trim_start_matches`] and [`trim_end_matches`], this method removes both the prefix
/// and suffix exactly once.
///
/// If the string does not start with `prefix` or does not end with `suffix`, returns `None`.
///
/// Each [pattern] can be a `&str`, [`char`], a slice of [`char`]s, or a
/// function or closure that determines if a character matches.
///
/// [`char`]: prim@char
/// [pattern]: self::pattern
/// [`trim_start_matches`]: Self::trim_start_matches
/// [`trim_end_matches`]: Self::trim_end_matches
///
/// # Examples
///
/// ```
/// #![feature(strip_circumfix)]
///
/// assert_eq!("bar:hello:foo".strip_circumfix("bar:", ":foo"), Some("hello"));
/// assert_eq!("bar:foo".strip_circumfix("foo", "foo"), None);
/// assert_eq!("foo:bar;".strip_circumfix("foo:", ';'), Some("bar"));
/// ```
#[must_use = "this returns the remaining substring as a new slice, \
without modifying the original"]
#[unstable(feature = "strip_circumfix", issue = "147946")]
pub fn strip_circumfix<P: Pattern, S: Pattern>(&self, prefix: P, suffix: S) -> Option<&str>
where
for<'a> S::Searcher<'a>: ReverseSearcher<'a>,
{
self.strip_prefix(prefix)?.strip_suffix(suffix)
}

/// Returns a string slice with the optional prefix removed.
///
/// If the string starts with the pattern `prefix`, returns the substring after the prefix.
Expand Down
Loading