From ccd68680ee1a6e28872e30e025047a5daca646c8 Mon Sep 17 00:00:00 2001 From: Erick Tryzelaar Date: Mon, 11 Jun 2012 08:19:49 -0700 Subject: [PATCH 1/8] cargo: remove leading underscores --- src/cargo/cargo.rs | 48 +++++++++++++++++++++++----------------------- 1 file changed, 24 insertions(+), 24 deletions(-) diff --git a/src/cargo/cargo.rs b/src/cargo/cargo.rs index 94efae2442f8a..1c9ae6f866a1b 100644 --- a/src/cargo/cargo.rs +++ b/src/cargo/cargo.rs @@ -399,26 +399,26 @@ fn parse_source(name: str, j: json::json) -> source { } alt j { - json::dict(_j) { - let mut url = alt _j.find("url") { + json::dict(j) { + let mut url = alt j.find("url") { some(json::string(u)) { u } _ { fail "needed 'url' field in source"; } }; - let method = alt _j.find("method") { + let method = alt j.find("method") { some(json::string(u)) { u } _ { assume_source_method(url) } }; - let key = alt _j.find("key") { + let key = alt j.find("key") { some(json::string(u)) { some(u) } _ { none } }; - let keyfp = alt _j.find("keyfp") { + let keyfp = alt j.find("keyfp") { some(json::string(u)) { some(u) } @@ -456,14 +456,14 @@ fn try_parse_sources(filename: str, sources: map::hashmap) { fn load_one_source_package(src: source, p: map::hashmap) { let name = alt p.find("name") { - some(json::string(_n)) { - if !valid_pkg_name(_n) { - warn("malformed source json: " + src.name + ", '" + _n + "'"+ + some(json::string(n)) { + if !valid_pkg_name(n) { + warn("malformed source json: " + src.name + ", '" + n + "'"+ " is an invalid name (alphanumeric, underscores and" + " dashes only)"); ret; } - _n + n } _ { warn("malformed source json: " + src.name + " (missing name)"); @@ -472,13 +472,13 @@ fn load_one_source_package(src: source, p: map::hashmap) { }; let uuid = alt p.find("uuid") { - some(json::string(_n)) { - if !is_uuid(_n) { - warn("malformed source json: " + src.name + ", '" + _n + "'"+ + some(json::string(n)) { + if !is_uuid(n) { + warn("malformed source json: " + src.name + ", '" + n + "'"+ " is an invalid uuid"); ret; } - _n + n } _ { warn("malformed source json: " + src.name + " (missing uuid)"); @@ -487,7 +487,7 @@ fn load_one_source_package(src: source, p: map::hashmap) { }; let url = alt p.find("url") { - some(json::string(_n)) { _n } + some(json::string(n)) { n } _ { warn("malformed source json: " + src.name + " (missing url)"); ret; @@ -495,7 +495,7 @@ fn load_one_source_package(src: source, p: map::hashmap) { }; let method = alt p.find("method") { - some(json::string(_n)) { _n } + some(json::string(n)) { n } _ { warn("malformed source json: " + src.name + " (missing method)"); ret; @@ -503,7 +503,7 @@ fn load_one_source_package(src: source, p: map::hashmap) { }; let ref = alt p.find("ref") { - some(json::string(_n)) { some(_n) } + some(json::string(n)) { some(n) } _ { none } }; @@ -512,7 +512,7 @@ fn load_one_source_package(src: source, p: map::hashmap) { some(json::list(js)) { for js.each {|j| alt j { - json::string(_j) { vec::grow(tags, 1u, _j); } + json::string(j) { vec::grow(tags, 1u, j); } _ { } } } @@ -521,7 +521,7 @@ fn load_one_source_package(src: source, p: map::hashmap) { } let description = alt p.find("description") { - some(json::string(_n)) { _n } + some(json::string(n)) { n } _ { warn("malformed source json: " + src.name + " (missing description)"); @@ -582,10 +582,10 @@ fn load_source_packages(c: cargo, src: source) { let pkgstr = io::read_whole_file_str(pkgfile); alt json::from_str(result::get(pkgstr)) { ok(json::list(js)) { - for js.each {|_j| - alt _j { - json::dict(_p) { - load_one_source_package(src, _p); + for js.each {|j| + alt j { + json::dict(p) { + load_one_source_package(src, p); } _ { warn("malformed source json: " + src.name + @@ -766,8 +766,8 @@ fn install_one_crate(c: cargo, path: str, cf: str) { fn rustc_sysroot() -> str { alt os::self_exe_path() { - some(_path) { - let path = [_path, "..", "bin", "rustc"]; + some(path) { + let path = [path, "..", "bin", "rustc"]; check vec::is_not_empty(path); let rustc = path::normalize(path::connect_many(path)); #debug(" rustc: %s", rustc); From 4686f7c316519aa4485493ea722f850f3db370fb Mon Sep 17 00:00:00 2001 From: Erick Tryzelaar Date: Mon, 11 Jun 2012 08:32:38 -0700 Subject: [PATCH 2/8] std: Add a to_str impl for json::error. --- src/cargo/cargo.rs | 7 ++++--- src/libstd/json.rs | 6 ++++++ 2 files changed, 10 insertions(+), 3 deletions(-) diff --git a/src/cargo/cargo.rs b/src/cargo/cargo.rs index 1c9ae6f866a1b..533ecf51e011a 100644 --- a/src/cargo/cargo.rs +++ b/src/cargo/cargo.rs @@ -12,6 +12,7 @@ import io::writer_util; import result; import std::{map, json, tempfile, term, sort, getopts}; import map::hashmap; +import json::to_str; import str; import vec; import getopts::{optflag, optopt, opt_present}; @@ -450,7 +451,7 @@ fn try_parse_sources(filename: str, sources: map::hashmap) { } } ok(_) { fail "malformed sources.json"; } - err(e) { fail #fmt("%s:%u:%u: %s", filename, e.line, e.col, e.msg); } + err(e) { fail #fmt("%s:%s", filename, e.to_str()); } } } @@ -570,7 +571,7 @@ fn load_source_info(c: cargo, src: source) { "(source info is not a dict)"); } err(e) { - warn(#fmt("%s:%u:%u: %s", src.name, e.line, e.col, e.msg)); + warn(#fmt("%s:%s", src.name, e.to_str())); } }; } @@ -599,7 +600,7 @@ fn load_source_packages(c: cargo, src: source) { "(packages is not a list)"); } err(e) { - warn(#fmt("%s:%u:%u: %s", src.name, e.line, e.col, e.msg)); + warn(#fmt("%s:%s", src.name, e.to_str())); } }; } diff --git a/src/libstd/json.rs b/src/libstd/json.rs index 5d9427c72b860..1ccdc5042dd39 100644 --- a/src/libstd/json.rs +++ b/src/libstd/json.rs @@ -603,6 +603,12 @@ impl of to_str::to_str for json { fn to_str() -> str { to_str(self) } } +impl of to_str::to_str for error { + fn to_str() -> str { + #fmt("%u:%u: %s", self.line, self.col, self.msg) + } +} + #[cfg(test)] mod tests { fn mk_dict(items: [(str, json)]) -> json { From 259d30237e9eea3e91bd90e5f53b4388f5e02cf0 Mon Sep 17 00:00:00 2001 From: Erick Tryzelaar Date: Mon, 11 Jun 2012 08:33:03 -0700 Subject: [PATCH 3/8] Clean up cargo imports. --- src/cargo/cargo.rs | 3 --- 1 file changed, 3 deletions(-) diff --git a/src/cargo/cargo.rs b/src/cargo/cargo.rs index 533ecf51e011a..77def540d68d4 100644 --- a/src/cargo/cargo.rs +++ b/src/cargo/cargo.rs @@ -9,12 +9,9 @@ import syntax::diagnostic; import result::{ok, err}; import io::writer_util; -import result; import std::{map, json, tempfile, term, sort, getopts}; import map::hashmap; import json::to_str; -import str; -import vec; import getopts::{optflag, optopt, opt_present}; type package = { From 7af370d0e82ff6da4dd8cbd72635fd31e3cb7e66 Mon Sep 17 00:00:00 2001 From: Erick Tryzelaar Date: Mon, 11 Jun 2012 18:58:28 -0700 Subject: [PATCH 4/8] Convert most str and vec fns to slices --- src/libcore/str.rs | 203 +++++++++++++++++++++++---------------------- src/libcore/vec.rs | 20 ++--- 2 files changed, 114 insertions(+), 109 deletions(-) diff --git a/src/libcore/str.rs b/src/libcore/str.rs index d62beaa184d28..cf81dcd7157ff 100644 --- a/src/libcore/str.rs +++ b/src/libcore/str.rs @@ -222,7 +222,7 @@ pure fn from_char(ch: char) -> str { } #[doc = "Convert a vector of chars to a string"] -pure fn from_chars(chs: [char]) -> str { +pure fn from_chars(chs: [const char]/&) -> str { let mut buf = ""; unchecked { reserve(buf, chs.len()); @@ -232,7 +232,7 @@ pure fn from_chars(chs: [char]) -> str { } #[doc = "Concatenate a vector of strings"] -pure fn concat(v: [str]) -> str { +pure fn concat(v: [const str]/&) -> str { let mut s: str = ""; for vec::each(v) {|ss| s += ss; } ret s; @@ -241,7 +241,7 @@ pure fn concat(v: [str]) -> str { #[doc = " Concatenate a vector of strings, placing a given separator between each "] -pure fn connect(v: [str], sep: str) -> str { +pure fn connect(v: [const str]/&a, sep: str) -> str { let mut s = "", first = true; for vec::each(v) {|ss| if first { first = false; } else { s += sep; } @@ -338,7 +338,7 @@ pure fn byte_slice(s: str/&, f: fn([u8]/&) -> T) -> T unsafe { } #[doc = "Convert a string to a vector of characters"] -pure fn chars(s: str) -> [char] { +pure fn chars(s: str/&) -> [char] { let mut buf = [], i = 0u; let len = len(s); while i < len { @@ -355,7 +355,7 @@ Take a substring of another. Returns a string containing `n` characters starting at byte offset `begin`. "] -pure fn substr(s: str, begin: uint, n: uint) -> str { +pure fn substr(s: str/&, begin: uint, n: uint) -> str { slice(s, begin, begin + count_bytes(s, begin, n)) } @@ -365,7 +365,7 @@ Returns a slice of the given string from the byte range [`begin`..`end`) Fails when `begin` and `end` do not point to valid characters or beyond the last character of the string "] -pure fn slice(s: str, begin: uint, end: uint) -> str unsafe { +pure fn slice(s: str/&, begin: uint, end: uint) -> str unsafe { assert is_char_boundary(s, begin); assert is_char_boundary(s, end); unsafe::slice_bytes(s, begin, end) @@ -374,7 +374,7 @@ pure fn slice(s: str, begin: uint, end: uint) -> str unsafe { #[doc = " Splits a string into substrings at each occurrence of a given character "] -pure fn split_char(s: str, sep: char) -> [str] { +pure fn split_char(s: str/&, sep: char) -> [str] { split_char_inner(s, sep, len(s), true) } @@ -384,18 +384,18 @@ character up to 'count' times The byte must be a valid UTF-8/ASCII byte "] -pure fn splitn_char(s: str, sep: char, count: uint) -> [str] { +pure fn splitn_char(s: str/&, sep: char, count: uint) -> [str] { split_char_inner(s, sep, count, true) } #[doc = " Like `split_char`, but omits empty strings from the returned vector "] -pure fn split_char_nonempty(s: str, sep: char) -> [str] { +pure fn split_char_nonempty(s: str/&, sep: char) -> [str] { split_char_inner(s, sep, len(s), false) } -pure fn split_char_inner(s: str, sep: char, count: uint, allow_empty: bool) +pure fn split_char_inner(s: str/&, sep: char, count: uint, allow_empty: bool) -> [str] unsafe { if sep < 128u as char { let b = sep as u8, l = len(s); @@ -422,7 +422,7 @@ pure fn split_char_inner(s: str, sep: char, count: uint, allow_empty: bool) #[doc = "Splits a string into substrings using a character function"] -pure fn split(s: str, sepfn: fn(char) -> bool) -> [str] { +pure fn split(s: str/&, sepfn: fn(char) -> bool) -> [str] { split_inner(s, sepfn, len(s), true) } @@ -430,16 +430,16 @@ pure fn split(s: str, sepfn: fn(char) -> bool) -> [str] { Splits a string into substrings using a character function, cutting at most `count` times. "] -pure fn splitn(s: str, sepfn: fn(char) -> bool, count: uint) -> [str] { +pure fn splitn(s: str/&, sepfn: fn(char) -> bool, count: uint) -> [str] { split_inner(s, sepfn, count, true) } #[doc = "Like `split`, but omits empty strings from the returned vector"] -pure fn split_nonempty(s: str, sepfn: fn(char) -> bool) -> [str] { +pure fn split_nonempty(s: str/&, sepfn: fn(char) -> bool) -> [str] { split_inner(s, sepfn, len(s), false) } -pure fn split_inner(s: str, sepfn: fn(cc: char) -> bool, count: uint, +pure fn split_inner(s: str/&, sepfn: fn(cc: char) -> bool, count: uint, allow_empty: bool) -> [str] unsafe { let l = len(s); let mut result = [], i = 0u, start = 0u, done = 0u; @@ -461,7 +461,7 @@ pure fn split_inner(s: str, sepfn: fn(cc: char) -> bool, count: uint, } // See Issue #1932 for why this is a naive search -pure fn iter_matches(s: str, sep: str, f: fn(uint, uint)) { +pure fn iter_matches(s: str/&a, sep: str/&b, f: fn(uint, uint)) { let sep_len = len(sep), l = len(s); assert sep_len > 0u; let mut i = 0u, match_start = 0u, match_i = 0u; @@ -488,7 +488,7 @@ pure fn iter_matches(s: str, sep: str, f: fn(uint, uint)) { } } -pure fn iter_between_matches(s: str, sep: str, f: fn(uint, uint)) { +pure fn iter_between_matches(s: str/&a, sep: str/&b, f: fn(uint, uint)) { let mut last_end = 0u; iter_matches(s, sep) {|from, to| f(last_end, from); @@ -506,7 +506,7 @@ Splits a string into a vector of the substrings separated by a given string assert [\"\", \"XXX\", \"YYY\", \"\"] == split_str(\".XXX.YYY.\", \".\") ~~~ "] -pure fn split_str(s: str, sep: str) -> [str] { +pure fn split_str(s: str/&a, sep: str/&b) -> [str] { let mut result = []; iter_between_matches(s, sep) {|from, to| unsafe { result += [unsafe::slice_bytes(s, from, to)]; } @@ -514,7 +514,7 @@ pure fn split_str(s: str, sep: str) -> [str] { result } -pure fn split_str_nonempty(s: str, sep: str) -> [str] { +pure fn split_str_nonempty(s: str/&a, sep: str/&b) -> [str] { let mut result = []; iter_between_matches(s, sep) {|from, to| if to > from { @@ -527,13 +527,13 @@ pure fn split_str_nonempty(s: str, sep: str) -> [str] { #[doc = " Splits a string into a vector of the substrings separated by LF ('\\n') "] -pure fn lines(s: str) -> [str] { split_char(s, '\n') } +pure fn lines(s: str/&) -> [str] { split_char(s, '\n') } #[doc = " Splits a string into a vector of the substrings separated by LF ('\\n') and/or CR LF ('\\r\\n') "] -pure fn lines_any(s: str) -> [str] { +pure fn lines_any(s: str/&) -> [str] { vec::map(lines(s), {|s| let l = len(s); let mut cp = s; @@ -547,19 +547,19 @@ pure fn lines_any(s: str) -> [str] { #[doc = " Splits a string into a vector of the substrings separated by whitespace "] -pure fn words(s: str) -> [str] { +pure fn words(s: str/&) -> [str] { split_nonempty(s, {|c| char::is_whitespace(c)}) } #[doc = "Convert a string to lowercase. ASCII only"] -pure fn to_lower(s: str) -> str { +pure fn to_lower(s: str/&) -> str { map(s, {|c| unchecked{(libc::tolower(c as libc::c_char)) as char} }) } #[doc = "Convert a string to uppercase. ASCII only"] -pure fn to_upper(s: str) -> str { +pure fn to_upper(s: str/&) -> str { map(s, {|c| unchecked{(libc::toupper(c as libc::c_char)) as char} }) @@ -629,7 +629,7 @@ Section: Iterating through strings Return true if a predicate matches all characters or if the string contains no characters "] -pure fn all(s: str, it: fn(char) -> bool) -> bool { +pure fn all(s: str/&, it: fn(char) -> bool) -> bool { all_between(s, 0u, len(s), it) } @@ -637,12 +637,12 @@ pure fn all(s: str, it: fn(char) -> bool) -> bool { Return true if a predicate matches any character (and false if it matches none or there are no characters) "] -pure fn any(ss: str, pred: fn(char) -> bool) -> bool { +pure fn any(ss: str/&, pred: fn(char) -> bool) -> bool { !all(ss, {|cc| !pred(cc)}) } #[doc = "Apply a function to each character"] -pure fn map(ss: str, ff: fn(char) -> char) -> str { +pure fn map(ss: str/&, ff: fn(char) -> char) -> str { let mut result = ""; unchecked { reserve(result, len(ss)); @@ -654,7 +654,7 @@ pure fn map(ss: str, ff: fn(char) -> char) -> str { } #[doc = "Iterate over the bytes in a string"] -pure fn bytes_iter(ss: str, it: fn(u8)) { +pure fn bytes_iter(ss: str/&, it: fn(u8)) { let mut pos = 0u; let len = len(ss); @@ -666,7 +666,7 @@ pure fn bytes_iter(ss: str, it: fn(u8)) { #[doc = "Iterate over the bytes in a string"] #[inline(always)] -pure fn each(s: str, it: fn(u8) -> bool) { +pure fn each(s: str/&, it: fn(u8) -> bool) { let mut i = 0u, l = len(s); while (i < l) { if !it(s[i]) { break; } @@ -676,7 +676,7 @@ pure fn each(s: str, it: fn(u8) -> bool) { #[doc = "Iterates over the chars in a string"] #[inline(always)] -pure fn each_char(s: str, it: fn(char) -> bool) { +pure fn each_char(s: str/&, it: fn(char) -> bool) { let mut pos = 0u; let len = len(s); while pos < len { @@ -687,7 +687,7 @@ pure fn each_char(s: str, it: fn(char) -> bool) { } #[doc = "Iterate over the characters in a string"] -pure fn chars_iter(s: str, it: fn(char)) { +pure fn chars_iter(s: str/&, it: fn(char)) { let mut pos = 0u; let len = len(s); while (pos < len) { @@ -700,7 +700,7 @@ pure fn chars_iter(s: str, it: fn(char)) { #[doc = " Apply a function to each substring after splitting by character "] -pure fn split_char_iter(ss: str, cc: char, ff: fn(&&str)) { +pure fn split_char_iter(ss: str/&, cc: char, ff: fn(&&str)) { vec::iter(split_char(ss, cc), ff) } @@ -708,18 +708,18 @@ pure fn split_char_iter(ss: str, cc: char, ff: fn(&&str)) { Apply a function to each substring after splitting by character, up to `count` times "] -pure fn splitn_char_iter(ss: str, sep: char, count: uint, +pure fn splitn_char_iter(ss: str/&, sep: char, count: uint, ff: fn(&&str)) unsafe { vec::iter(splitn_char(ss, sep, count), ff) } #[doc = "Apply a function to each word"] -pure fn words_iter(ss: str, ff: fn(&&str)) { +pure fn words_iter(ss: str/&, ff: fn(&&str)) { vec::iter(words(ss), ff) } #[doc = "Apply a function to each line (by '\\n')"] -pure fn lines_iter(ss: str, ff: fn(&&str)) { +pure fn lines_iter(ss: str/&, ff: fn(&&str)) { vec::iter(lines(ss), ff) } @@ -740,7 +740,7 @@ Returns the byte index of the first matching character An `option` containing the byte index of the first matching character or `none` if there is no match "] -pure fn find_char(s: str, c: char) -> option { +pure fn find_char(s: str/&, c: char) -> option { find_char_between(s, c, 0u, len(s)) } @@ -764,7 +764,7 @@ or `none` if there is no match `start` must be less than or equal to `len(s)`. `start` must be the index of a character boundary, as defined by `is_char_boundary`. "] -pure fn find_char_from(s: str, c: char, start: uint) -> option { +pure fn find_char_from(s: str/&, c: char, start: uint) -> option { find_char_between(s, c, start, len(s)) } @@ -789,7 +789,7 @@ or `none` if there is no match or equal to `len(s)`. `start` must be the index of a character boundary, as defined by `is_char_boundary`. "] -pure fn find_char_between(s: str, c: char, start: uint, end: uint) +pure fn find_char_between(s: str/&, c: char, start: uint, end: uint) -> option { if c < 128u as char { assert start <= end; @@ -819,7 +819,7 @@ Returns the byte index of the last matching character An `option` containing the byte index of the last matching character or `none` if there is no match "] -pure fn rfind_char(s: str, c: char) -> option { +pure fn rfind_char(s: str/&, c: char) -> option { rfind_char_between(s, c, len(s), 0u) } @@ -843,7 +843,7 @@ or `none` if there is no match `start` must be less than or equal to `len(s)`. `start` must be the index of a character boundary, as defined by `is_char_boundary`. "] -pure fn rfind_char_from(s: str, c: char, start: uint) -> option { +pure fn rfind_char_from(s: str/&, c: char, start: uint) -> option { rfind_char_between(s, c, start, 0u) } @@ -868,7 +868,7 @@ or `none` if there is no match or equal to `len(s)`. `start` must be the index of a character boundary, as defined by `is_char_boundary`. "] -pure fn rfind_char_between(s: str, c: char, start: uint, end: uint) +pure fn rfind_char_between(s: str/&, c: char, start: uint, end: uint) -> option { if c < 128u as char { assert start >= end; @@ -899,7 +899,7 @@ the given predicate An `option` containing the byte index of the first matching character or `none` if there is no match "] -pure fn find(s: str, f: fn(char) -> bool) -> option { +pure fn find(s: str/&, f: fn(char) -> bool) -> option { find_between(s, 0u, len(s), f) } @@ -923,7 +923,8 @@ or `none` if there is no match `start` must be less than or equal to `len(s)`. `start` must be the index of a character boundary, as defined by `is_char_boundary`. "] -pure fn find_from(s: str, start: uint, f: fn(char) -> bool) -> option { +pure fn find_from(s: str/&, start: uint, f: fn(char) + -> bool) -> option { find_between(s, start, len(s), f) } @@ -949,7 +950,7 @@ or `none` if there is no match or equal to `len(s)`. `start` must be the index of a character boundary, as defined by `is_char_boundary`. "] -pure fn find_between(s: str, start: uint, end: uint, f: fn(char) -> bool) +pure fn find_between(s: str/&, start: uint, end: uint, f: fn(char) -> bool) -> option { assert start <= end; assert end <= len(s); @@ -977,7 +978,7 @@ the given predicate An option containing the byte index of the last matching character or `none` if there is no match "] -pure fn rfind(s: str, f: fn(char) -> bool) -> option { +pure fn rfind(s: str/&, f: fn(char) -> bool) -> option { rfind_between(s, len(s), 0u, f) } @@ -1001,7 +1002,8 @@ or `none` if there is no match `start` must be less than or equal to `len(s)', `start` must be the index of a character boundary, as defined by `is_char_boundary` "] -pure fn rfind_from(s: str, start: uint, f: fn(char) -> bool) -> option { +pure fn rfind_from(s: str/&, start: uint, f: fn(char) -> bool) + -> option { rfind_between(s, start, 0u, f) } @@ -1027,7 +1029,7 @@ or `none` if there is no match than or equal to `len(s)`. `start` must be the index of a character boundary, as defined by `is_char_boundary` "] -pure fn rfind_between(s: str, start: uint, end: uint, f: fn(char) -> bool) +pure fn rfind_between(s: str/&, start: uint, end: uint, f: fn(char) -> bool) -> option { assert start >= end; assert start <= len(s); @@ -1042,7 +1044,7 @@ pure fn rfind_between(s: str, start: uint, end: uint, f: fn(char) -> bool) } // Utility used by various searching functions -pure fn match_at(haystack: str, needle: str, at: uint) -> bool { +pure fn match_at(haystack: str/&a, needle: str/&b, at: uint) -> bool { let mut i = at; for each(needle) {|c| if haystack[i] != c { ret false; } i += 1u; } ret true; @@ -1061,7 +1063,7 @@ Returns the byte index of the first matching substring An `option` containing the byte index of the first matching substring or `none` if there is no match "] -pure fn find_str(haystack: str, needle: str) -> option { +pure fn find_str(haystack: str/&a, needle: str/&b) -> option { find_str_between(haystack, needle, 0u, len(haystack)) } @@ -1084,7 +1086,7 @@ or `none` if there is no match `start` must be less than or equal to `len(s)` "] -pure fn find_str_from(haystack: str, needle: str, start: uint) +pure fn find_str_from(haystack: str/&a, needle: str/&b, start: uint) -> option { find_str_between(haystack, needle, start, len(haystack)) } @@ -1109,7 +1111,8 @@ or `none` if there is no match `start` must be less than or equal to `end` and `end` must be less than or equal to `len(s)`. "] -pure fn find_str_between(haystack: str, needle: str, start: uint, end:uint) +pure fn find_str_between(haystack: str/&a, needle: str/&b, start: uint, + end:uint) -> option { // See Issue #1932 for why this is a naive search assert end <= len(haystack); @@ -1134,7 +1137,7 @@ Returns true if one string contains another * haystack - The string to look in * needle - The string to look for "] -pure fn contains(haystack: str, needle: str) -> bool { +pure fn contains(haystack: str/&a, needle: str/&b) -> bool { option::is_some(find_str(haystack, needle)) } @@ -1146,7 +1149,7 @@ Returns true if one string starts with another * haystack - The string to look in * needle - The string to look for "] -pure fn starts_with(haystack: str, needle: str) -> bool unsafe { +pure fn starts_with(haystack: str/&a, needle: str/&b) -> bool unsafe { let haystack_len = len(haystack), needle_len = len(needle); if needle_len == 0u { true } else if needle_len > haystack_len { false } @@ -1161,7 +1164,7 @@ Returns true if one string ends with another * haystack - The string to look in * needle - The string to look for "] -pure fn ends_with(haystack: str, needle: str) -> bool { +pure fn ends_with(haystack: str/&a, needle: str/&b) -> bool { let haystack_len = len(haystack), needle_len = len(needle); if needle_len == 0u { true } else if needle_len > haystack_len { false } @@ -1173,24 +1176,24 @@ Section: String properties */ #[doc = "Determines if a string contains only ASCII characters"] -pure fn is_ascii(s: str) -> bool { +pure fn is_ascii(s: str/&) -> bool { let mut i: uint = len(s); while i > 0u { i -= 1u; if !u8::is_ascii(s[i]) { ret false; } } ret true; } #[doc = "Returns true if the string has length 0"] -pure fn is_empty(s: str) -> bool { len(s) == 0u } +pure fn is_empty(s: str/&) -> bool { len(s) == 0u } #[doc = "Returns true if the string has length greater than 0"] -pure fn is_not_empty(s: str) -> bool { !is_empty(s) } +pure fn is_not_empty(s: str/&) -> bool { !is_empty(s) } #[doc = " Returns true if the string contains only whitespace Whitespace characters are determined by `char::is_whitespace` "] -pure fn is_whitespace(s: str) -> bool { +pure fn is_whitespace(s: str/&) -> bool { ret all(s, char::is_whitespace); } @@ -1199,27 +1202,26 @@ Returns true if the string contains only alphanumerics Alphanumeric characters are determined by `char::is_alphanumeric` "] -fn is_alphanumeric(s: str) -> bool { +fn is_alphanumeric(s: str/&) -> bool { ret all(s, char::is_alphanumeric); } #[doc = " Returns the string length/size in bytes not counting the null terminator "] -pure fn len(s: str) -> uint unsafe { - let repr: *vec::unsafe::vec_repr = ::unsafe::reinterpret_cast(s); - (*repr).fill - 1u +pure fn len(s: str/&) -> uint { + unpack_slice(s) { |_p, n| n - 1u } } #[doc = "Returns the number of characters that a string holds"] -pure fn char_len(s: str) -> uint { count_chars(s, 0u, len(s)) } +pure fn char_len(s: str/&) -> uint { count_chars(s, 0u, len(s)) } /* Section: Misc */ #[doc = "Determines if a vector of bytes contains valid UTF-8"] -pure fn is_utf8(v: [const u8]) -> bool { +pure fn is_utf8(v: [const u8]/&) -> bool { let mut i = 0u; let total = vec::len::(v); while i < total { @@ -1237,7 +1239,7 @@ pure fn is_utf8(v: [const u8]) -> bool { } #[doc = "Determines if a vector of `u16` contains valid UTF-16"] -pure fn is_utf16(v: [const u16]) -> bool { +pure fn is_utf16(v: [const u16]/&) -> bool { let len = vec::len(v); let mut i = 0u; while (i < len) { @@ -1258,7 +1260,7 @@ pure fn is_utf16(v: [const u16]) -> bool { } #[doc = "Converts to a vector of `u16` encoded as UTF-16"] -pure fn to_utf16(s: str) -> [u16] { +pure fn to_utf16(s: str/&) -> [u16] { let mut u = []; chars_iter(s) {|cch| // Arithmetic with u32 literals is easier on the eyes than chars. @@ -1280,7 +1282,7 @@ pure fn to_utf16(s: str) -> [u16] { ret u; } -pure fn utf16_chars(v: [const u16], f: fn(char)) { +pure fn utf16_chars(v: [const u16]/&, f: fn(char)) { let len = vec::len(v); let mut i = 0u; while (i < len && v[i] != 0u16) { @@ -1305,7 +1307,7 @@ pure fn utf16_chars(v: [const u16], f: fn(char)) { } -pure fn from_utf16(v: [const u16]) -> str { +pure fn from_utf16(v: [const u16]/&) -> str { let mut buf = ""; unchecked { reserve(buf, vec::len(v)); @@ -1328,7 +1330,7 @@ As char_len but for a slice of a string The number of Unicode characters in `s` between the given indices. "] -pure fn count_chars(s: str, start: uint, end: uint) -> uint { +pure fn count_chars(s: str/&, start: uint, end: uint) -> uint { assert is_char_boundary(s, start); assert is_char_boundary(s, end); let mut i = start, len = 0u; @@ -1343,7 +1345,7 @@ pure fn count_chars(s: str, start: uint, end: uint) -> uint { #[doc = " Counts the number of bytes taken by the `n` in `s` starting from `start`. "] -pure fn count_bytes(s: str, start: uint, n: uint) -> uint { +pure fn count_bytes(s: str/&b, start: uint, n: uint) -> uint { assert is_char_boundary(s, start); let mut end = start, cnt = n; let l = len(s); @@ -1375,7 +1377,7 @@ pure fn utf8_char_width(b: u8) -> uint { Returns false if the index points into the middle of a multi-byte character sequence. "] -pure fn is_char_boundary(s: str, index: uint) -> bool { +pure fn is_char_boundary(s: str/&, index: uint) -> bool { if index == len(s) { ret true; } let b = s[index]; ret b < 128u8 || b >= 192u8; @@ -1428,7 +1430,7 @@ index of the next unicode character. If `i` is greater than or equal to the length of the string. If `i` is not the index of the beginning of a valid UTF-8 character. "] -pure fn char_range_at(s: str, i: uint) -> {ch: char, next: uint} { +pure fn char_range_at(s: str/&, i: uint) -> {ch: char, next: uint} { let b0 = s[i]; let w = utf8_char_width(b0); assert (w != 0u); @@ -1451,14 +1453,14 @@ pure fn char_range_at(s: str, i: uint) -> {ch: char, next: uint} { } #[doc = "Pluck a character out of a string"] -pure fn char_at(s: str, i: uint) -> char { ret char_range_at(s, i).ch; } +pure fn char_at(s: str/&, i: uint) -> char { ret char_range_at(s, i).ch; } #[doc = " Given a byte position and a str, return the previous char and its position This function can be used to iterate over a unicode string in reverse. "] -pure fn char_range_at_reverse(ss: str, start: uint) +pure fn char_range_at_reverse(ss: str/&, start: uint) -> {ch: char, prev: uint} { let mut prev = start; @@ -1497,7 +1499,7 @@ Loop through a substring, char by char `true` If execution proceeded correctly, `false` if it was interrupted, that is if `it` returned `false` at any point. "] -pure fn all_between(s: str, start: uint, end: uint, +pure fn all_between(s: str/&, start: uint, end: uint, it: fn(char) -> bool) -> bool { assert is_char_boundary(s, start); let mut i = start; @@ -1530,7 +1532,7 @@ Loop through a substring, char by char `true` if `it` returns `true` for any character "] -pure fn any_between(s: str, start: uint, end: uint, +pure fn any_between(s: str/&, start: uint, end: uint, it: fn(char) -> bool) -> bool { !all_between(s, start, end, {|c| !it(c)}) } @@ -1668,7 +1670,7 @@ pure fn capacity(&&s: str) -> uint unsafe { } #[doc = "Escape each char in `s` with char::escape_default."] -pure fn escape_default(s: str) -> str { +pure fn escape_default(s: str/&) -> str { let mut out: str = ""; unchecked { reserve_at_least(out, str::len(s)); @@ -1678,7 +1680,7 @@ pure fn escape_default(s: str) -> str { } #[doc = "Escape each char in `s` with char::escape_unicode."] -pure fn escape_unicode(s: str) -> str { +pure fn escape_unicode(s: str/&) -> str { let mut out: str = ""; unchecked { reserve_at_least(out, str::len(s)); @@ -1762,11 +1764,11 @@ mod unsafe { If begin is greater than end. If end is greater than the length of the string. "] - unsafe fn slice_bytes(s: str, begin: uint, end: uint) -> str unsafe { - assert (begin <= end); - assert (end <= len(s)); + unsafe fn slice_bytes(s: str/&, begin: uint, end: uint) -> str unsafe { + unpack_slice(s) { |sbuf, n| + assert (begin <= end); + assert (end <= n); - let mut v = as_buf(s) { |sbuf| let mut v = []; vec::reserve(v, end - begin + 1u); vec::as_buf(v) { |vbuf| @@ -1774,10 +1776,9 @@ mod unsafe { ptr::memcpy(vbuf, src, end - begin); } vec::unsafe::set_len(v, end - begin); - v - }; - v += [0u8]; - ret ::unsafe::transmute(v); + v += [0u8]; + ::unsafe::transmute(v) + } } #[doc = "Appends a byte to a string. (Not UTF-8 safe)."] @@ -1834,6 +1835,19 @@ mod unsafe { #[doc = "Extension methods for strings"] impl extensions for str { + #[doc = "Returns a string with leading and trailing whitespace removed"] + #[inline] + fn trim() -> str { trim(self) } + #[doc = "Returns a string with leading whitespace removed"] + #[inline] + fn trim_left() -> str { trim_left(self) } + #[doc = "Returns a string with trailing whitespace removed"] + #[inline] + fn trim_right() -> str { trim_right(self) } +} + +#[doc = "Extension methods for strings"] +impl extensions/& for str/& { #[doc = " Return true if a predicate matches all characters or if the string contains no characters @@ -1848,7 +1862,7 @@ impl extensions for str { fn any(it: fn(char) -> bool) -> bool { any(self, it) } #[doc = "Returns true if one string contains another"] #[inline] - fn contains(needle: str) -> bool { contains(self, needle) } + fn contains(needle: str/&a) -> bool { contains(self, needle) } #[doc = "Iterate over the bytes in a string"] #[inline] fn each(it: fn(u8) -> bool) { each(self, it) } @@ -1857,7 +1871,7 @@ impl extensions for str { fn each_char(it: fn(char) -> bool) { each_char(self, it) } #[doc = "Returns true if one string ends with another"] #[inline] - fn ends_with(needle: str) -> bool { ends_with(self, needle) } + fn ends_with(needle: str/&) -> bool { ends_with(self, needle) } #[doc = "Returns true if the string has length 0"] #[inline] fn is_empty() -> bool { is_empty(self) } @@ -1902,10 +1916,10 @@ impl extensions for str { string "] #[inline] - fn split_str(sep: str) -> [str] { split_str(self, sep) } + fn split_str(sep: str/&a) -> [str] { split_str(self, sep) } #[doc = "Returns true if one string starts with another"] #[inline] - fn starts_with(needle: str) -> bool { starts_with(self, needle) } + fn starts_with(needle: str/&a) -> bool { starts_with(self, needle) } #[doc = " Take a substring of another. @@ -1920,15 +1934,6 @@ impl extensions for str { #[doc = "Convert a string to uppercase"] #[inline] fn to_upper() -> str { to_upper(self) } - #[doc = "Returns a string with leading and trailing whitespace removed"] - #[inline] - fn trim() -> str { trim(self) } - #[doc = "Returns a string with leading whitespace removed"] - #[inline] - fn trim_left() -> str { trim_left(self) } - #[doc = "Returns a string with trailing whitespace removed"] - #[inline] - fn trim_right() -> str { trim_right(self) } #[doc = "Escape each char in `s` with char::escape_default."] #[inline] fn escape_default() -> str { escape_default(self) } @@ -2091,7 +2096,7 @@ mod tests { #[test] fn test_split_str() { - fn t(s: str, sep: str, i: int, k: str) { + fn t(s: str, sep: str/&a, i: int, k: str) { let v = split_str(s, sep); assert eq(v[i], k); } diff --git a/src/libcore/vec.rs b/src/libcore/vec.rs index a94b8e6e1b49e..7058f2202b9f0 100644 --- a/src/libcore/vec.rs +++ b/src/libcore/vec.rs @@ -266,7 +266,7 @@ pure fn view(v: [T]/&, start: uint, end: uint) -> [T]/&a { #[doc = " Split the vector `v` by applying each element against the predicate `f`. "] -fn split(v: [T], f: fn(T) -> bool) -> [[T]] { +fn split(v: [T]/&, f: fn(T) -> bool) -> [[T]] { let ln = len(v); if (ln == 0u) { ret [] } @@ -289,7 +289,7 @@ fn split(v: [T], f: fn(T) -> bool) -> [[T]] { Split the vector `v` by applying each element against the predicate `f` up to `n` times. "] -fn splitn(v: [T], n: uint, f: fn(T) -> bool) -> [[T]] { +fn splitn(v: [T]/&, n: uint, f: fn(T) -> bool) -> [[T]] { let ln = len(v); if (ln == 0u) { ret [] } @@ -315,7 +315,7 @@ fn splitn(v: [T], n: uint, f: fn(T) -> bool) -> [[T]] { Reverse split the vector `v` by applying each element against the predicate `f`. "] -fn rsplit(v: [T], f: fn(T) -> bool) -> [[T]] { +fn rsplit(v: [T]/&, f: fn(T) -> bool) -> [[T]] { let ln = len(v); if (ln == 0u) { ret [] } @@ -338,7 +338,7 @@ fn rsplit(v: [T], f: fn(T) -> bool) -> [[T]] { Reverse split the vector `v` by applying each element against the predicate `f` up to `n times. "] -fn rsplitn(v: [T], n: uint, f: fn(T) -> bool) -> [[T]] { +fn rsplitn(v: [T]/&, n: uint, f: fn(T) -> bool) -> [[T]] { let ln = len(v); if (ln == 0u) { ret [] } @@ -776,7 +776,7 @@ Convert two vectors to a vector of pairs Returns a vector of tuples, where the i-th tuple contains contains the i-th elements from each of the input vectors. "] -pure fn zip(v: [const T], u: [const U]) -> [(T, U)] { +pure fn zip(v: [const T]/&, u: [const U]/&) -> [(T, U)] { let mut zipped = []; let sz = len(v); let mut i = 0u; @@ -859,7 +859,7 @@ Iterates over a vector, with option to break Return true to continue, false to break. "] #[inline(always)] -pure fn each(v: [T]/&, f: fn(T) -> bool) unsafe { +pure fn each(v: [const T]/&, f: fn(T) -> bool) unsafe { vec::unpack_slice(v) {|p, n| let mut n = n; let mut p = p; @@ -877,7 +877,7 @@ Iterates over a vector's elements and indices Return true to continue, false to break. "] #[inline(always)] -pure fn eachi(v: [T]/&, f: fn(uint, T) -> bool) unsafe { +pure fn eachi(v: [const T]/&, f: fn(uint, T) -> bool) unsafe { vec::unpack_slice(v) {|p, n| let mut i = 0u; let mut p = p; @@ -996,7 +996,7 @@ fn as_mut_buf(v: [mut E]/&, f: fn(*mut E) -> T) -> T unsafe { Work with the buffer and length of a slice. "] #[inline(always)] -pure fn unpack_slice(s: [T]/&, +pure fn unpack_slice(s: [const T]/&, f: fn(*T, uint) -> U) -> U unsafe { let v : *(*T,uint) = ::unsafe::reinterpret_cast(ptr::addr_of(s)); let (buf,len) = *v; @@ -1316,7 +1316,7 @@ mod u8 { // // This cannot be used with iter-trait.rs because of the region pointer // required in the slice. -impl extensions/& of iter::base_iter for [A]/& { +impl extensions/& of iter::base_iter for [const A]/& { fn each(blk: fn(A) -> bool) { each(self, blk) } fn size_hint() -> option { some(len(self)) } fn eachi(blk: fn(uint, A) -> bool) { iter::eachi(self, blk) } @@ -1328,7 +1328,7 @@ impl extensions/& of iter::base_iter for [A]/& { fn contains(x: A) -> bool { iter::contains(self, x) } fn count(x: A) -> uint { iter::count(self, x) } } -impl extensions/& for [A]/& { +impl extensions/& for [const A]/& { fn filter_to_vec(pred: fn(A) -> bool) -> [A] { iter::filter_to_vec(self, pred) } From fd011d3cf7a10a2e2a9e86b4a106b531ae123a2d Mon Sep 17 00:00:00 2001 From: Erick Tryzelaar Date: Tue, 12 Jun 2012 16:16:47 -0700 Subject: [PATCH 5/8] Rewrite int/uint helper functions to use refs This lets us pass them to generic functions. --- src/libcore/int-template.rs | 30 +++++++++++++++--------------- src/libcore/int-template/int.rs | 2 +- src/libcore/uint-template.rs | 30 +++++++++++++++--------------- src/libcore/uint-template/uint.rs | 2 +- src/libstd/map.rs | 14 ++++---------- 5 files changed, 36 insertions(+), 42 deletions(-) diff --git a/src/libcore/int-template.rs b/src/libcore/int-template.rs index cfe6169760868..b1d1457654e22 100644 --- a/src/libcore/int-template.rs +++ b/src/libcore/int-template.rs @@ -16,21 +16,21 @@ export ord, eq, num; const min_value: T = -1 as T << (inst::bits - 1 as T); const max_value: T = min_value - 1 as T; -pure fn min(x: T, y: T) -> T { if x < y { x } else { y } } -pure fn max(x: T, y: T) -> T { if x > y { x } else { y } } - -pure fn add(x: T, y: T) -> T { x + y } -pure fn sub(x: T, y: T) -> T { x - y } -pure fn mul(x: T, y: T) -> T { x * y } -pure fn div(x: T, y: T) -> T { x / y } -pure fn rem(x: T, y: T) -> T { x % y } - -pure fn lt(x: T, y: T) -> bool { x < y } -pure fn le(x: T, y: T) -> bool { x <= y } -pure fn eq(x: T, y: T) -> bool { x == y } -pure fn ne(x: T, y: T) -> bool { x != y } -pure fn ge(x: T, y: T) -> bool { x >= y } -pure fn gt(x: T, y: T) -> bool { x > y } +pure fn min(&&x: T, &&y: T) -> T { if x < y { x } else { y } } +pure fn max(&&x: T, &&y: T) -> T { if x > y { x } else { y } } + +pure fn add(&&x: T, &&y: T) -> T { x + y } +pure fn sub(&&x: T, &&y: T) -> T { x - y } +pure fn mul(&&x: T, &&y: T) -> T { x * y } +pure fn div(&&x: T, &&y: T) -> T { x / y } +pure fn rem(&&x: T, &&y: T) -> T { x % y } + +pure fn lt(&&x: T, &&y: T) -> bool { x < y } +pure fn le(&&x: T, &&y: T) -> bool { x <= y } +pure fn eq(&&x: T, &&y: T) -> bool { x == y } +pure fn ne(&&x: T, &&y: T) -> bool { x != y } +pure fn ge(&&x: T, &&y: T) -> bool { x >= y } +pure fn gt(&&x: T, &&y: T) -> bool { x > y } pure fn is_positive(x: T) -> bool { x > 0 as T } pure fn is_negative(x: T) -> bool { x < 0 as T } diff --git a/src/libcore/int-template/int.rs b/src/libcore/int-template/int.rs index b7c4d1717bbca..d28333c79e63d 100644 --- a/src/libcore/int-template/int.rs +++ b/src/libcore/int-template/int.rs @@ -7,7 +7,7 @@ const bits: T = 32 as T; const bits: T = 64 as T; #[doc = "Produce a uint suitable for use in a hash table"] -pure fn hash(x: int) -> uint { ret x as uint; } +pure fn hash(&&x: int) -> uint { ret x as uint; } #[doc = "Returns `base` raised to the power of `exponent`"] fn pow(base: int, exponent: uint) -> int { diff --git a/src/libcore/uint-template.rs b/src/libcore/uint-template.rs index cb9b759eeaed1..fda4253a688d4 100644 --- a/src/libcore/uint-template.rs +++ b/src/libcore/uint-template.rs @@ -16,21 +16,21 @@ export ord, eq, num; const min_value: T = 0 as T; const max_value: T = 0 as T - 1 as T; -pure fn min(x: T, y: T) -> T { if x < y { x } else { y } } -pure fn max(x: T, y: T) -> T { if x > y { x } else { y } } - -pure fn add(x: T, y: T) -> T { x + y } -pure fn sub(x: T, y: T) -> T { x - y } -pure fn mul(x: T, y: T) -> T { x * y } -pure fn div(x: T, y: T) -> T { x / y } -pure fn rem(x: T, y: T) -> T { x % y } - -pure fn lt(x: T, y: T) -> bool { x < y } -pure fn le(x: T, y: T) -> bool { x <= y } -pure fn eq(x: T, y: T) -> bool { x == y } -pure fn ne(x: T, y: T) -> bool { x != y } -pure fn ge(x: T, y: T) -> bool { x >= y } -pure fn gt(x: T, y: T) -> bool { x > y } +pure fn min(&&x: T, &&y: T) -> T { if x < y { x } else { y } } +pure fn max(&&x: T, &&y: T) -> T { if x > y { x } else { y } } + +pure fn add(&&x: T, &&y: T) -> T { x + y } +pure fn sub(&&x: T, &&y: T) -> T { x - y } +pure fn mul(&&x: T, &&y: T) -> T { x * y } +pure fn div(&&x: T, &&y: T) -> T { x / y } +pure fn rem(&&x: T, &&y: T) -> T { x % y } + +pure fn lt(&&x: T, &&y: T) -> bool { x < y } +pure fn le(&&x: T, &&y: T) -> bool { x <= y } +pure fn eq(&&x: T, &&y: T) -> bool { x == y } +pure fn ne(&&x: T, &&y: T) -> bool { x != y } +pure fn ge(&&x: T, &&y: T) -> bool { x >= y } +pure fn gt(&&x: T, &&y: T) -> bool { x > y } pure fn is_positive(x: T) -> bool { x > 0 as T } pure fn is_negative(x: T) -> bool { x < 0 as T } diff --git a/src/libcore/uint-template/uint.rs b/src/libcore/uint-template/uint.rs index c8fb9731d472f..e1bb89c27c4e7 100644 --- a/src/libcore/uint-template/uint.rs +++ b/src/libcore/uint-template/uint.rs @@ -54,7 +54,7 @@ is either `x/y` or `x/y + 1`. pure fn div_floor(x: uint, y: uint) -> uint { ret x / y; } #[doc = "Produce a uint suitable for use in a hash table"] -pure fn hash(x: uint) -> uint { ret x; } +pure fn hash(&&x: uint) -> uint { ret x; } #[doc = " Iterate over the range [`lo`..`hi`), or stop when requested diff --git a/src/libstd/map.rs b/src/libstd/map.rs index fc6d3ee52fc7f..afcf77ad80030 100644 --- a/src/libstd/map.rs +++ b/src/libstd/map.rs @@ -297,20 +297,14 @@ fn bytes_hash() -> hashmap<[u8], V> { ret hashmap(vec::u8::hash, vec::u8::eq); } -fn hash_int(&&x: int) -> uint { int::hash(x) } -fn eq_int(&&a: int, &&b: int) -> bool { ret a == b; } - #[doc = "Construct a hashmap for int keys"] fn int_hash() -> hashmap { - ret hashmap(hash_int, eq_int); + ret hashmap(int::hash, int::eq); } -fn hash_uint(&&x: uint) -> uint { uint::hash(x) } -fn eq_uint(&&a: uint, &&b: uint) -> bool { ret a == b; } - #[doc = "Construct a hashmap for uint keys"] fn uint_hash() -> hashmap { - ret hashmap(hash_uint, eq_uint); + ret hashmap(uint::hash, uint::eq); } #[doc = " @@ -355,12 +349,12 @@ fn hash_from_bytes(items: [([u8], V)]) -> hashmap<[u8], V> { #[doc = "Construct a hashmap from a vector with int keys"] fn hash_from_ints(items: [(int, V)]) -> hashmap { - hash_from_vec(hash_int, eq_int, items) + hash_from_vec(int::hash, int::eq, items) } #[doc = "Construct a hashmap from a vector with uint keys"] fn hash_from_uints(items: [(uint, V)]) -> hashmap { - hash_from_vec(hash_uint, eq_uint, items) + hash_from_vec(uint::hash, uint::eq, items) } #[cfg(test)] From 81281dbc880eb6e6b8bbb5866428daa34cea6572 Mon Sep 17 00:00:00 2001 From: Erick Tryzelaar Date: Tue, 12 Jun 2012 16:16:58 -0700 Subject: [PATCH 6/8] whitespace cleanup --- src/libstd/map.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/libstd/map.rs b/src/libstd/map.rs index afcf77ad80030..67085502cc5eb 100644 --- a/src/libstd/map.rs +++ b/src/libstd/map.rs @@ -328,7 +328,7 @@ fn vec_from_set(s: set) -> [T] { #[doc = "Construct a hashmap from a vector"] fn hash_from_vec(hasher: hashfn, eqer: eqfn, - items: [(K, V)]) -> hashmap { + items: [(K, V)]) -> hashmap { let map = hashmap(hasher, eqer); vec::iter(items) { |item| let (key, value) = item; From 44966c80e715a174dee080c26b881c8e98d288ef Mon Sep 17 00:00:00 2001 From: Erick Tryzelaar Date: Tue, 12 Jun 2012 16:17:41 -0700 Subject: [PATCH 7/8] std: Remove copy from all the hashmap key type params --- src/libstd/map.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/libstd/map.rs b/src/libstd/map.rs index 67085502cc5eb..140349089a81d 100644 --- a/src/libstd/map.rs +++ b/src/libstd/map.rs @@ -262,7 +262,7 @@ mod chained { ret vec::to_mut(vec::from_elem(nchains, absent)); } - fn mk(hasher: hashfn, eqer: eqfn) -> t { + fn mk(hasher: hashfn, eqer: eqfn) -> t { let initial_capacity: uint = 32u; // 2^5 let slf: t = @{mut count: 0u, mut chains: chains(initial_capacity), @@ -282,7 +282,7 @@ Parameters: hasher - The hash function for key type K eqer - The equality function for key type K */ -fn hashmap(hasher: hashfn, eqer: eqfn) +fn hashmap(hasher: hashfn, eqer: eqfn) -> hashmap { chained::mk(hasher, eqer) } From 4b902cf55e6706922c0c6b1bb45a65203add8909 Mon Sep 17 00:00:00 2001 From: Erick Tryzelaar Date: Tue, 12 Jun 2012 17:20:51 -0700 Subject: [PATCH 8/8] Fix json no-implicit-copy warnings --- src/cargo/cargo.rs | 42 ++++----- src/libstd/json.rs | 223 ++++++++++++++++++++++++--------------------- 2 files changed, 139 insertions(+), 126 deletions(-) diff --git a/src/cargo/cargo.rs b/src/cargo/cargo.rs index 77def540d68d4..2bfde838bce43 100644 --- a/src/cargo/cargo.rs +++ b/src/cargo/cargo.rs @@ -400,25 +400,25 @@ fn parse_source(name: str, j: json::json) -> source { json::dict(j) { let mut url = alt j.find("url") { some(json::string(u)) { - u + *u } _ { fail "needed 'url' field in source"; } }; let method = alt j.find("method") { some(json::string(u)) { - u + *u } _ { assume_source_method(url) } }; let key = alt j.find("key") { some(json::string(u)) { - some(u) + some(*u) } _ { none } }; let keyfp = alt j.find("keyfp") { some(json::string(u)) { - some(u) + some(*u) } _ { none } }; @@ -455,13 +455,13 @@ fn try_parse_sources(filename: str, sources: map::hashmap) { fn load_one_source_package(src: source, p: map::hashmap) { let name = alt p.find("name") { some(json::string(n)) { - if !valid_pkg_name(n) { - warn("malformed source json: " + src.name + ", '" + n + "'"+ + if !valid_pkg_name(*n) { + warn("malformed source json: " + src.name + ", '" + *n + "'"+ " is an invalid name (alphanumeric, underscores and" + " dashes only)"); ret; } - n + *n } _ { warn("malformed source json: " + src.name + " (missing name)"); @@ -471,12 +471,12 @@ fn load_one_source_package(src: source, p: map::hashmap) { let uuid = alt p.find("uuid") { some(json::string(n)) { - if !is_uuid(n) { - warn("malformed source json: " + src.name + ", '" + n + "'"+ + if !is_uuid(*n) { + warn("malformed source json: " + src.name + ", '" + *n + "'"+ " is an invalid uuid"); ret; } - n + *n } _ { warn("malformed source json: " + src.name + " (missing uuid)"); @@ -485,7 +485,7 @@ fn load_one_source_package(src: source, p: map::hashmap) { }; let url = alt p.find("url") { - some(json::string(n)) { n } + some(json::string(n)) { *n } _ { warn("malformed source json: " + src.name + " (missing url)"); ret; @@ -493,7 +493,7 @@ fn load_one_source_package(src: source, p: map::hashmap) { }; let method = alt p.find("method") { - some(json::string(n)) { n } + some(json::string(n)) { *n } _ { warn("malformed source json: " + src.name + " (missing method)"); ret; @@ -501,16 +501,16 @@ fn load_one_source_package(src: source, p: map::hashmap) { }; let ref = alt p.find("ref") { - some(json::string(n)) { some(n) } + some(json::string(n)) { some(*n) } _ { none } }; let mut tags = []; alt p.find("tags") { some(json::list(js)) { - for js.each {|j| + for (*js).each {|j| alt j { - json::string(j) { vec::grow(tags, 1u, j); } + json::string(j) { vec::grow(tags, 1u, *j); } _ { } } } @@ -519,7 +519,7 @@ fn load_one_source_package(src: source, p: map::hashmap) { } let description = alt p.find("description") { - some(json::string(n)) { n } + some(json::string(n)) { *n } _ { warn("malformed source json: " + src.name + " (missing description)"); @@ -580,7 +580,7 @@ fn load_source_packages(c: cargo, src: source) { let pkgstr = io::read_whole_file_str(pkgfile); alt json::from_str(result::get(pkgstr)) { ok(json::list(js)) { - for js.each {|j| + for (*js).each {|j| alt j { json::dict(p) { load_one_source_package(src, p); @@ -1576,18 +1576,18 @@ fn dump_sources(c: cargo) { let chash = map::str_hash(); let child = json::dict(chash); - chash.insert("url", json::string(v.url)); - chash.insert("method", json::string(v.method)); + chash.insert("url", json::string(@v.url)); + chash.insert("method", json::string(@v.method)); alt copy v.key { some(key) { - chash.insert("key", json::string(key)); + chash.insert("key", json::string(@key)); } _ {} } alt copy v.keyfp { some(keyfp) { - chash.insert("keyfp", json::string(keyfp)); + chash.insert("keyfp", json::string(@keyfp)); } _ {} } diff --git a/src/libstd/json.rs b/src/libstd/json.rs index 1ccdc5042dd39..1ac6a54765978 100644 --- a/src/libstd/json.rs +++ b/src/libstd/json.rs @@ -28,17 +28,17 @@ export null; #[doc = "Represents a json value"] enum json { num(float), - string(str), + string(@str), boolean(bool), - list([json]), - dict(map::hashmap), + list(@[json]), + dict(map::hashmap), null, } type error = { line: uint, col: uint, - msg: str, + msg: @str, }; #[doc = "Serializes a json value into a io::writer"] @@ -46,22 +46,7 @@ fn to_writer(wr: io::writer, j: json) { alt j { num(n) { wr.write_str(float::to_str(n, 6u)); } string(s) { - wr.write_char('"'); - let mut escaped = ""; - str::chars_iter(s) { |c| - alt c { - '"' { escaped += "\\\""; } - '\\' { escaped += "\\\\"; } - '\x08' { escaped += "\\b"; } - '\x0c' { escaped += "\\f"; } - '\n' { escaped += "\\n"; } - '\r' { escaped += "\\r"; } - '\t' { escaped += "\\t"; } - _ { escaped += str::from_char(c); } - } - }; - wr.write_str(escaped); - wr.write_char('"'); + wr.write_str(escape_str(*s)); } boolean(b) { wr.write_str(if b { "true" } else { "false" }); @@ -69,7 +54,7 @@ fn to_writer(wr: io::writer, j: json) { list(v) { wr.write_char('['); let mut first = true; - vec::iter(v) { |item| + for (*v).each { |item| if !first { wr.write_str(", "); } @@ -91,7 +76,7 @@ fn to_writer(wr: io::writer, j: json) { wr.write_str(", "); } first = false; - to_writer(wr, string(key)); + wr.write_str(escape_str(key)); wr.write_str(": "); to_writer(wr, value); }; @@ -103,6 +88,26 @@ fn to_writer(wr: io::writer, j: json) { } } +fn escape_str(s: str) -> str { + let mut escaped = "\""; + str::chars_iter(s) { |c| + alt c { + '"' { escaped += "\\\""; } + '\\' { escaped += "\\\\"; } + '\x08' { escaped += "\\b"; } + '\x0c' { escaped += "\\f"; } + '\n' { escaped += "\\n"; } + '\r' { escaped += "\\r"; } + '\t' { escaped += "\\t"; } + _ { escaped += str::from_char(c); } + } + }; + + escaped += "\""; + + escaped +} + #[doc = "Serializes a json value into a string"] fn to_str(j: json) -> str { io::with_str_writer { |wr| to_writer(wr, j) } @@ -134,8 +139,8 @@ impl parser for parser { self.ch } - fn error(msg: str) -> result { - err({ line: self.line, col: self.col, msg: msg }) + fn error(+msg: str) -> result { + err({ line: self.line, col: self.col, msg: @msg }) } fn parse() -> result { @@ -318,7 +323,7 @@ impl parser for parser { ok(res) } - fn parse_str() -> result { + fn parse_str() -> result<@str, error> { let mut escape = false; let mut res = ""; @@ -365,7 +370,7 @@ impl parser for parser { } else { if self.ch == '"' { self.bump(); - ret ok(res); + ret ok(@res); } str::push_char(res, self.ch); } @@ -382,7 +387,7 @@ impl parser for parser { if self.ch == ']' { self.bump(); - ret ok(list(values)); + ret ok(list(@values)); } loop { @@ -398,7 +403,7 @@ impl parser for parser { alt self.ch { ',' { self.bump(); } - ']' { self.bump(); ret ok(list(values)); } + ']' { self.bump(); ret ok(list(@values)); } _ { ret self.error("expecting ',' or ']'"); } } }; @@ -436,7 +441,7 @@ impl parser for parser { self.bump(); alt self.parse_value() { - ok(value) { values.insert(key, value); } + ok(value) { values.insert(copy *key, value); } e { ret e; } } self.parse_whitespace(); @@ -478,7 +483,7 @@ fn eq(value0: json, value1: json) -> bool { (num(f0), num(f1)) { f0 == f1 } (string(s0), string(s1)) { s0 == s1 } (boolean(b0), boolean(b1)) { b0 == b1 } - (list(l0), list(l1)) { vec::all2(l0, l1, eq) } + (list(l0), list(l1)) { vec::all2(*l0, *l1, eq) } (dict(d0), dict(d1)) { if d0.size() == d1.size() { let mut equal = true; @@ -558,13 +563,17 @@ impl of to_json for bool { } impl of to_json for str { + fn to_json() -> json { string(@copy self) } +} + +impl of to_json for @str { fn to_json() -> json { string(self) } } impl of to_json for (A, B) { fn to_json() -> json { let (a, b) = self; - list([a.to_json(), b.to_json()]) + list(@[a.to_json(), b.to_json()]) } } @@ -572,19 +581,19 @@ impl of to_json for (A, B, C) { fn to_json() -> json { let (a, b, c) = self; - list([a.to_json(), b.to_json(), c.to_json()]) + list(@[a.to_json(), b.to_json(), c.to_json()]) } } impl of to_json for [A] { - fn to_json() -> json { list(self.map { |elt| elt.to_json() }) } + fn to_json() -> json { list(@self.map { |elt| elt.to_json() }) } } impl of to_json for hashmap { fn to_json() -> json { let d = map::str_hash(); for self.each() { |key, value| - d.insert(key, value.to_json()); + d.insert(copy key, value.to_json()); } dict(d) } @@ -605,7 +614,7 @@ impl of to_str::to_str for json { impl of to_str::to_str for error { fn to_str() -> str { - #fmt("%u:%u: %s", self.line, self.col, self.msg) + #fmt("%u:%u: %s", self.line, self.col, *self.msg) } } @@ -615,7 +624,7 @@ mod tests { let d = map::str_hash(); vec::iter(items) { |item| - let (key, value) = item; + let (key, value) = copy item; d.insert(key, value); }; @@ -637,8 +646,8 @@ mod tests { #[test] fn test_write_str() { - assert to_str(string("")) == "\"\""; - assert to_str(string("foo")) == "\"foo\""; + assert to_str(string(@"")) == "\"\""; + assert to_str(string(@"foo")) == "\"foo\""; } #[test] @@ -649,12 +658,12 @@ mod tests { #[test] fn test_write_list() { - assert to_str(list([])) == "[]"; - assert to_str(list([boolean(true)])) == "[true]"; - assert to_str(list([ + assert to_str(list(@[])) == "[]"; + assert to_str(list(@[boolean(true)])) == "[true]"; + assert to_str(list(@[ boolean(false), null, - list([string("foo\nbar"), num(3.5f)]) + list(@[string(@"foo\nbar"), num(3.5f)]) ])) == "[false, null, [\"foo\\nbar\", 3.5]]"; } @@ -664,9 +673,9 @@ mod tests { assert to_str(mk_dict([("a", boolean(true))])) == "{ \"a\": true }"; assert to_str(mk_dict([ ("a", boolean(true)), - ("b", list([ - mk_dict([("c", string("\x0c\r"))]), - mk_dict([("d", string(""))]) + ("b", list(@[ + mk_dict([("c", string(@"\x0c\r"))]), + mk_dict([("d", string(@""))]) ])) ])) == "{ " + @@ -681,35 +690,35 @@ mod tests { #[test] fn test_trailing_characters() { assert from_str("nulla") == - err({line: 1u, col: 5u, msg: "trailing characters"}); + err({line: 1u, col: 5u, msg: @"trailing characters"}); assert from_str("truea") == - err({line: 1u, col: 5u, msg: "trailing characters"}); + err({line: 1u, col: 5u, msg: @"trailing characters"}); assert from_str("falsea") == - err({line: 1u, col: 6u, msg: "trailing characters"}); + err({line: 1u, col: 6u, msg: @"trailing characters"}); assert from_str("1a") == - err({line: 1u, col: 2u, msg: "trailing characters"}); + err({line: 1u, col: 2u, msg: @"trailing characters"}); assert from_str("[]a") == - err({line: 1u, col: 3u, msg: "trailing characters"}); + err({line: 1u, col: 3u, msg: @"trailing characters"}); assert from_str("{}a") == - err({line: 1u, col: 3u, msg: "trailing characters"}); + err({line: 1u, col: 3u, msg: @"trailing characters"}); } #[test] fn test_read_identifiers() { assert from_str("n") == - err({line: 1u, col: 2u, msg: "invalid syntax"}); + err({line: 1u, col: 2u, msg: @"invalid syntax"}); assert from_str("nul") == - err({line: 1u, col: 4u, msg: "invalid syntax"}); + err({line: 1u, col: 4u, msg: @"invalid syntax"}); assert from_str("t") == - err({line: 1u, col: 2u, msg: "invalid syntax"}); + err({line: 1u, col: 2u, msg: @"invalid syntax"}); assert from_str("truz") == - err({line: 1u, col: 4u, msg: "invalid syntax"}); + err({line: 1u, col: 4u, msg: @"invalid syntax"}); assert from_str("f") == - err({line: 1u, col: 2u, msg: "invalid syntax"}); + err({line: 1u, col: 2u, msg: @"invalid syntax"}); assert from_str("faz") == - err({line: 1u, col: 3u, msg: "invalid syntax"}); + err({line: 1u, col: 3u, msg: @"invalid syntax"}); assert from_str("null") == ok(null); assert from_str("true") == ok(boolean(true)); @@ -722,20 +731,20 @@ mod tests { #[test] fn test_read_num() { assert from_str("+") == - err({line: 1u, col: 1u, msg: "invalid syntax"}); + err({line: 1u, col: 1u, msg: @"invalid syntax"}); assert from_str(".") == - err({line: 1u, col: 1u, msg: "invalid syntax"}); + err({line: 1u, col: 1u, msg: @"invalid syntax"}); assert from_str("-") == - err({line: 1u, col: 2u, msg: "invalid number"}); + err({line: 1u, col: 2u, msg: @"invalid number"}); assert from_str("00") == - err({line: 1u, col: 2u, msg: "invalid number"}); + err({line: 1u, col: 2u, msg: @"invalid number"}); assert from_str("1.") == - err({line: 1u, col: 3u, msg: "invalid number"}); + err({line: 1u, col: 3u, msg: @"invalid number"}); assert from_str("1e") == - err({line: 1u, col: 3u, msg: "invalid number"}); + err({line: 1u, col: 3u, msg: @"invalid number"}); assert from_str("1e+") == - err({line: 1u, col: 4u, msg: "invalid number"}); + err({line: 1u, col: 4u, msg: @"invalid number"}); assert from_str("3") == ok(num(3f)); assert from_str("3.1") == ok(num(3.1f)); @@ -750,82 +759,86 @@ mod tests { #[test] fn test_read_str() { assert from_str("\"") == - err({line: 1u, col: 2u, msg: "EOF while parsing string"}); + err({line: 1u, col: 2u, msg: @"EOF while parsing string"}); assert from_str("\"lol") == - err({line: 1u, col: 5u, msg: "EOF while parsing string"}); + err({line: 1u, col: 5u, msg: @"EOF while parsing string"}); - assert from_str("\"\"") == ok(string("")); - assert from_str("\"foo\"") == ok(string("foo")); - assert from_str("\"\\\"\"") == ok(string("\"")); - assert from_str("\"\\b\"") == ok(string("\x08")); - assert from_str("\"\\n\"") == ok(string("\n")); - assert from_str("\"\\r\"") == ok(string("\r")); - assert from_str("\"\\t\"") == ok(string("\t")); - assert from_str(" \"foo\" ") == ok(string("foo")); + assert from_str("\"\"") == ok(string(@"")); + assert from_str("\"foo\"") == ok(string(@"foo")); + assert from_str("\"\\\"\"") == ok(string(@"\"")); + assert from_str("\"\\b\"") == ok(string(@"\x08")); + assert from_str("\"\\n\"") == ok(string(@"\n")); + assert from_str("\"\\r\"") == ok(string(@"\r")); + assert from_str("\"\\t\"") == ok(string(@"\t")); + assert from_str(" \"foo\" ") == ok(string(@"foo")); } #[test] fn test_read_list() { assert from_str("[") == - err({line: 1u, col: 2u, msg: "EOF while parsing value"}); + err({line: 1u, col: 2u, msg: @"EOF while parsing value"}); assert from_str("[1") == - err({line: 1u, col: 3u, msg: "EOF while parsing list"}); + err({line: 1u, col: 3u, msg: @"EOF while parsing list"}); assert from_str("[1,") == - err({line: 1u, col: 4u, msg: "EOF while parsing value"}); + err({line: 1u, col: 4u, msg: @"EOF while parsing value"}); assert from_str("[1,]") == - err({line: 1u, col: 4u, msg: "invalid syntax"}); + err({line: 1u, col: 4u, msg: @"invalid syntax"}); assert from_str("[6 7]") == - err({line: 1u, col: 4u, msg: "expecting ',' or ']'"}); - - assert from_str("[]") == ok(list([])); - assert from_str("[ ]") == ok(list([])); - assert from_str("[true]") == ok(list([boolean(true)])); - assert from_str("[ false ]") == ok(list([boolean(false)])); - assert from_str("[null]") == ok(list([null])); - assert from_str("[3, 1]") == ok(list([num(3f), num(1f)])); - assert from_str("\n[3, 2]\n") == ok(list([num(3f), num(2f)])); + err({line: 1u, col: 4u, msg: @"expecting ',' or ']'"}); + + assert from_str("[]") == ok(list(@[])); + assert from_str("[ ]") == ok(list(@[])); + assert from_str("[true]") == ok(list(@[boolean(true)])); + assert from_str("[ false ]") == ok(list(@[boolean(false)])); + assert from_str("[null]") == ok(list(@[null])); + assert from_str("[3, 1]") == ok(list(@[num(3f), num(1f)])); + assert from_str("\n[3, 2]\n") == ok(list(@[num(3f), num(2f)])); assert from_str("[2, [4, 1]]") == - ok(list([num(2f), list([num(4f), num(1f)])])); + ok(list(@[num(2f), list(@[num(4f), num(1f)])])); } #[test] fn test_read_dict() { assert from_str("{") == - err({line: 1u, col: 2u, msg: "EOF while parsing object"}); + err({line: 1u, col: 2u, msg: @"EOF while parsing object"}); assert from_str("{ ") == - err({line: 1u, col: 3u, msg: "EOF while parsing object"}); + err({line: 1u, col: 3u, msg: @"EOF while parsing object"}); assert from_str("{1") == - err({line: 1u, col: 2u, msg: "key must be a string"}); + err({line: 1u, col: 2u, msg: @"key must be a string"}); assert from_str("{ \"a\"") == - err({line: 1u, col: 6u, msg: "EOF while parsing object"}); + err({line: 1u, col: 6u, msg: @"EOF while parsing object"}); assert from_str("{\"a\"") == - err({line: 1u, col: 5u, msg: "EOF while parsing object"}); + err({line: 1u, col: 5u, msg: @"EOF while parsing object"}); assert from_str("{\"a\" ") == - err({line: 1u, col: 6u, msg: "EOF while parsing object"}); + err({line: 1u, col: 6u, msg: @"EOF while parsing object"}); assert from_str("{\"a\" 1") == - err({line: 1u, col: 6u, msg: "expecting ':'"}); + err({line: 1u, col: 6u, msg: @"expecting ':'"}); assert from_str("{\"a\":") == - err({line: 1u, col: 6u, msg: "EOF while parsing value"}); + err({line: 1u, col: 6u, msg: @"EOF while parsing value"}); assert from_str("{\"a\":1") == - err({line: 1u, col: 7u, msg: "EOF while parsing object"}); + err({line: 1u, col: 7u, msg: @"EOF while parsing object"}); assert from_str("{\"a\":1 1") == - err({line: 1u, col: 8u, msg: "expecting ',' or '}'"}); + err({line: 1u, col: 8u, msg: @"expecting ',' or '}'"}); assert from_str("{\"a\":1,") == - err({line: 1u, col: 8u, msg: "EOF while parsing object"}); + err({line: 1u, col: 8u, msg: @"EOF while parsing object"}); assert eq(result::get(from_str("{}")), mk_dict([])); assert eq(result::get(from_str("{\"a\": 3}")), mk_dict([("a", num(3.0f))])); assert eq(result::get(from_str("{ \"a\": null, \"b\" : true }")), - mk_dict([("a", null), ("b", boolean(true))])); + mk_dict([ + ("a", null), + ("b", boolean(true))])); assert eq(result::get(from_str("\n{ \"a\": null, \"b\" : true }\n")), - mk_dict([("a", null), ("b", boolean(true))])); + mk_dict([ + ("a", null), + ("b", boolean(true))])); assert eq(result::get(from_str("{\"a\" : 1.0 ,\"b\": [ true ]}")), mk_dict([ ("a", num(1.0)), - ("b", list([boolean(true)])) + ("b", list(@[boolean(true)])) ])); assert eq(result::get(from_str( "{" + @@ -838,9 +851,9 @@ mod tests { "}")), mk_dict([ ("a", num(1.0f)), - ("b", list([ + ("b", list(@[ boolean(true), - string("foo\nbar"), + string(@"foo\nbar"), mk_dict([ ("c", mk_dict([("d", null)])) ]) @@ -851,6 +864,6 @@ mod tests { #[test] fn test_multiline_errors() { assert from_str("{\n \"foo\":\n \"bar\"") == - err({line: 3u, col: 8u, msg: "EOF while parsing object"}); + err({line: 3u, col: 8u, msg: @"EOF while parsing object"}); } }