about summary refs log tree commit diff
path: root/src/libcore
diff options
context:
space:
mode:
authorAlex Crichton <alex@alexcrichton.com>2015-01-21 11:53:49 -0800
committerAlex Crichton <alex@alexcrichton.com>2015-01-21 11:53:49 -0800
commit886c6f3534e6f03916eeff2ea8b235e85dd04b42 (patch)
tree616ec48db83b768a4be84225bed9b0c0f730072d /src/libcore
parent036d8c41897099b5822eafa40e3f1fd2cdc4a92a (diff)
parent537889aa78c984ee6484d16fec4a67f35778aec6 (diff)
downloadrust-886c6f3534e6f03916eeff2ea8b235e85dd04b42.tar.gz
rust-886c6f3534e6f03916eeff2ea8b235e85dd04b42.zip
rollup merge of #21258: aturon/stab-3-index
Conflicts:
	src/libcore/ops.rs
	src/librustc_typeck/astconv.rs
	src/libstd/io/mem.rs
	src/libsyntax/parse/lexer/mod.rs
Diffstat (limited to 'src/libcore')
-rw-r--r--src/libcore/fmt/float.rs4
-rw-r--r--src/libcore/iter.rs104
-rw-r--r--src/libcore/ops.rs67
-rw-r--r--src/libcore/slice.rs68
-rw-r--r--src/libcore/str/mod.rs110
5 files changed, 164 insertions, 189 deletions
diff --git a/src/libcore/fmt/float.rs b/src/libcore/fmt/float.rs
index f1b9ebe6d90..245dc00d838 100644
--- a/src/libcore/fmt/float.rs
+++ b/src/libcore/fmt/float.rs
@@ -179,7 +179,7 @@ pub fn float_to_str_bytes_common<T: Float, U, F>(
         _ => ()
     }
 
-    buf.slice_to_mut(end).reverse();
+    buf[..end].reverse();
 
     // Remember start of the fractional digits.
     // Points one beyond end of buf if none get generated,
