From de2f61740d4622f3938cb6ddb01854c80c1e9082 Mon Sep 17 00:00:00 2001 From: Oliver Middleton Date: Sat, 19 Nov 2016 18:43:41 +0000 Subject: [PATCH 1/2] Optimise Chars::last() The default implementation of last() goes through the entire iterator but that's not needed here. --- src/libcollectionstest/str.rs | 8 ++++++++ src/libcore/str/mod.rs | 6 ++++++ 2 files changed, 14 insertions(+) diff --git a/src/libcollectionstest/str.rs b/src/libcollectionstest/str.rs index cc56bbf4890aa..a13e1fb33d159 100644 --- a/src/libcollectionstest/str.rs +++ b/src/libcollectionstest/str.rs @@ -814,6 +814,14 @@ fn test_iterator_clone() { assert!(it.clone().zip(it).all(|(x,y)| x == y)); } +#[test] +fn test_iterator_last() { + let s = "ศไทย中华Việt Nam"; + let mut it = s.chars(); + it.next(); + assert_eq!(it.last(), Some('m')); +} + #[test] fn test_bytesator() { let s = "ศไทย中华Việt Nam"; diff --git a/src/libcore/str/mod.rs b/src/libcore/str/mod.rs index 196750254af30..1dfd00e11aa96 100644 --- a/src/libcore/str/mod.rs +++ b/src/libcore/str/mod.rs @@ -432,6 +432,12 @@ impl<'a> Iterator for Chars<'a> { // `isize::MAX` (that's well below `usize::MAX`). ((len + 3) / 4, Some(len)) } + + #[inline] + fn last(mut self) -> Option { + // No need to go through the entire string. + self.next_back() + } } #[stable(feature = "rust1", since = "1.0.0")] From 9e86e18092174b43514816c4bdeeafe8b518553f Mon Sep 17 00:00:00 2001 From: Oliver Middleton Date: Sun, 20 Nov 2016 00:37:48 +0000 Subject: [PATCH 2/2] Optimise CharIndices::last() The default implementation of last() goes through the entire iterator but that's not needed here. --- src/libcollectionstest/str.rs | 8 ++++++++ src/libcore/str/mod.rs | 6 ++++++ 2 files changed, 14 insertions(+) diff --git a/src/libcollectionstest/str.rs b/src/libcollectionstest/str.rs index a13e1fb33d159..ebbfbefc21b66 100644 --- a/src/libcollectionstest/str.rs +++ b/src/libcollectionstest/str.rs @@ -919,6 +919,14 @@ fn test_char_indices_revator() { assert_eq!(pos, p.len()); } +#[test] +fn test_char_indices_last() { + let s = "ศไทย中华Việt Nam"; + let mut it = s.char_indices(); + it.next(); + assert_eq!(it.last(), Some((27, 'm'))); +} + #[test] fn test_splitn_char_iterator() { let data = "\nMäry häd ä little lämb\nLittle lämb\n"; diff --git a/src/libcore/str/mod.rs b/src/libcore/str/mod.rs index 1dfd00e11aa96..1bd6188f4875a 100644 --- a/src/libcore/str/mod.rs +++ b/src/libcore/str/mod.rs @@ -511,6 +511,12 @@ impl<'a> Iterator for CharIndices<'a> { fn size_hint(&self) -> (usize, Option) { self.iter.size_hint() } + + #[inline] + fn last(mut self) -> Option<(usize, char)> { + // No need to go through the entire string. + self.next_back() + } } #[stable(feature = "rust1", since = "1.0.0")]