std: convert str::reserve* to methods, and methodise str::push_*.
This commit is contained in:
parent
a64e886e3c
commit
1553874149
@ -49,7 +49,7 @@ impl<'self> ToBase64 for &'self [u8] {
|
||||
fn to_base64(&self) -> ~str {
|
||||
let mut s = ~"";
|
||||
let len = self.len();
|
||||
str::reserve(&mut s, ((len + 3u) / 4u) * 3u);
|
||||
s.reserve(((len + 3u) / 4u) * 3u);
|
||||
|
||||
let mut i = 0u;
|
||||
|
||||
@ -59,10 +59,10 @@ fn to_base64(&self) -> ~str {
|
||||
(self[i + 2u] as uint);
|
||||
|
||||
// This 24-bit number gets separated into four 6-bit numbers.
|
||||
str::push_char(&mut s, CHARS[(n >> 18u) & 63u]);
|
||||
str::push_char(&mut s, CHARS[(n >> 12u) & 63u]);
|
||||
str::push_char(&mut s, CHARS[(n >> 6u) & 63u]);
|
||||
str::push_char(&mut s, CHARS[n & 63u]);
|
||||
s.push_char(CHARS[(n >> 18u) & 63u]);
|
||||
s.push_char(CHARS[(n >> 12u) & 63u]);
|
||||
s.push_char(CHARS[(n >> 6u) & 63u]);
|
||||
s.push_char(CHARS[n & 63u]);
|
||||
|
||||
i += 3u;
|
||||
}
|
||||
@ -73,18 +73,18 @@ fn to_base64(&self) -> ~str {
|
||||
0 => (),
|
||||
1 => {
|
||||
let n = (self[i] as uint) << 16u;
|
||||
str::push_char(&mut s, CHARS[(n >> 18u) & 63u]);
|
||||
str::push_char(&mut s, CHARS[(n >> 12u) & 63u]);
|
||||
str::push_char(&mut s, '=');
|
||||
str::push_char(&mut s, '=');
|
||||
s.push_char(CHARS[(n >> 18u) & 63u]);
|
||||
s.push_char(CHARS[(n >> 12u) & 63u]);
|
||||
s.push_char('=');
|
||||
s.push_char('=');
|
||||
}
|
||||
2 => {
|
||||
let n = (self[i] as uint) << 16u |
|
||||
(self[i + 1u] as uint) << 8u;
|
||||
str::push_char(&mut s, CHARS[(n >> 18u) & 63u]);
|
||||
str::push_char(&mut s, CHARS[(n >> 12u) & 63u]);
|
||||
str::push_char(&mut s, CHARS[(n >> 6u) & 63u]);
|
||||
str::push_char(&mut s, '=');
|
||||
s.push_char(CHARS[(n >> 18u) & 63u]);
|
||||
s.push_char(CHARS[(n >> 12u) & 63u]);
|
||||
s.push_char(CHARS[(n >> 6u) & 63u]);
|
||||
s.push_char('=');
|
||||
}
|
||||
_ => fail!("Algebra is broken, please alert the math police")
|
||||
}
|
||||
|
@ -79,7 +79,7 @@ fn escape_str(s: &str) -> ~str {
|
||||
|
||||
fn spaces(n: uint) -> ~str {
|
||||
let mut ss = ~"";
|
||||
for n.times { str::push_str(&mut ss, " "); }
|
||||
for n.times { ss.push_str(" "); }
|
||||
return ss;
|
||||
}
|
||||
|
||||
@ -712,14 +712,14 @@ fn parse_str(&mut self) -> Result<~str, Error> {
|
||||
|
||||
if (escape) {
|
||||
match self.ch {
|
||||
'"' => str::push_char(&mut res, '"'),
|
||||
'\\' => str::push_char(&mut res, '\\'),
|
||||
'/' => str::push_char(&mut res, '/'),
|
||||
'b' => str::push_char(&mut res, '\x08'),
|
||||
'f' => str::push_char(&mut res, '\x0c'),
|
||||
'n' => str::push_char(&mut res, '\n'),
|
||||
'r' => str::push_char(&mut res, '\r'),
|
||||
't' => str::push_char(&mut res, '\t'),
|
||||
'"' => res.push_char('"'),
|
||||
'\\' => res.push_char('\\'),
|
||||
'/' => res.push_char('/'),
|
||||
'b' => res.push_char('\x08'),
|
||||
'f' => res.push_char('\x0c'),
|
||||
'n' => res.push_char('\n'),
|
||||
'r' => res.push_char('\r'),
|
||||
't' => res.push_char('\t'),
|
||||
'u' => {
|
||||
// Parse \u1234.
|
||||
let mut i = 0u;
|
||||
@ -748,7 +748,7 @@ fn parse_str(&mut self) -> Result<~str, Error> {
|
||||
~"invalid \\u escape (not four digits)");
|
||||
}
|
||||
|
||||
str::push_char(&mut res, n as char);
|
||||
res.push_char(n as char);
|
||||
}
|
||||
_ => return self.error(~"invalid escape")
|
||||
}
|
||||
@ -760,7 +760,7 @@ fn parse_str(&mut self) -> Result<~str, Error> {
|
||||
self.bump();
|
||||
return Ok(res);
|
||||
}
|
||||
str::push_char(&mut res, self.ch);
|
||||
res.push_char(self.ch);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -81,7 +81,7 @@ fn encode_inner(s: &str, full_url: bool) -> ~str {
|
||||
'a' .. 'z' |
|
||||
'0' .. '9' |
|
||||
'-' | '.' | '_' | '~' => {
|
||||
str::push_char(&mut out, ch);
|
||||
out.push_char(ch);
|
||||
}
|
||||
_ => {
|
||||
if full_url {
|
||||
@ -92,7 +92,7 @@ fn encode_inner(s: &str, full_url: bool) -> ~str {
|
||||
// sub-delims:
|
||||
'!' | '$' | '&' | '"' | '(' | ')' | '*' |
|
||||
'+' | ',' | ';' | '=' => {
|
||||
str::push_char(&mut out, ch);
|
||||
out.push_char(ch);
|
||||
}
|
||||
|
||||
_ => out += fmt!("%%%X", ch as uint)
|
||||
@ -148,18 +148,18 @@ fn decode_inner(s: &str, full_url: bool) -> ~str {
|
||||
// sub-delims:
|
||||
'!' | '$' | '&' | '"' | '(' | ')' | '*' |
|
||||
'+' | ',' | ';' | '=' => {
|
||||
str::push_char(&mut out, '%');
|
||||
str::push_char(&mut out, bytes[0u] as char);
|
||||
str::push_char(&mut out, bytes[1u] as char);
|
||||
out.push_char('%');
|
||||
out.push_char(bytes[0u] as char);
|
||||
out.push_char(bytes[1u] as char);
|
||||
}
|
||||
|
||||
ch => str::push_char(&mut out, ch)
|
||||
ch => out.push_char(ch)
|
||||
}
|
||||
} else {
|
||||
str::push_char(&mut out, ch);
|
||||
out.push_char(ch);
|
||||
}
|
||||
}
|
||||
ch => str::push_char(&mut out, ch)
|
||||
ch => out.push_char(ch)
|
||||
}
|
||||
}
|
||||
|
||||
@ -191,9 +191,9 @@ fn encode_plus(s: &str) -> ~str {
|
||||
let ch = rdr.read_byte() as char;
|
||||
match ch {
|
||||
'A' .. 'Z' | 'a' .. 'z' | '0' .. '9' | '_' | '.' | '-' => {
|
||||
str::push_char(&mut out, ch);
|
||||
out.push_char(ch);
|
||||
}
|
||||
' ' => str::push_char(&mut out, '+'),
|
||||
' ' => out.push_char('+'),
|
||||
_ => out += fmt!("%%%X", ch as uint)
|
||||
}
|
||||
}
|
||||
@ -216,7 +216,7 @@ pub fn encode_form_urlencoded(m: &HashMap<~str, ~[~str]>) -> ~str {
|
||||
if first {
|
||||
first = false;
|
||||
} else {
|
||||
str::push_char(&mut out, '&');
|
||||
out.push_char('&');
|
||||
first = false;
|
||||
}
|
||||
|
||||
@ -267,9 +267,9 @@ pub fn decode_form_urlencoded(s: &[u8]) -> HashMap<~str, ~[~str]> {
|
||||
};
|
||||
|
||||
if parsing_key {
|
||||
str::push_char(&mut key, ch)
|
||||
key.push_char(ch)
|
||||
} else {
|
||||
str::push_char(&mut value, ch)
|
||||
value.push_char(ch)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1289,9 +1289,7 @@ fn rope_to_string(r: Rope) -> ~str {
|
||||
fn aux(str: &mut ~str, node: @node::Node) {
|
||||
match (*node) {
|
||||
node::Leaf(x) => {
|
||||
str::push_str(
|
||||
str,
|
||||
x.content.slice(x.byte_offset, x.byte_offset + x.byte_len));
|
||||
str.push_str(x.content.slice(x.byte_offset, x.byte_offset + x.byte_len));
|
||||
}
|
||||
node::Concat(ref x) => {
|
||||
aux(str, x.left);
|
||||
|
@ -149,7 +149,7 @@ fn take_nonempty_prefix(rdr: @io::Reader,
|
||||
let mut buf = ~"";
|
||||
let mut ch = ch;
|
||||
while pred(ch) {
|
||||
str::push_char(&mut buf, ch);
|
||||
buf.push_char(ch);
|
||||
ch = rdr.read_char();
|
||||
}
|
||||
if buf.is_empty() {
|
||||
|
@ -851,7 +851,7 @@ fn parse_type(ch: char, tm: &Tm) -> ~str {
|
||||
while !rdr.eof() {
|
||||
match rdr.read_char() {
|
||||
'%' => buf += parse_type(rdr.read_char(), tm),
|
||||
ch => str::push_char(&mut buf, ch)
|
||||
ch => buf.push_char(ch)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -980,7 +980,7 @@ fn read_ty(&mut self, xcx: @ExtendedDecodeContext) -> ty::t {
|
||||
fn type_string(doc: ebml::Doc) -> ~str {
|
||||
let mut str = ~"";
|
||||
for uint::range(doc.start, doc.end) |i| {
|
||||
str::push_char(&mut str, doc.data[i] as char);
|
||||
str.push_char(doc.data[i] as char);
|
||||
}
|
||||
str
|
||||
}
|
||||
|
@ -694,9 +694,9 @@ pub fn append_loan_path_to_str_from_interior(&self,
|
||||
out: &mut ~str) {
|
||||
match *loan_path {
|
||||
LpExtend(_, _, LpDeref) => {
|
||||
str::push_char(out, '(');
|
||||
out.push_char('(');
|
||||
self.append_loan_path_to_str(loan_path, out);
|
||||
str::push_char(out, ')');
|
||||
out.push_char(')');
|
||||
}
|
||||
LpExtend(_, _, LpInterior(_)) |
|
||||
LpVar(_) => {
|
||||
@ -712,7 +712,7 @@ pub fn append_loan_path_to_str(&self,
|
||||
LpVar(id) => {
|
||||
match self.tcx.items.find(&id) {
|
||||
Some(&ast_map::node_local(ref ident)) => {
|
||||
str::push_str(out, *token::ident_to_str(ident));
|
||||
out.push_str(*token::ident_to_str(ident));
|
||||
}
|
||||
r => {
|
||||
self.tcx.sess.bug(
|
||||
@ -726,23 +726,23 @@ pub fn append_loan_path_to_str(&self,
|
||||
self.append_loan_path_to_str_from_interior(lp_base, out);
|
||||
match fname {
|
||||
mc::NamedField(ref fname) => {
|
||||
str::push_char(out, '.');
|
||||
str::push_str(out, *token::ident_to_str(fname));
|
||||
out.push_char('.');
|
||||
out.push_str(*token::ident_to_str(fname));
|
||||
}
|
||||
mc::PositionalField(idx) => {
|
||||
str::push_char(out, '#'); // invent a notation here
|
||||
str::push_str(out, idx.to_str());
|
||||
out.push_char('#'); // invent a notation here
|
||||
out.push_str(idx.to_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
LpExtend(lp_base, _, LpInterior(mc::InteriorElement(_))) => {
|
||||
self.append_loan_path_to_str_from_interior(lp_base, out);
|
||||
str::push_str(out, "[]");
|
||||
out.push_str("[]");
|
||||
}
|
||||
|
||||
LpExtend(lp_base, _, LpDeref) => {
|
||||
str::push_char(out, '*');
|
||||
out.push_char('*');
|
||||
self.append_loan_path_to_str(lp_base, out);
|
||||
}
|
||||
}
|
||||
|
@ -947,13 +947,13 @@ fn bits_to_str(words: &[uint]) -> ~str {
|
||||
for words.each |&word| {
|
||||
let mut v = word;
|
||||
for uint::range(0, uint::bytes) |_| {
|
||||
str::push_char(&mut result, sep);
|
||||
str::push_str(&mut result, fmt!("%02x", v & 0xFF));
|
||||
result.push_char(sep);
|
||||
result.push_str(fmt!("%02x", v & 0xFF));
|
||||
v >>= 8;
|
||||
sep = '-';
|
||||
}
|
||||
}
|
||||
str::push_char(&mut result, ']');
|
||||
result.push_char(']');
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -139,121 +139,35 @@ pub fn from_byte(b: u8) -> ~str {
|
||||
unsafe { ::cast::transmute(~[b, 0u8]) }
|
||||
}
|
||||
|
||||
/// Appends a character at the end of a string
|
||||
pub fn push_char(s: &mut ~str, ch: char) {
|
||||
unsafe {
|
||||
let code = ch as uint;
|
||||
let nb = if code < max_one_b { 1u }
|
||||
else if code < max_two_b { 2u }
|
||||
else if code < max_three_b { 3u }
|
||||
else if code < max_four_b { 4u }
|
||||
else if code < max_five_b { 5u }
|
||||
else { 6u };
|
||||
let len = s.len();
|
||||
let new_len = len + nb;
|
||||
reserve_at_least(&mut *s, new_len);
|
||||
let off = len;
|
||||
do as_buf(*s) |buf, _len| {
|
||||
let buf: *mut u8 = ::cast::transmute(buf);
|
||||
match nb {
|
||||
1u => {
|
||||
*ptr::mut_offset(buf, off) = code as u8;
|
||||
}
|
||||
2u => {
|
||||
*ptr::mut_offset(buf, off) = (code >> 6u & 31u | tag_two_b) as u8;
|
||||
*ptr::mut_offset(buf, off + 1u) = (code & 63u | tag_cont) as u8;
|
||||
}
|
||||
3u => {
|
||||
*ptr::mut_offset(buf, off) = (code >> 12u & 15u | tag_three_b) as u8;
|
||||
*ptr::mut_offset(buf, off + 1u) = (code >> 6u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 2u) = (code & 63u | tag_cont) as u8;
|
||||
}
|
||||
4u => {
|
||||
*ptr::mut_offset(buf, off) = (code >> 18u & 7u | tag_four_b) as u8;
|
||||
*ptr::mut_offset(buf, off + 1u) = (code >> 12u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 2u) = (code >> 6u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 3u) = (code & 63u | tag_cont) as u8;
|
||||
}
|
||||
5u => {
|
||||
*ptr::mut_offset(buf, off) = (code >> 24u & 3u | tag_five_b) as u8;
|
||||
*ptr::mut_offset(buf, off + 1u) = (code >> 18u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 2u) = (code >> 12u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 3u) = (code >> 6u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 4u) = (code & 63u | tag_cont) as u8;
|
||||
}
|
||||
6u => {
|
||||
*ptr::mut_offset(buf, off) = (code >> 30u & 1u | tag_six_b) as u8;
|
||||
*ptr::mut_offset(buf, off + 1u) = (code >> 24u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 2u) = (code >> 18u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 3u) = (code >> 12u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 4u) = (code >> 6u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 5u) = (code & 63u | tag_cont) as u8;
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
raw::set_len(s, new_len);
|
||||
}
|
||||
}
|
||||
|
||||
/// Convert a char to a string
|
||||
pub fn from_char(ch: char) -> ~str {
|
||||
let mut buf = ~"";
|
||||
push_char(&mut buf, ch);
|
||||
buf.push_char(ch);
|
||||
buf
|
||||
}
|
||||
|
||||
/// Convert a vector of chars to a string
|
||||
pub fn from_chars(chs: &[char]) -> ~str {
|
||||
let mut buf = ~"";
|
||||
reserve(&mut buf, chs.len());
|
||||
buf.reserve(chs.len());
|
||||
for chs.each |ch| {
|
||||
push_char(&mut buf, *ch);
|
||||
buf.push_char(*ch)
|
||||
}
|
||||
buf
|
||||
}
|
||||
|
||||
/// Appends a string slice to the back of a string, without overallocating
|
||||
#[inline(always)]
|
||||
pub fn push_str_no_overallocate(lhs: &mut ~str, rhs: &str) {
|
||||
unsafe {
|
||||
let llen = lhs.len();
|
||||
let rlen = rhs.len();
|
||||
reserve(&mut *lhs, llen + rlen);
|
||||
do as_buf(*lhs) |lbuf, _llen| {
|
||||
do as_buf(rhs) |rbuf, _rlen| {
|
||||
let dst = ptr::offset(lbuf, llen);
|
||||
let dst = ::cast::transmute_mut_unsafe(dst);
|
||||
ptr::copy_memory(dst, rbuf, rlen);
|
||||
}
|
||||
}
|
||||
raw::set_len(lhs, llen + rlen);
|
||||
}
|
||||
}
|
||||
|
||||
/// Appends a string slice to the back of a string
|
||||
#[inline(always)]
|
||||
/// A function version of the `.push_str`, required for `fmt!` during
|
||||
/// the bootstrap. Use `lhs.push_str(rhs)` instead of this.
|
||||
#[doc="hidden"]
|
||||
pub fn push_str(lhs: &mut ~str, rhs: &str) {
|
||||
unsafe {
|
||||
let llen = lhs.len();
|
||||
let rlen = rhs.len();
|
||||
reserve_at_least(&mut *lhs, llen + rlen);
|
||||
do as_buf(*lhs) |lbuf, _llen| {
|
||||
do as_buf(rhs) |rbuf, _rlen| {
|
||||
let dst = ptr::offset(lbuf, llen);
|
||||
let dst = ::cast::transmute_mut_unsafe(dst);
|
||||
ptr::copy_memory(dst, rbuf, rlen);
|
||||
}
|
||||
}
|
||||
raw::set_len(lhs, llen + rlen);
|
||||
}
|
||||
lhs.push_str(rhs)
|
||||
}
|
||||
|
||||
/// Concatenate two strings together
|
||||
#[inline(always)]
|
||||
pub fn append(lhs: ~str, rhs: &str) -> ~str {
|
||||
let mut v = lhs;
|
||||
push_str_no_overallocate(&mut v, rhs);
|
||||
v.push_str_no_overallocate(rhs);
|
||||
v
|
||||
}
|
||||
|
||||
@ -286,7 +200,7 @@ pub fn concat(&self) -> ~str {
|
||||
}
|
||||
let mut s = ~"";
|
||||
|
||||
reserve(&mut s, len);
|
||||
s.reserve(len);
|
||||
|
||||
unsafe {
|
||||
do as_buf(s) |buf, _| {
|
||||
@ -319,7 +233,7 @@ pub fn connect(&self, sep: &str) -> ~str {
|
||||
let mut s = ~"";
|
||||
let mut first = true;
|
||||
|
||||
reserve(&mut s, len);
|
||||
s.reserve(len);
|
||||
|
||||
unsafe {
|
||||
do as_buf(s) |buf, _| {
|
||||
@ -358,7 +272,7 @@ pub fn concat(&self) -> ~str {
|
||||
}
|
||||
let mut s = ~"";
|
||||
|
||||
reserve(&mut s, len);
|
||||
s.reserve(len);
|
||||
|
||||
unsafe {
|
||||
do as_buf(s) |buf, _| {
|
||||
@ -391,7 +305,7 @@ pub fn connect(&self, sep: &str) -> ~str {
|
||||
let mut s = ~"";
|
||||
let mut first = true;
|
||||
|
||||
reserve(&mut s, len);
|
||||
s.reserve(len);
|
||||
|
||||
unsafe {
|
||||
do as_buf(s) |buf, _| {
|
||||
@ -425,7 +339,7 @@ pub fn repeat(ss: &str, nn: uint) -> ~str {
|
||||
let mut ret = ~"";
|
||||
// ignore the NULL terminator
|
||||
let len = len - 1;
|
||||
reserve(&mut ret, nn * len);
|
||||
ret.reserve(nn * len);
|
||||
|
||||
unsafe {
|
||||
do as_buf(ret) |rbuf, _len| {
|
||||
@ -1148,9 +1062,9 @@ fn equiv(&self, other: &~str) -> bool { eq_slice(*self, *other) }
|
||||
/// Apply a function to each character
|
||||
pub fn map(ss: &str, ff: &fn(char) -> char) -> ~str {
|
||||
let mut result = ~"";
|
||||
reserve(&mut result, ss.len());
|
||||
result.reserve(ss.len());
|
||||
for ss.iter().advance |cc| {
|
||||
str::push_char(&mut result, ff(cc));
|
||||
result.push_char(ff(cc));
|
||||
}
|
||||
result
|
||||
}
|
||||
@ -1325,8 +1239,8 @@ pub fn utf16_chars(v: &[u16], f: &fn(char)) {
|
||||
*/
|
||||
pub fn from_utf16(v: &[u16]) -> ~str {
|
||||
let mut buf = ~"";
|
||||
reserve(&mut buf, v.len());
|
||||
utf16_chars(v, |ch| push_char(&mut buf, ch));
|
||||
buf.reserve(v.len());
|
||||
utf16_chars(v, |ch| buf.push_char(ch));
|
||||
buf
|
||||
}
|
||||
|
||||
@ -1336,7 +1250,7 @@ pub fn from_utf16(v: &[u16]) -> ~str {
|
||||
*/
|
||||
pub fn with_capacity(capacity: uint) -> ~str {
|
||||
let mut buf = ~"";
|
||||
reserve(&mut buf, capacity);
|
||||
buf.reserve(capacity);
|
||||
buf
|
||||
}
|
||||
|
||||
@ -1660,54 +1574,6 @@ pub fn subslice_offset(outer: &str, inner: &str) -> uint {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Reserves capacity for exactly `n` bytes in the given string, not including
|
||||
* the null terminator.
|
||||
*
|
||||
* Assuming single-byte characters, the resulting string will be large
|
||||
* enough to hold a string of length `n`. To account for the null terminator,
|
||||
* the underlying buffer will have the size `n` + 1.
|
||||
*
|
||||
* If the capacity for `s` is already equal to or greater than the requested
|
||||
* capacity, then no action is taken.
|
||||
*
|
||||
* # Arguments
|
||||
*
|
||||
* * s - A string
|
||||
* * n - The number of bytes to reserve space for
|
||||
*/
|
||||
#[inline(always)]
|
||||
pub fn reserve(s: &mut ~str, n: uint) {
|
||||
unsafe {
|
||||
let v: *mut ~[u8] = cast::transmute(s);
|
||||
vec::reserve(&mut *v, n + 1);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Reserves capacity for at least `n` bytes in the given string, not including
|
||||
* the null terminator.
|
||||
*
|
||||
* Assuming single-byte characters, the resulting string will be large
|
||||
* enough to hold a string of length `n`. To account for the null terminator,
|
||||
* the underlying buffer will have the size `n` + 1.
|
||||
*
|
||||
* This function will over-allocate in order to amortize the allocation costs
|
||||
* in scenarios where the caller may need to repeatedly reserve additional
|
||||
* space.
|
||||
*
|
||||
* If the capacity for `s` is already equal to or greater than the requested
|
||||
* capacity, then no action is taken.
|
||||
*
|
||||
* # Arguments
|
||||
*
|
||||
* * s - A string
|
||||
* * n - The number of bytes to reserve space for
|
||||
*/
|
||||
#[inline(always)]
|
||||
pub fn reserve_at_least(s: &mut ~str, n: uint) {
|
||||
reserve(s, uint::next_power_of_two(n + 1u) - 1u)
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the number of single-byte characters the string can hold without
|
||||
@ -1724,9 +1590,9 @@ pub fn capacity(s: &const ~str) -> uint {
|
||||
/// Escape each char in `s` with char::escape_default.
|
||||
pub fn escape_default(s: &str) -> ~str {
|
||||
let mut out: ~str = ~"";
|
||||
reserve_at_least(&mut out, s.len());
|
||||
out.reserve_at_least(s.len());
|
||||
for s.iter().advance |c| {
|
||||
push_str(&mut out, char::escape_default(c));
|
||||
out.push_str(char::escape_default(c));
|
||||
}
|
||||
out
|
||||
}
|
||||
@ -1734,9 +1600,9 @@ pub fn escape_default(s: &str) -> ~str {
|
||||
/// Escape each char in `s` with char::escape_unicode.
|
||||
pub fn escape_unicode(s: &str) -> ~str {
|
||||
let mut out: ~str = ~"";
|
||||
reserve_at_least(&mut out, s.len());
|
||||
out.reserve_at_least(s.len());
|
||||
for s.iter().advance |c| {
|
||||
push_str(&mut out, char::escape_unicode(c));
|
||||
out.push_str(char::escape_unicode(c));
|
||||
}
|
||||
out
|
||||
}
|
||||
@ -1747,7 +1613,7 @@ pub mod raw {
|
||||
use libc;
|
||||
use ptr;
|
||||
use str::raw;
|
||||
use str::{as_buf, is_utf8, reserve_at_least};
|
||||
use str::{as_buf, is_utf8};
|
||||
use vec;
|
||||
|
||||
/// Create a Rust string from a null-terminated *u8 buffer
|
||||
@ -1859,7 +1725,7 @@ pub unsafe fn slice_bytes(s: &str, begin: uint, end: uint) -> &str {
|
||||
/// Appends a byte to a string. (Not UTF-8 safe).
|
||||
pub unsafe fn push_byte(s: &mut ~str, b: u8) {
|
||||
let new_len = s.len() + 1;
|
||||
reserve_at_least(&mut *s, new_len);
|
||||
s.reserve_at_least(new_len);
|
||||
do as_buf(*s) |buf, len| {
|
||||
let buf: *mut u8 = ::cast::transmute(buf);
|
||||
*ptr::mut_offset(buf, len) = b;
|
||||
@ -1870,7 +1736,7 @@ pub unsafe fn push_byte(s: &mut ~str, b: u8) {
|
||||
/// Appends a vector of bytes to a string. (Not UTF-8 safe).
|
||||
unsafe fn push_bytes(s: &mut ~str, bytes: &[u8]) {
|
||||
let new_len = s.len() + bytes.len();
|
||||
reserve_at_least(&mut *s, new_len);
|
||||
s.reserve_at_least(new_len);
|
||||
for bytes.each |byte| { push_byte(&mut *s, *byte); }
|
||||
}
|
||||
|
||||
@ -2274,18 +2140,154 @@ fn find_str(&self, needle: &str) -> Option<uint> {
|
||||
|
||||
#[allow(missing_doc)]
|
||||
pub trait OwnedStr {
|
||||
fn push_str(&mut self, v: &str);
|
||||
fn push_str_no_overallocate(&mut self, rhs: &str);
|
||||
fn push_str(&mut self, rhs: &str);
|
||||
fn push_char(&mut self, c: char);
|
||||
fn reserve(&mut self, n: uint);
|
||||
fn reserve_at_least(&mut self, n: uint);
|
||||
}
|
||||
|
||||
impl OwnedStr for ~str {
|
||||
#[inline]
|
||||
fn push_str(&mut self, v: &str) {
|
||||
push_str(self, v);
|
||||
/// Appends a string slice to the back of a string, without overallocating
|
||||
#[inline(always)]
|
||||
fn push_str_no_overallocate(&mut self, rhs: &str) {
|
||||
unsafe {
|
||||
let llen = self.len();
|
||||
let rlen = rhs.len();
|
||||
self.reserve(llen + rlen);
|
||||
do as_buf(*self) |lbuf, _llen| {
|
||||
do as_buf(rhs) |rbuf, _rlen| {
|
||||
let dst = ptr::offset(lbuf, llen);
|
||||
let dst = ::cast::transmute_mut_unsafe(dst);
|
||||
ptr::copy_memory(dst, rbuf, rlen);
|
||||
}
|
||||
}
|
||||
raw::set_len(self, llen + rlen);
|
||||
}
|
||||
}
|
||||
|
||||
/// Appends a string slice to the back of a string
|
||||
#[inline]
|
||||
fn push_str(&mut self, rhs: &str) {
|
||||
unsafe {
|
||||
let llen = self.len();
|
||||
let rlen = rhs.len();
|
||||
self.reserve_at_least(llen + rlen);
|
||||
do as_buf(*self) |lbuf, _llen| {
|
||||
do as_buf(rhs) |rbuf, _rlen| {
|
||||
let dst = ptr::offset(lbuf, llen);
|
||||
let dst = ::cast::transmute_mut_unsafe(dst);
|
||||
ptr::copy_memory(dst, rbuf, rlen);
|
||||
}
|
||||
}
|
||||
raw::set_len(self, llen + rlen);
|
||||
}
|
||||
}
|
||||
/// Appends a character to the back of a string
|
||||
#[inline]
|
||||
fn push_char(&mut self, c: char) {
|
||||
push_char(self, c);
|
||||
unsafe {
|
||||
let code = c as uint;
|
||||
let nb = if code < max_one_b { 1u }
|
||||
else if code < max_two_b { 2u }
|
||||
else if code < max_three_b { 3u }
|
||||
else if code < max_four_b { 4u }
|
||||
else if code < max_five_b { 5u }
|
||||
else { 6u };
|
||||
let len = self.len();
|
||||
let new_len = len + nb;
|
||||
self.reserve_at_least(new_len);
|
||||
let off = len;
|
||||
do as_buf(*self) |buf, _len| {
|
||||
let buf: *mut u8 = ::cast::transmute(buf);
|
||||
match nb {
|
||||
1u => {
|
||||
*ptr::mut_offset(buf, off) = code as u8;
|
||||
}
|
||||
2u => {
|
||||
*ptr::mut_offset(buf, off) = (code >> 6u & 31u | tag_two_b) as u8;
|
||||
*ptr::mut_offset(buf, off + 1u) = (code & 63u | tag_cont) as u8;
|
||||
}
|
||||
3u => {
|
||||
*ptr::mut_offset(buf, off) = (code >> 12u & 15u | tag_three_b) as u8;
|
||||
*ptr::mut_offset(buf, off + 1u) = (code >> 6u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 2u) = (code & 63u | tag_cont) as u8;
|
||||
}
|
||||
4u => {
|
||||
*ptr::mut_offset(buf, off) = (code >> 18u & 7u | tag_four_b) as u8;
|
||||
*ptr::mut_offset(buf, off + 1u) = (code >> 12u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 2u) = (code >> 6u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 3u) = (code & 63u | tag_cont) as u8;
|
||||
}
|
||||
5u => {
|
||||
*ptr::mut_offset(buf, off) = (code >> 24u & 3u | tag_five_b) as u8;
|
||||
*ptr::mut_offset(buf, off + 1u) = (code >> 18u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 2u) = (code >> 12u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 3u) = (code >> 6u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 4u) = (code & 63u | tag_cont) as u8;
|
||||
}
|
||||
6u => {
|
||||
*ptr::mut_offset(buf, off) = (code >> 30u & 1u | tag_six_b) as u8;
|
||||
*ptr::mut_offset(buf, off + 1u) = (code >> 24u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 2u) = (code >> 18u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 3u) = (code >> 12u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 4u) = (code >> 6u & 63u | tag_cont) as u8;
|
||||
*ptr::mut_offset(buf, off + 5u) = (code & 63u | tag_cont) as u8;
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
raw::set_len(self, new_len);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Reserves capacity for exactly `n` bytes in the given string, not including
|
||||
* the null terminator.
|
||||
*
|
||||
* Assuming single-byte characters, the resulting string will be large
|
||||
* enough to hold a string of length `n`. To account for the null terminator,
|
||||
* the underlying buffer will have the size `n` + 1.
|
||||
*
|
||||
* If the capacity for `s` is already equal to or greater than the requested
|
||||
* capacity, then no action is taken.
|
||||
*
|
||||
* # Arguments
|
||||
*
|
||||
* * s - A string
|
||||
* * n - The number of bytes to reserve space for
|
||||
*/
|
||||
#[inline(always)]
|
||||
pub fn reserve(&mut self, n: uint) {
|
||||
unsafe {
|
||||
let v: *mut ~[u8] = cast::transmute(self);
|
||||
vec::reserve(&mut *v, n + 1);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Reserves capacity for at least `n` bytes in the given string, not including
|
||||
* the null terminator.
|
||||
*
|
||||
* Assuming single-byte characters, the resulting string will be large
|
||||
* enough to hold a string of length `n`. To account for the null terminator,
|
||||
* the underlying buffer will have the size `n` + 1.
|
||||
*
|
||||
* This function will over-allocate in order to amortize the allocation costs
|
||||
* in scenarios where the caller may need to repeatedly reserve additional
|
||||
* space.
|
||||
*
|
||||
* If the capacity for `s` is already equal to or greater than the requested
|
||||
* capacity, then no action is taken.
|
||||
*
|
||||
* # Arguments
|
||||
*
|
||||
* * s - A string
|
||||
* * n - The number of bytes to reserve space for
|
||||
*/
|
||||
#[inline(always)]
|
||||
fn reserve_at_least(&mut self, n: uint) {
|
||||
self.reserve(uint::next_power_of_two(n + 1u) - 1u)
|
||||
}
|
||||
}
|
||||
|
||||
@ -2582,13 +2584,13 @@ fn test_unsafe_slice() {
|
||||
fn a_million_letter_a() -> ~str {
|
||||
let mut i = 0;
|
||||
let mut rs = ~"";
|
||||
while i < 100000 { push_str(&mut rs, "aaaaaaaaaa"); i += 1; }
|
||||
while i < 100000 { rs.push_str("aaaaaaaaaa"); i += 1; }
|
||||
rs
|
||||
}
|
||||
fn half_a_million_letter_a() -> ~str {
|
||||
let mut i = 0;
|
||||
let mut rs = ~"";
|
||||
while i < 100000 { push_str(&mut rs, "aaaaa"); i += 1; }
|
||||
while i < 100000 { rs.push_str("aaaaa"); i += 1; }
|
||||
rs
|
||||
}
|
||||
let letters = a_million_letter_a();
|
||||
|
@ -136,10 +136,10 @@ unsafe fn fail_borrowed(box: *mut BoxRepr, file: *c_char, line: size_t) {
|
||||
let mut sep = " at ";
|
||||
for borrow_list.rev_iter().advance |entry| {
|
||||
if entry.box == box {
|
||||
str::push_str(&mut msg, sep);
|
||||
msg.push_str(sep);
|
||||
let filename = str::raw::from_c_str(entry.file);
|
||||
str::push_str(&mut msg, filename);
|
||||
str::push_str(&mut msg, fmt!(":%u", entry.line as uint));
|
||||
msg.push_str(filename);
|
||||
msg.push_str(fmt!(":%u", entry.line as uint));
|
||||
sep = " and at ";
|
||||
}
|
||||
}
|
||||
|
@ -276,6 +276,9 @@ fn log_conv(c: &Conv) {
|
||||
stms.push(cx.stmt_let(fmt_sp, npieces > 1,
|
||||
ident, cx.expr_str_uniq(fmt_sp, s)));
|
||||
} else {
|
||||
// we call the push_str function because the
|
||||
// bootstrap doesnt't seem to work if we call the
|
||||
// method.
|
||||
let args = ~[cx.expr_mut_addr_of(fmt_sp, buf()), cx.expr_str(fmt_sp, s)];
|
||||
let call = cx.expr_call_global(fmt_sp,
|
||||
~[core_ident,
|
||||
|
@ -125,7 +125,7 @@ fn block_trim(lines: ~[~str], chars: ~str, max: Option<uint>) -> ~[~str] {
|
||||
fn read_to_eol(rdr: @mut StringReader) -> ~str {
|
||||
let mut val = ~"";
|
||||
while rdr.curr != '\n' && !is_eof(rdr) {
|
||||
str::push_char(&mut val, rdr.curr);
|
||||
val.push_char(rdr.curr);
|
||||
bump(rdr);
|
||||
}
|
||||
if rdr.curr == '\n' { bump(rdr); }
|
||||
@ -237,7 +237,7 @@ fn read_block_comment(rdr: @mut StringReader,
|
||||
// doc-comments are not really comments, they are attributes
|
||||
if rdr.curr == '*' || rdr.curr == '!' {
|
||||
while !(rdr.curr == '*' && nextch(rdr) == '/') && !is_eof(rdr) {
|
||||
str::push_char(&mut curr_line, rdr.curr);
|
||||
curr_line.push_char(rdr.curr);
|
||||
bump(rdr);
|
||||
}
|
||||
if !is_eof(rdr) {
|
||||
@ -261,7 +261,7 @@ fn read_block_comment(rdr: @mut StringReader,
|
||||
curr_line = ~"";
|
||||
bump(rdr);
|
||||
} else {
|
||||
str::push_char(&mut curr_line, rdr.curr);
|
||||
curr_line.push_char(rdr.curr);
|
||||
if rdr.curr == '/' && nextch(rdr) == '*' {
|
||||
bump(rdr);
|
||||
bump(rdr);
|
||||
|
@ -358,11 +358,11 @@ fn scan_exponent(rdr: @mut StringReader) -> Option<~str> {
|
||||
let mut c = rdr.curr;
|
||||
let mut rslt = ~"";
|
||||
if c == 'e' || c == 'E' {
|
||||
str::push_char(&mut rslt, c);
|
||||
rslt.push_char(c);
|
||||
bump(rdr);
|
||||
c = rdr.curr;
|
||||
if c == '-' || c == '+' {
|
||||
str::push_char(&mut rslt, c);
|
||||
rslt.push_char(c);
|
||||
bump(rdr);
|
||||
}
|
||||
let exponent = scan_digits(rdr, 10u);
|
||||
@ -379,7 +379,7 @@ fn scan_digits(rdr: @mut StringReader, radix: uint) -> ~str {
|
||||
if c == '_' { bump(rdr); loop; }
|
||||
match char::to_digit(c, radix) {
|
||||
Some(_) => {
|
||||
str::push_char(&mut rslt, c);
|
||||
rslt.push_char(c);
|
||||
bump(rdr);
|
||||
}
|
||||
_ => return rslt
|
||||
@ -721,31 +721,28 @@ fn binop(rdr: @mut StringReader, op: token::binop) -> token::Token {
|
||||
let escaped = rdr.curr;
|
||||
bump(rdr);
|
||||
match escaped {
|
||||
'n' => str::push_char(&mut accum_str, '\n'),
|
||||
'r' => str::push_char(&mut accum_str, '\r'),
|
||||
't' => str::push_char(&mut accum_str, '\t'),
|
||||
'\\' => str::push_char(&mut accum_str, '\\'),
|
||||
'\'' => str::push_char(&mut accum_str, '\''),
|
||||
'"' => str::push_char(&mut accum_str, '"'),
|
||||
'n' => accum_str.push_char('\n'),
|
||||
'r' => accum_str.push_char('\r'),
|
||||
't' => accum_str.push_char('\t'),
|
||||
'\\' => accum_str.push_char('\\'),
|
||||
'\'' => accum_str.push_char('\''),
|
||||
'"' => accum_str.push_char('"'),
|
||||
'\n' => consume_whitespace(rdr),
|
||||
'x' => {
|
||||
str::push_char(&mut accum_str,
|
||||
scan_numeric_escape(rdr, 2u));
|
||||
accum_str.push_char(scan_numeric_escape(rdr, 2u));
|
||||
}
|
||||
'u' => {
|
||||
str::push_char(&mut accum_str,
|
||||
scan_numeric_escape(rdr, 4u));
|
||||
accum_str.push_char(scan_numeric_escape(rdr, 4u));
|
||||
}
|
||||
'U' => {
|
||||
str::push_char(&mut accum_str,
|
||||
scan_numeric_escape(rdr, 8u));
|
||||
accum_str.push_char(scan_numeric_escape(rdr, 8u));
|
||||
}
|
||||
c2 => {
|
||||
rdr.fatal(fmt!("unknown string escape: %d", c2 as int));
|
||||
}
|
||||
}
|
||||
}
|
||||
_ => str::push_char(&mut accum_str, ch)
|
||||
_ => accum_str.push_char(ch)
|
||||
}
|
||||
}
|
||||
bump(rdr);
|
||||
|
@ -79,7 +79,7 @@ fn make_random_fasta(wr: @io::Writer,
|
||||
};
|
||||
let mut op: ~str = ~"";
|
||||
for uint::range(0u, n as uint) |_i| {
|
||||
str::push_char(&mut op, select_random(myrandom_next(rng, 100u32),
|
||||
op.push_char(select_random(myrandom_next(rng, 100u32),
|
||||
copy genelist));
|
||||
if op.len() >= LINE_LENGTH() {
|
||||
wr.write_line(op);
|
||||
|
@ -95,10 +95,10 @@ enum Result {
|
||||
|
||||
priv fn cmd_to_str(cmd: ~[~str]) -> ~str {
|
||||
let mut res = ~"*";
|
||||
str::push_str(&mut res, cmd.len().to_str());
|
||||
str::push_str(&mut res, "\r\n");
|
||||
res.push_str(cmd.len().to_str());
|
||||
res.push_str("\r\n");
|
||||
for cmd.each |s| {
|
||||
str::push_str(&mut res, str::concat(~[~"$", s.len().to_str(), ~"\r\n",
|
||||
res.push_str(str::concat(~[~"$", s.len().to_str(), ~"\r\n",
|
||||
copy *s, ~"\r\n"]));
|
||||
}
|
||||
res
|
||||
|
@ -6,7 +6,7 @@ struct StringBuffer {
|
||||
|
||||
impl StringBuffer {
|
||||
pub fn append(&mut self, v: &str) {
|
||||
str::push_str(&mut self.s, v);
|
||||
self.s.push_str(v);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -33,7 +33,7 @@ pub fn main() {
|
||||
let mut stack = ~"a×c€";
|
||||
assert_eq!(str::pop_char(&mut stack), '€');
|
||||
assert_eq!(str::pop_char(&mut stack), 'c');
|
||||
str::push_char(&mut stack, 'u');
|
||||
stack.push_char('u');
|
||||
assert!(stack == ~"a×u");
|
||||
assert_eq!(str::shift_char(&mut stack), 'a');
|
||||
assert_eq!(str::shift_char(&mut stack), '×');
|
||||
|
Loading…
Reference in New Issue
Block a user