@@ -316,7 +316,7 @@ pub fn float_to_str_bytes_common<T: Float, U, F>(
 
             impl<'a> fmt::Writer for Filler<'a> {
                 fn write_str(&mut self, s: &str) -> fmt::Result {
-                    slice::bytes::copy_memory(self.buf.slice_from_mut(*self.end),
+                    slice::bytes::copy_memory(&mut self.buf[(*self.end)..],
                                               s.as_bytes());
                     *self.end += s.len();
                     Ok(())
diff --git a/src/libcore/iter.rs b/src/libcore/iter.rs
index 2a21ceef7a1..773ac99b0de 100644
--- a/src/libcore/iter.rs
+++ b/src/libcore/iter.rs
@@ -2715,63 +2715,93 @@ impl<A: Int> Iterator for RangeStepInclusive<A> {
     }
 }
 
-
-/// The `Step` trait identifies objects which can be stepped over in both
-/// directions. The `steps_between` function provides a way to
-/// compare two Step objects (it could be provided using `step()` and `Ord`,
-/// but the implementation would be so inefficient as to be useless).
-#[unstable = "design of range notation/iteration is in flux"]
-pub trait Step: Ord {
-    /// Change self to the next object.
-    fn step(&mut self);
-    /// Change self to the previous object.
-    fn step_back(&mut self);
-    /// The steps_between two step objects.
-    /// start should always be less than end, so the result should never be negative.
-    /// Return None if it is not possible to calculate steps_between without
-    /// overflow.
-    fn steps_between(start: &Self, end: &Self) -> Option<uint>;
-}
-
-macro_rules! step_impl {
+macro_rules! range_impl {
     ($($t:ty)*) => ($(
-        #[unstable = "Trait is unstable."]
-        impl Step for $t {
-            #[inline]
-            fn step(&mut self) { *self += 1; }
+        #[stable]
+        impl Iterator for ::ops::Range<$t> {
+            type Item = $t;
+
             #[inline]
-            fn step_back(&mut self) { *self -= 1; }
+            fn next(&mut self) -> Option<$t> {
+                if self.start < self.end {
+                    let result = self.start;
+                    self.start += 1;
+                    return Some(result);
+                }
+
+                return None;
+            }
+
             #[inline]
-            fn steps_between(start: &$t, end: &$t) -> Option<uint> {
-                debug_assert!(end >= start);
-                Some((*end - *start) as uint)
+            fn size_hint(&self) -> (uint, Option<uint>) {
+                debug_assert!(self.end >= self.start);
+                let hint = (self.end - self.start) as uint;
+                (hint, Some(hint))
             }
         }
+
+        #[stable]
+        impl ExactSizeIterator for ::ops::Range<$t> {}
     )*)
 }
 
-macro_rules! step_impl_no_between {
+macro_rules! range_impl_no_hint {
     ($($t:ty)*) => ($(
-        #[unstable = "Trait is unstable."]
-        impl Step for $t {
+        #[stable]
+        impl Iterator for ::ops::Range<$t> {
+            type Item = $t;
+
             #[inline]
-            fn step(&mut self) { *self += 1; }
+            fn next(&mut self) -> Option<$t> {
+                if self.start < self.end {
+                    let result = self.start;
+                    self.start += 1;
+                    return Some(result);
+                }
+
+                return None;
+            }
+        }
+    )*)
+}
+
+macro_rules! range_other_impls {
+    ($($t:ty)*) => ($(
+        #[stable]
+        impl DoubleEndedIterator for ::ops::Range<$t> {
             #[inline]
-            fn step_back(&mut self) { *self -= 1; }
+            fn next_back(&mut self) -> Option<$t> {
+                if self.start < self.end {
+                    self.end -= 1;
+                    return Some(self.end);
+                }
+
+                return None;
+            }
+        }
+
+        #[stable]
+        impl Iterator for ::ops::RangeFrom<$t> {
+            type Item = $t;
+
             #[inline]
-            fn steps_between(_start: &$t, _end: &$t) -> Option<uint> {
-                None
+            fn next(&mut self) -> Option<$t> {
+                let result = self.start;
+                self.start += 1;
+                debug_assert!(result < self.start);
+                return Some(result);
             }
         }
     )*)
 }
 
-step_impl!(uint u8 u16 u32 int i8 i16 i32);
+range_impl!(uint u8 u16 u32 int i8 i16 i32);
 #[cfg(target_pointer_width = "64")]
-step_impl!(u64 i64);
+range_impl!(u64 i64);
 #[cfg(target_pointer_width = "32")]
-step_impl_no_between!(u64 i64);
+range_impl_no_hint!(u64 i64);
 
+range_other_impls!(uint u8 u16 u32 u64 int i8 i16 i32 i64);
 
 /// An iterator that repeats an element endlessly
 #[derive(Clone)]
diff --git a/src/libcore/ops.rs b/src/libcore/ops.rs
index e15c1001f0e..372596cdd44 100644
--- a/src/libcore/ops.rs
+++ b/src/libcore/ops.rs
@@ -67,10 +67,7 @@
 
 #![stable]
 
-use clone::Clone;
-use iter::{Step, Iterator,DoubleEndedIterator,ExactSizeIterator};
 use marker::Sized;
-use option::Option::{self, Some, None};
 use fmt;
 
 /// The `Drop` trait is used to run some code when a value goes out of scope. This
@@ -898,10 +895,12 @@ shr_impl_all! { u8 u16 u32 u64 usize i8 i16 i32 i64 isize }
 /// }
 /// ```
 #[lang="index"]
+#[stable]
 pub trait Index<Index: ?Sized> {
     type Output: ?Sized;
 
     /// The method for the indexing (`Foo[Bar]`) operation
+    #[stable]
     fn index<'a>(&'a self, index: &Index) -> &'a Self::Output;
 }
 
@@ -934,17 +933,19 @@ pub trait Index<Index: ?Sized> {
 /// }
 /// ```
 #[lang="index_mut"]
+#[stable]
 pub trait IndexMut<Index: ?Sized> {
     type Output: ?Sized;
 
     /// The method for the indexing (`Foo[Bar]`) operation
+    #[stable]
     fn index_mut<'a>(&'a mut self, index: &Index) -> &'a mut Self::Output;
 }
 
 /// An unbounded range.
 #[derive(Copy, Clone, PartialEq, Eq)]
 #[lang="full_range"]
-#[unstable = "API still in development"]
+#[unstable = "may be renamed to RangeFull"]
 pub struct FullRange;
 
 #[stable]
@@ -957,7 +958,7 @@ impl fmt::Debug for FullRange {
 /// A (half-open) range which is bounded at both ends.
 #[derive(Copy, Clone, PartialEq, Eq)]
 #[lang="range"]
-#[unstable = "API still in development"]
+#[stable]
 pub struct Range<Idx> {
     /// The lower bound of the range (inclusive).
     pub start: Idx,
@@ -965,47 +966,6 @@ pub struct Range<Idx> {
     pub end: Idx,
 }
 
-#[unstable = "API still in development"]
-impl<Idx: Clone + Step> Iterator for Range<Idx> {
-    type Item = Idx;
-
-    #[inline]
-    fn next(&mut self) -> Option<Idx> {
-        if self.start < self.end {
-            let result = self.start.clone();
-            self.start.step();
-            return Some(result);
-        }
-
-        return None;
-    }
-
-    #[inline]
-    fn size_hint(&self) -> (uint, Option<uint>) {
-        if let Some(hint) = Step::steps_between(&self.start, &self.end) {
-            (hint, Some(hint))
-        } else {
-            (0, None)
-        }
-    }
-}
-
-#[unstable = "API still in development"]
-impl<Idx: Clone + Step> DoubleEndedIterator for Range<Idx> {
-    #[inline]
-    fn next_back(&mut self) -> Option<Idx> {
-        if self.start < self.end {
-            self.end.step_back();
-            return Some(self.end.clone());
-        }
-
-        return None;
-    }
-}
-
-#[unstable = "API still in development"]
-impl<Idx: Clone + Step> ExactSizeIterator for Range<Idx> {}
-
 #[stable]
 impl<Idx: fmt::Debug> fmt::Debug for Range<Idx> {
     fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
@@ -1016,24 +976,13 @@ impl<Idx: fmt::Debug> fmt::Debug for Range<Idx> {
 /// A range which is only bounded below.
 #[derive(Copy, Clone, PartialEq, Eq)]
 #[lang="range_from"]
-#[unstable = "API still in development"]
+#[stable]
 pub struct RangeFrom<Idx> {
     /// The lower bound of the range (inclusive).
     pub start: Idx,
 }
 
-#[unstable = "API still in development"]
-impl<Idx: Clone + Step> Iterator for RangeFrom<Idx> {
-    type Item = Idx;
 
-    #[inline]
-    fn next(&mut self) -> Option<Idx> {
-        // Deliberately overflow so we loop forever.
-        let result = self.start.clone();
-        self.start.step();
-        return Some(result);
-    }
-}
 
 #[stable]
 impl<Idx: fmt::Debug> fmt::Debug for RangeFrom<Idx> {
@@ -1045,7 +994,7 @@ impl<Idx: fmt::Debug> fmt::Debug for RangeFrom<Idx> {
 /// A range which is only bounded above.
 #[derive(Copy, Clone, PartialEq, Eq)]
 #[lang="range_to"]
-#[unstable = "API still in development"]
+#[stable]
 pub struct RangeTo<Idx> {
     /// The upper bound of the range (exclusive).
     pub end: Idx,
diff --git a/src/libcore/slice.rs b/src/libcore/slice.rs
index 1f3cfe3c75f..ec43a35248e 100644
--- a/src/libcore/slice.rs
+++ b/src/libcore/slice.rs
@@ -67,9 +67,6 @@ use raw::Slice as RawSlice;
 pub trait SliceExt {
     type Item;
 
-    fn slice<'a>(&'a self, start: uint, end: uint) -> &'a [Self::Item];
-    fn slice_from<'a>(&'a self, start: uint) -> &'a [Self::Item];
-    fn slice_to<'a>(&'a self, end: uint) -> &'a [Self::Item];
     fn split_at<'a>(&'a self, mid: uint) -> (&'a [Self::Item], &'a [Self::Item]);
     fn iter<'a>(&'a self) -> Iter<'a, Self::Item>;
     fn split<'a, P>(&'a self, pred: P) -> Split<'a, Self::Item, P>
@@ -93,9 +90,6 @@ pub trait SliceExt {
     fn is_empty(&self) -> bool { self.len() == 0 }
     fn get_mut<'a>(&'a mut self, index: uint) -> Option<&'a mut Self::Item>;
     fn as_mut_slice<'a>(&'a mut self) -> &'a mut [Self::Item];
-    fn slice_mut<'a>(&'a mut self, start: uint, end: uint) -> &'a mut [Self::Item];
-    fn slice_from_mut<'a>(&'a mut self, start: uint) -> &'a mut [Self::Item];
-    fn slice_to_mut<'a>(&'a mut self, end: uint) -> &'a mut [Self::Item];
     fn iter_mut<'a>(&'a mut self) -> IterMut<'a, Self::Item>;
     fn first_mut<'a>(&'a mut self) -> Option<&'a mut Self::Item>;
     fn tail_mut<'a>(&'a mut self) -> &'a mut [Self::Item];
@@ -136,28 +130,6 @@ impl<T> SliceExt for [T] {
     type Item = T;
 
     #[inline]
-    fn slice(&self, start: uint, end: uint) -> &[T] {
-        assert!(start <= end);
-        assert!(end <= self.len());
-        unsafe {
-            transmute(RawSlice {
-                data: self.as_ptr().offset(start as int),
-                len: (end - start)
-            })
-        }
-    }
-
-    #[inline]
-    fn slice_from(&self, start: uint) -> &[T] {
-        self.slice(start, self.len())
-    }
-
-    #[inline]
-    fn slice_to(&self, end: uint) -> &[T] {
-        self.slice(0, end)
-    }
-
-    #[inline]
     fn split_at(&self, mid: uint) -> (&[T], &[T]) {
         (&self[..mid], &self[mid..])
     }
@@ -291,20 +263,6 @@ impl<T> SliceExt for [T] {
     #[inline]
     fn as_mut_slice(&mut self) -> &mut [T] { self }
 
-    fn slice_mut(&mut self, start: uint, end: uint) -> &mut [T] {
-        ops::IndexMut::index_mut(self, &ops::Range { start: start, end: end } )
-    }
-
-    #[inline]
-    fn slice_from_mut(&mut self, start: uint) -> &mut [T] {
-        ops::IndexMut::index_mut(self, &ops::RangeFrom { start: start } )
-    }
-
-    #[inline]
-    fn slice_to_mut(&mut self, end: uint) -> &mut [T] {
-        ops::IndexMut::index_mut(self, &ops::RangeTo { end: end } )
-    }
-
     #[inline]
     fn split_at_mut(&mut self, mid: uint) -> (&mut [T], &mut [T]) {
         unsafe {
@@ -345,13 +303,13 @@ impl<T> SliceExt for [T] {
 
     #[inline]
     fn tail_mut(&mut self) -> &mut [T] {
-        self.slice_from_mut(1)
+        &mut self[1 ..]
     }
 
     #[inline]
     fn init_mut(&mut self) -> &mut [T] {
         let len = self.len();
-        self.slice_to_mut(len-1)
+        &mut self[.. (len - 1)]
     }
 
     #[inline]
@@ -483,7 +441,7 @@ impl<T> SliceExt for [T] {
         self.swap(j, i-1);
 
         // Step 4: Reverse the (previously) weakly decreasing part
-        self.slice_from_mut(i).reverse();
+        self[i..].reverse();
 
         true
     }
@@ -505,7 +463,7 @@ impl<T> SliceExt for [T] {
         }
 
         // Step 2: Reverse the weakly increasing part
-        self.slice_from_mut(i).reverse();
+        self[i..].reverse();
 
         // Step 3: Find the rightmost element equal to or bigger than the pivot (i-1)
         let mut j = self.len() - 1;
@@ -522,8 +480,8 @@ impl<T> SliceExt for [T] {
     #[inline]
     fn clone_from_slice(&mut self, src: &[T]) -> uint where T: Clone {
         let min = cmp::min(self.len(), src.len());
-        let dst = self.slice_to_mut(min);
-        let src = src.slice_to(min);
+        let dst = &mut self[.. min];
+        let src = &src[.. min];
         for i in range(0, min) {
             dst[i].clone_from(&src[i]);
         }
@@ -531,6 +489,7 @@ impl<T> SliceExt for [T] {
     }
 }
 
+#[stable]
 impl<T> ops::Index<uint> for [T] {
     type Output = T;
 
@@ -541,6 +500,7 @@ impl<T> ops::Index<uint> for [T] {
     }
 }
 
+#[stable]
 impl<T> ops::IndexMut<uint> for [T] {
     type Output = T;
 
@@ -551,6 +511,7 @@ impl<T> ops::IndexMut<uint> for [T] {
     }
 }
 
+#[stable]
 impl<T> ops::Index<ops::Range<uint>> for [T] {
     type Output = [T];
     #[inline]
@@ -565,6 +526,7 @@ impl<T> ops::Index<ops::Range<uint>> for [T] {
         }
     }
 }
+#[stable]
 impl<T> ops::Index<ops::RangeTo<uint>> for [T] {
     type Output = [T];
     #[inline]
@@ -572,6 +534,7 @@ impl<T> ops::Index<ops::RangeTo<uint>> for [T] {
         self.index(&ops::Range{ start: 0, end: index.end })
     }
 }
+#[stable]
 impl<T> ops::Index<ops::RangeFrom<uint>> for [T] {
     type Output = [T];
     #[inline]
@@ -579,6 +542,7 @@ impl<T> ops::Index<ops::RangeFrom<uint>> for [T] {
         self.index(&ops::Range{ start: index.start, end: self.len() })
     }
 }
+#[stable]
 impl<T> ops::Index<ops::FullRange> for [T] {
     type Output = [T];
     #[inline]
@@ -587,6 +551,7 @@ impl<T> ops::Index<ops::FullRange> for [T] {
     }
 }
 
+#[stable]
 impl<T> ops::IndexMut<ops::Range<uint>> for [T] {
     type Output = [T];
     #[inline]
@@ -601,6 +566,7 @@ impl<T> ops::IndexMut<ops::Range<uint>> for [T] {
         }
     }
 }
+#[stable]
 impl<T> ops::IndexMut<ops::RangeTo<uint>> for [T] {
     type Output = [T];
     #[inline]
@@ -608,6 +574,7 @@ impl<T> ops::IndexMut<ops::RangeTo<uint>> for [T] {
         self.index_mut(&ops::Range{ start: 0, end: index.end })
     }
 }
+#[stable]
 impl<T> ops::IndexMut<ops::RangeFrom<uint>> for [T] {
     type Output = [T];
     #[inline]
@@ -616,6 +583,7 @@ impl<T> ops::IndexMut<ops::RangeFrom<uint>> for [T] {
         self.index_mut(&ops::Range{ start: index.start, end: len })
     }
 }
+#[stable]
 impl<T> ops::IndexMut<ops::FullRange> for [T] {
     type Output = [T];
     #[inline]
@@ -1051,7 +1019,7 @@ impl<'a, T, P> Iterator for SplitMut<'a, T, P> where P: FnMut(&T) -> bool {
             Some(idx) => {
                 let tmp = mem::replace(&mut self.v, &mut []);
                 let (head, tail) = tmp.split_at_mut(idx);
-                self.v = tail.slice_from_mut(1);
+                self.v = &mut tail[1..];
                 Some(head)
             }
         }
@@ -1087,7 +1055,7 @@ impl<'a, T, P> DoubleEndedIterator for SplitMut<'a, T, P> where
                 let tmp = mem::replace(&mut self.v, &mut []);
                 let (head, tail) = tmp.split_at_mut(idx);
                 self.v = head;
-                Some(tail.slice_from_mut(1))
+                Some(&mut tail[1..])
             }
         }
     }
diff --git a/src/libcore/str/mod.rs b/src/libcore/str/mod.rs
index 6bb9ddf750b..bdac686cb66 100644
--- a/src/libcore/str/mod.rs
+++ b/src/libcore/str/mod.rs
@@ -928,13 +928,13 @@ impl<'a> Iterator for SplitStr<'a> {
 
         match self.it.next() {
             Some((from, to)) => {
-                let ret = Some(self.it.haystack.slice(self.last_end, from));
+                let ret = Some(&self.it.haystack[self.last_end .. from]);
                 self.last_end = to;
                 ret
             }
             None => {
                 self.finished = true;
-                Some(self.it.haystack.slice(self.last_end, self.it.haystack.len()))
+                Some(&self.it.haystack[self.last_end .. self.it.haystack.len()])
             }
         }
     }
@@ -1141,27 +1141,90 @@ mod traits {
         }
     }
 
+    /// Returns a slice of the given string from the byte range
+    /// [`begin`..`end`).
+    ///
+    /// This operation is `O(1)`.
+    ///
+    /// Panics when `begin` and `end` do not point to valid characters
+    /// or point beyond the last character of the string.
+    ///
+    /// # Example
+    ///
+    /// ```rust
+    /// let s = "Löwe 老虎 Léopard";
+    /// assert_eq!(&s[0 .. 1], "L");
+    ///
+    /// assert_eq!(&s[1 .. 9], "öwe 老");
+    ///
+    /// // these will panic:
+    /// // byte 2 lies within `ö`:
+    /// // &s[2 ..3];
+    ///
+    /// // byte 8 lies within `老`
+    /// // &s[1 .. 8];
+    ///
+    /// // byte 100 is outside the string
+    /// // &s[3 .. 100];
+    /// ```
+    #[stable]
     impl ops::Index<ops::Range<uint>> for str {
         type Output = str;
         #[inline]
         fn index(&self, index: &ops::Range<uint>) -> &str {
-            self.slice(index.start, index.end)
+            // is_char_boundary checks that the index is in [0, .len()]
+            if index.start <= index.end &&
+               self.is_char_boundary(index.start) &&
+               self.is_char_boundary(index.end) {
+                unsafe { self.slice_unchecked(index.start, index.end) }
+            } else {
+                super::slice_error_fail(self, index.start, index.end)
+            }
         }
     }
+
+    /// Returns a slice of the string from the beginning to byte
+    /// `end`.
+    ///
+    /// Equivalent to `self[0 .. end]`.
+    ///
+    /// Panics when `end` does not point to a valid character, or is
+    /// out of bounds.
+    #[stable]
     impl ops::Index<ops::RangeTo<uint>> for str {
         type Output = str;
         #[inline]
         fn index(&self, index: &ops::RangeTo<uint>) -> &str {
-            self.slice_to(index.end)
+            // is_char_boundary checks that the index is in [0, .len()]
+            if self.is_char_boundary(index.end) {
+                unsafe { self.slice_unchecked(0, index.end) }
+            } else {
+                super::slice_error_fail(self, 0, index.end)
+            }
         }
     }
+
+    /// Returns a slice of the string from `begin` to its end.
+    ///
+    /// Equivalent to `self[begin .. self.len()]`.
+    ///
+    /// Panics when `begin` does not point to a valid character, or is
+    /// out of bounds.
+    #[stable]
     impl ops::Index<ops::RangeFrom<uint>> for str {
         type Output = str;
         #[inline]
         fn index(&self, index: &ops::RangeFrom<uint>) -> &str {
-            self.slice_from(index.start)
+            // is_char_boundary checks that the index is in [0, .len()]
+            if self.is_char_boundary(index.start) {
+                unsafe { self.slice_unchecked(index.start, self.len()) }
+            } else {
+                super::slice_error_fail(self, index.start, self.len())
+            }
         }
     }
+
+    #[stable]
     impl ops::Index<ops::FullRange> for str {
         type Output = str;
         #[inline]
@@ -1234,9 +1297,6 @@ pub trait StrExt {
     fn lines<'a>(&'a self) -> Lines<'a>;
     fn lines_any<'a>(&'a self) -> LinesAny<'a>;
     fn char_len(&self) -> uint;
-    fn slice<'a>(&'a self, begin: uint, end: uint) -> &'a str;
-    fn slice_from<'a>(&'a self, begin: uint) -> &'a str;
-    fn slice_to<'a>(&'a self, end: uint) -> &'a str;
     fn slice_chars<'a>(&'a self, begin: uint, end: uint) -> &'a str;
     unsafe fn slice_unchecked<'a>(&'a self, begin: uint, end: uint) -> &'a str;
     fn starts_with(&self, pat: &str) -> bool;
