Skip to content

Commit

Permalink
auto merge of rust-lang#16332 : brson/rust/slicestab, r=aturon
Browse files Browse the repository at this point in the history
This implements some of the recommendations from https://github.com/rust-lang/meeting-minutes/blob/master/Meeting-API-review-2014-08-06.md.

Explanation in commits.
  • Loading branch information
bors committed Aug 14, 2014
2 parents 9d45d63 + fce442e commit 385c39a
Show file tree
Hide file tree
Showing 65 changed files with 450 additions and 210 deletions.
2 changes: 1 addition & 1 deletion src/compiletest/header.rs
Original file line number Diff line number Diff line change
Expand Up @@ -233,7 +233,7 @@ fn parse_exec_env(line: &str) -> Option<(String, String)> {
parse_name_value_directive(line, "exec-env").map(|nv| {
// nv is either FOO or FOO=BAR
let mut strs: Vec<String> = nv.as_slice()
.splitn('=', 1)
.splitn(1, '=')
.map(|s| s.to_string())
.collect();

Expand Down
46 changes: 25 additions & 21 deletions src/etc/unicode.py
Original file line number Diff line number Diff line change
Expand Up @@ -293,13 +293,12 @@ def emit_bsearch_range_table(f):
f.write("""
fn bsearch_range_table(c: char, r: &'static [(char,char)]) -> bool {
use core::cmp::{Equal, Less, Greater};
use core::slice::ImmutableVector;
use core::option::None;
r.bsearch(|&(lo,hi)| {
use core::slice::ImmutableSlice;
r.binary_search(|&(lo,hi)| {
if lo <= c && c <= hi { Equal }
else if hi < c { Less }
else { Greater }
}) != None
}).found().is_some()
}\n
""")

Expand Down Expand Up @@ -352,9 +351,10 @@ def emit_conversions_module(f, lowerupper, upperlower):
f.write("pub mod conversions {")
f.write("""
use core::cmp::{Equal, Less, Greater};
use core::slice::ImmutableVector;
use core::slice::ImmutableSlice;
use core::tuple::Tuple2;
use core::option::{Option, Some, None};
use core::slice;
pub fn to_lower(c: char) -> char {
match bsearch_case_table(c, LuLl_table) {
Expand All @@ -371,11 +371,14 @@ def emit_conversions_module(f, lowerupper, upperlower):
}
fn bsearch_case_table(c: char, table: &'static [(char, char)]) -> Option<uint> {
table.bsearch(|&(key, _)| {
match table.binary_search(|&(key, _)| {
if c == key { Equal }
else if key < c { Less }
else { Greater }
})
}) {
slice::Found(i) => Some(i),
slice::NotFound(_) => None,
}
}
""")
Expand All @@ -387,8 +390,8 @@ def emit_conversions_module(f, lowerupper, upperlower):

def emit_grapheme_module(f, grapheme_table, grapheme_cats):
f.write("""pub mod grapheme {
use core::option::{Some, None};
use core::slice::ImmutableVector;
use core::slice::ImmutableSlice;
use core::slice;
#[allow(non_camel_case_types)]
#[deriving(Clone)]
Expand All @@ -400,16 +403,16 @@ def emit_grapheme_module(f, grapheme_table, grapheme_cats):
fn bsearch_range_value_table(c: char, r: &'static [(char, char, GraphemeCat)]) -> GraphemeCat {
use core::cmp::{Equal, Less, Greater};
match r.bsearch(|&(lo, hi, _)| {
match r.binary_search(|&(lo, hi, _)| {
if lo <= c && c <= hi { Equal }
else if hi < c { Less }
else { Greater }
}) {
Some(idx) => {
slice::Found(idx) => {
let (_, _, cat) = r[idx];
cat
}
None => GC_Any
slice::NotFound(_) => GC_Any
}
}
Expand All @@ -427,20 +430,21 @@ def emit_grapheme_module(f, grapheme_table, grapheme_cats):
def emit_charwidth_module(f, width_table):
f.write("pub mod charwidth {\n")
f.write(" use core::option::{Option, Some, None};\n")
f.write(" use core::slice::ImmutableVector;\n")
f.write(" use core::slice::ImmutableSlice;\n")
f.write(" use core::slice;\n")
f.write("""
fn bsearch_range_value_table(c: char, is_cjk: bool, r: &'static [(char, char, u8, u8)]) -> u8 {
use core::cmp::{Equal, Less, Greater};
match r.bsearch(|&(lo, hi, _, _)| {
match r.binary_search(|&(lo, hi, _, _)| {
if lo <= c && c <= hi { Equal }
else if hi < c { Less }
else { Greater }
}) {
Some(idx) => {
slice::Found(idx) => {
let (_, _, r_ncjk, r_cjk) = r[idx];
if is_cjk { r_cjk } else { r_ncjk }
}
None => 1
slice::NotFound(_) => 1
}
}
""")
Expand Down Expand Up @@ -525,19 +529,19 @@ def comp_pfun(char):

f.write("""
fn bsearch_range_value_table(c: char, r: &'static [(char, char, u8)]) -> u8 {
use core::option::{Some, None};
use core::cmp::{Equal, Less, Greater};
use core::slice::ImmutableVector;
match r.bsearch(|&(lo, hi, _)| {
use core::slice::ImmutableSlice;
use core::slice;
match r.binary_search(|&(lo, hi, _)| {
if lo <= c && c <= hi { Equal }
else if hi < c { Less }
else { Greater }
}) {
Some(idx) => {
slice::Found(idx) => {
let (_, _, result) = r[idx];
result
}
None => 0
slice::NotFound(_) => 0
}
}\n
""")
Expand Down
2 changes: 1 addition & 1 deletion src/libcollections/hash/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -296,7 +296,7 @@ mod tests {
use std::prelude::*;
use std::mem;

use slice::ImmutableVector;
use slice::ImmutableSlice;
use super::{Hash, Hasher, Writer};

struct MyWriterHasher;
Expand Down
2 changes: 1 addition & 1 deletion src/libcollections/hash/sip.rs
Original file line number Diff line number Diff line change
Expand Up @@ -275,7 +275,7 @@ mod tests {

use str::Str;
use string::String;
use slice::{Vector, ImmutableVector};
use slice::{Slice, ImmutableSlice};
use vec::Vec;

use super::super::{Hash, Writer};
Expand Down
2 changes: 2 additions & 0 deletions src/libcollections/ringbuf.rs
Original file line number Diff line number Diff line change
Expand Up @@ -362,6 +362,7 @@ pub struct MutItems<'a, T> {

impl<'a, T> Iterator<&'a mut T> for MutItems<'a, T> {
#[inline]
#[allow(deprecated)] // mut_shift_ref
fn next(&mut self) -> Option<&'a mut T> {
if self.nelts == 0 {
return None;
Expand All @@ -384,6 +385,7 @@ impl<'a, T> Iterator<&'a mut T> for MutItems<'a, T> {

impl<'a, T> DoubleEndedIterator<&'a mut T> for MutItems<'a, T> {
#[inline]
#[allow(deprecated)] // mut_shift_ref
fn next_back(&mut self) -> Option<&'a mut T> {
if self.nelts == 0 {
return None;
Expand Down
21 changes: 11 additions & 10 deletions src/libcollections/slice.rs
Original file line number Diff line number Diff line change
Expand Up @@ -45,8 +45,8 @@ represents iteration over a slice.
## Traits
A number of traits add methods that allow you to accomplish tasks with slices.
These traits include `ImmutableVector`, which is defined for `&[T]` types,
and `MutableVector`, defined for `&mut [T]` types.
These traits include `ImmutableSlice`, which is defined for `&[T]` types,
and `MutableSlice`, defined for `&mut [T]` types.
An example is the method `.slice(a, b)` that returns an immutable "view" into
a `Vec` or another slice from the index interval `[a, b)`:
Expand Down Expand Up @@ -98,10 +98,11 @@ use {Collection, MutableSeq};
use vec::Vec;

pub use core::slice::{ref_slice, mut_ref_slice, Splits, Windows};
pub use core::slice::{Chunks, Vector, ImmutableVector, ImmutableEqVector};
pub use core::slice::{ImmutableOrdVector, MutableVector, Items, MutItems};
pub use core::slice::{Chunks, Slice, ImmutableSlice, ImmutablePartialEqSlice};
pub use core::slice::{ImmutableOrdSlice, MutableSlice, Items, MutItems};
pub use core::slice::{MutSplits, MutChunks};
pub use core::slice::{bytes, MutableCloneableVector};
pub use core::slice::{bytes, MutableCloneableSlice};
pub use core::slice::{BinarySearchResult, Found, NotFound};

// Functional utilities

Expand All @@ -116,7 +117,7 @@ pub trait VectorVector<T> {
fn connect_vec(&self, sep: &T) -> Vec<T>;
}

impl<'a, T: Clone, V: Vector<T>> VectorVector<T> for &'a [V] {
impl<'a, T: Clone, V: Slice<T>> VectorVector<T> for &'a [V] {
fn concat_vec(&self) -> Vec<T> {
let size = self.iter().fold(0u, |acc, v| acc + v.as_slice().len());
let mut result = Vec::with_capacity(size);
Expand Down Expand Up @@ -558,7 +559,7 @@ fn merge_sort<T>(v: &mut [T], compare: |&T, &T| -> Ordering) {

/// Extension methods for vectors such that their elements are
/// mutable.
pub trait MutableVectorAllocating<'a, T> {
pub trait MutableSliceAllocating<'a, T> {
/// Sort the vector, in place, using `compare` to compare
/// elements.
///
Expand Down Expand Up @@ -604,7 +605,7 @@ pub trait MutableVectorAllocating<'a, T> {
fn move_from(self, src: Vec<T>, start: uint, end: uint) -> uint;
}

impl<'a,T> MutableVectorAllocating<'a, T> for &'a mut [T] {
impl<'a,T> MutableSliceAllocating<'a, T> for &'a mut [T] {
#[inline]
fn sort_by(self, compare: |&T, &T| -> Ordering) {
merge_sort(self, compare)
Expand All @@ -621,7 +622,7 @@ impl<'a,T> MutableVectorAllocating<'a, T> for &'a mut [T] {

/// Methods for mutable vectors with orderable elements, such as
/// in-place sorting.
pub trait MutableOrdVector<T> {
pub trait MutableOrdSlice<T> {
/// Sort the vector, in place.
///
/// This is equivalent to `self.sort_by(|a, b| a.cmp(b))`.
Expand Down Expand Up @@ -667,7 +668,7 @@ pub trait MutableOrdVector<T> {
fn prev_permutation(self) -> bool;
}

impl<'a, T: Ord> MutableOrdVector<T> for &'a mut [T] {
impl<'a, T: Ord> MutableOrdSlice<T> for &'a mut [T] {
#[inline]
fn sort(self) {
self.sort_by(|a,b| a.cmp(b))
Expand Down
18 changes: 9 additions & 9 deletions src/libcollections/str.rs
Original file line number Diff line number Diff line change
Expand Up @@ -894,7 +894,7 @@ mod tests {
use {Collection, MutableSeq};

use super::*;
use std::slice::{Vector, ImmutableVector};
use std::slice::{Slice, ImmutableSlice};
use string::String;
use vec::Vec;

Expand Down Expand Up @@ -1812,38 +1812,38 @@ mod tests {
fn test_splitn_char_iterator() {
let data = "\nMäry häd ä little lämb\nLittle lämb\n";

let split: Vec<&str> = data.splitn(' ', 3).collect();
let split: Vec<&str> = data.splitn(3, ' ').collect();
assert_eq!(split, vec!["\nMäry", "häd", "ä", "little lämb\nLittle lämb\n"]);

let split: Vec<&str> = data.splitn(|c: char| c == ' ', 3).collect();
let split: Vec<&str> = data.splitn(3, |c: char| c == ' ').collect();
assert_eq!(split, vec!["\nMäry", "häd", "ä", "little lämb\nLittle lämb\n"]);

// Unicode
let split: Vec<&str> = data.splitn('ä', 3).collect();
let split: Vec<&str> = data.splitn(3, 'ä').collect();
assert_eq!(split, vec!["\nM", "ry h", "d ", " little lämb\nLittle lämb\n"]);

let split: Vec<&str> = data.splitn(|c: char| c == 'ä', 3).collect();
let split: Vec<&str> = data.splitn(3, |c: char| c == 'ä').collect();
assert_eq!(split, vec!["\nM", "ry h", "d ", " little lämb\nLittle lämb\n"]);
}

#[test]
fn test_rsplitn_char_iterator() {
let data = "\nMäry häd ä little lämb\nLittle lämb\n";

let mut split: Vec<&str> = data.rsplitn(' ', 3).collect();
let mut split: Vec<&str> = data.rsplitn(3, ' ').collect();
split.reverse();
assert_eq!(split, vec!["\nMäry häd ä", "little", "lämb\nLittle", "lämb\n"]);

let mut split: Vec<&str> = data.rsplitn(|c: char| c == ' ', 3).collect();
let mut split: Vec<&str> = data.rsplitn(3, |c: char| c == ' ').collect();
split.reverse();
assert_eq!(split, vec!["\nMäry häd ä", "little", "lämb\nLittle", "lämb\n"]);

// Unicode
let mut split: Vec<&str> = data.rsplitn('ä', 3).collect();
let mut split: Vec<&str> = data.rsplitn(3, 'ä').collect();
split.reverse();
assert_eq!(split, vec!["\nMäry häd ", " little l", "mb\nLittle l", "mb\n"]);

let mut split: Vec<&str> = data.rsplitn(|c: char| c == 'ä', 3).collect();
let mut split: Vec<&str> = data.rsplitn(3, |c: char| c == 'ä').collect();
split.reverse();
assert_eq!(split, vec!["\nMäry häd ", " little l", "mb\nLittle l", "mb\n"]);
}
Expand Down
13 changes: 8 additions & 5 deletions src/libcollections/string.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,12 +18,15 @@ use core::default::Default;
use core::fmt;
use core::mem;
use core::ptr;
use core::raw::Slice;
// FIXME: ICE's abound if you import the `Slice` type while importing `Slice` trait
use RawSlice = core::raw::Slice;
use core::slice::Slice;

use {Collection, Mutable, MutableSeq};
use hash;
use str;
use str::{CharRange, StrAllocating, MaybeOwned, Owned, Slice};
use str::{CharRange, StrAllocating, MaybeOwned, Owned};
use MaybeOwnedSlice = str::Slice; // So many `Slice`s...
use vec::Vec;

/// A growable string stored as a UTF-8 encoded buffer.
Expand Down Expand Up @@ -130,15 +133,15 @@ impl String {
/// ```
pub fn from_utf8_lossy<'a>(v: &'a [u8]) -> MaybeOwned<'a> {
if str::is_utf8(v) {
return Slice(unsafe { mem::transmute(v) })
return MaybeOwnedSlice(unsafe { mem::transmute(v) })
}

static TAG_CONT_U8: u8 = 128u8;
static REPLACEMENT: &'static [u8] = b"\xEF\xBF\xBD"; // U+FFFD in UTF-8
let mut i = 0;
let total = v.len();
fn unsafe_get(xs: &[u8], i: uint) -> u8 {
unsafe { *xs.unsafe_ref(i) }
unsafe { *xs.unsafe_get(i) }
}
fn safe_get(xs: &[u8], i: uint, total: uint) -> u8 {
if i >= total {
Expand Down Expand Up @@ -496,7 +499,7 @@ impl String {
unsafe {
// Attempt to not use an intermediate buffer by just pushing bytes
// directly onto this string.
let slice = Slice {
let slice = RawSlice {
data: self.vec.as_ptr().offset(cur_len as int),
len: 4,
};
Expand Down
2 changes: 1 addition & 1 deletion src/libcollections/trie.rs
Original file line number Diff line number Diff line change
Expand Up @@ -926,7 +926,7 @@ macro_rules! iterator_impl {
// such thing as invalid pointers and memory unsafety. The
// reason is performance, without doing this we can get the
// bench_iter_large microbenchmark down to about 30000 ns/iter
// (using .unsafe_ref to index self.stack directly, 38000
// (using .unsafe_get to index self.stack directly, 38000
// ns/iter with [] checked indexing), but this smashes that down
// to 13500 ns/iter.
//
Expand Down
Loading

0 comments on commit 385c39a

Please sign in to comment.