5个版本
0.2.0 | 2023年3月2日 |
---|---|
0.1.3 | 2023年2月28日 |
0.1.2 | 2023年2月24日 |
0.1.1 | 2023年2月24日 |
0.1.0 | 2023年2月24日 |
#267 in 值格式化
12KB
109 行
str-cat
此crate提供了宏,可以高效地连接字符串,无额外副作用。
lib.rs
:
此crate提供了宏,可以高效地连接字符串,无额外副作用。
使用方法
基本用法
use str_cat::str_cat;
let s = str_cat!("Hello", " ", "World", "!");
assert_eq!(s, "Hello World!");
大致相当于
let mut s = String::with_capacity("Hello".len() + " ".len() + "World".len() + "!".len());
s.push_str("Hello");
s.push_str(" ");
s.push_str("World");
s.push_str("!");
无额外副作用
该宏运行无额外副作用,这意味着所有相关的表达式只计算一次。
let mut get_world_calls = 0;
let mut get_world = || {
get_world_calls += 1;
"World"
};
let s = str_cat!("Hello", " ", get_world(), "!");
assert_eq!(s, "Hello World!");
assert_eq!(get_world_calls, 1);
大致相当于
let world = get_world(); // evaluate the expression and store it for later use
let mut s = String::with_capacity("Hello".len() + " ".len() + world.len() + "!".len());
s.push_str("Hello");
s.push_str(" ");
s.push_str(&world);
s.push_str("!");
追加到现有字符串
let mut s = "Hello".to_owned();
str_cat!(&mut s; " ", "World!");
assert_eq!(s, "Hello World!");
重用现有分配
let mut s = "Hello World!".to_owned();
let ptr = s.as_ptr();
let cap = s.capacity();
s.clear();
str_cat!(&mut s; "Hello");
assert_eq!(s, "Hello");
// Did not grow
assert_eq!(s.as_ptr(), ptr);
assert_eq!(s.capacity(), cap);
自定义最小容量
let s = str_cat!(String::with_capacity(16); "foo", "bar");
assert_eq!(s, "foobar");
assert!(s.capacity() >= 16);
参数类型
当可以避免显式调用 .to_string()
时,使用 format!
应该更简单、更高效。当需要将任何可以解引用到 str
的表达式连接起来时,它都适用。
// Just an example. It's better to use `format!` in this case.
let s = str_cat!(
"Hello".to_owned(),
Box::new(" "),
['W', 'o', 'r', 'l', 'd'].iter().collect::<String>(),
'!'.to_string(),
123456.to_string(),
);
assert_eq!(s, "Hello World!123456");
隐式借用
就像 format!
和 println!
一样,str_cat
会自动为您借用参数,因此您不需要自己输入那个 &
。
let world = "World!".to_owned();
let s = str_cat!("Hello ", world); // no need for `&`
assert_eq!(s, "Hello World!");
assert_eq!(world, "World!"); // not moved, still valid
变体
还有针对 PathBuf
、OsString
和 Vec
的变体。
use str_cat::os_str_cat;
// Works for anything that implements AsRef<OsStr>.
let s = os_str_cat!(
OsStr::new("Hello"),
OsStr::new(" ").to_owned(),
Path::new("World"),
"!",
);
assert_eq!(s, OsStr::new("Hello World!"));