@@ -1358,7 +1418,7 @@ impl StrExt for str {
     fn lines_any(&self) -> LinesAny {
         fn f(line: &str) -> &str {
             let l = line.len();
-            if l > 0 && line.as_bytes()[l - 1] == b'\r' { line.slice(0, l - 1) }
+            if l > 0 && line.as_bytes()[l - 1] == b'\r' { &line[0 .. l - 1] }
             else { line }
         }
 
@@ -1369,38 +1429,6 @@ impl StrExt for str {
     #[inline]
     fn char_len(&self) -> uint { self.chars().count() }
 
-    #[inline]
-    fn slice(&self, begin: uint, end: uint) -> &str {
-        // is_char_boundary checks that the index is in [0, .len()]
-        if begin <= end &&
-           self.is_char_boundary(begin) &&
-           self.is_char_boundary(end) {
-            unsafe { self.slice_unchecked(begin, end) }
-        } else {
-            slice_error_fail(self, begin, end)
-        }
-    }
-
-    #[inline]
-    fn slice_from(&self, begin: uint) -> &str {
-        // is_char_boundary checks that the index is in [0, .len()]
-        if self.is_char_boundary(begin) {
-            unsafe { self.slice_unchecked(begin, self.len()) }
-        } else {
-            slice_error_fail(self, begin, self.len())
-        }
-    }
-
-    #[inline]
-    fn slice_to(&self, end: uint) -> &str {
-        // is_char_boundary checks that the index is in [0, .len()]
-        if self.is_char_boundary(end) {
-            unsafe { self.slice_unchecked(0, end) }
-        } else {
-            slice_error_fail(self, 0, end)
-        }
-    }
-
     fn slice_chars(&self, begin: uint, end: uint) -> &str {
         assert!(begin <= end);
         let mut count = 0;