src/chop_basename.rs in faster_path-0.3.7 vs src/chop_basename.rs in faster_path-0.3.8
- old
+ new
@@ -1,23 +1,16 @@
-use std::path::MAIN_SEPARATOR;
+use path_parsing::{find_last_non_sep_pos, find_last_sep_pos};
use std::str;
pub fn chop_basename<'a>(input: &'a str) -> Option<(&'a str, &'a str)> {
- if input.is_empty() {
+ let bytes = input.as_bytes();
+ let len = find_last_non_sep_pos(&bytes)? + 1;
+ let base_start = find_last_sep_pos(&bytes[..len]).map_or(0, |pos| pos + 1);
+ if base_start == len {
return None;
}
-
- let input = input.trim_right_matches(MAIN_SEPARATOR);
- let end = input.rsplitn(2, MAIN_SEPARATOR).nth(0).unwrap().len();
- let base = &input[input.len()-end..input.len()];
- let directory = &input[0..input.len()-base.len()];
-
- if directory.is_empty() && (base.is_empty() || base.chars().next().unwrap() == MAIN_SEPARATOR) {
- return None
- };
-
- Some((directory, base))
+ Some((&input[0..base_start], &input[base_start..len]))
}
#[test]
fn it_chops_the_basename_and_dirname() {
assert_eq!(chop_basename(""), None );
@@ -25,7 +18,13 @@
assert_eq!(chop_basename("."), Some(("", ".")) );
assert_eq!(chop_basename("asdf/asdf"), Some(("asdf/", "asdf")) );
assert_eq!(chop_basename("asdf.txt"), Some(("", "asdf.txt")) );
assert_eq!(chop_basename("asdf/"), Some(("", "asdf")) );
assert_eq!(chop_basename("/asdf/"), Some(("/", "asdf")) );
+ assert_eq!(chop_basename("a///b"), Some(("a///", "b")) );
+ assert_eq!(chop_basename("a///b//"), Some(("a///", "b")) );
+ assert_eq!(chop_basename("/a///b//"), Some(("/a///", "b")) );
+ assert_eq!(chop_basename("/a///b//"), Some(("/a///", "b")) );
+
+ assert_eq!(chop_basename("./../..///.../..//"), Some(("./../..///.../", "..")));
}