flexstr 0.9.2

A flexible, simple to use, immutable, clone-efficient `String` replacement for Rust
Documentation
A flexible, simple to use, immutable, clone-efficient [String] replacement for Rust ## String Creation from Literals String constants are easily wrapped into the unified string type. String contents are inlined when possible otherwise allocated on the heap. ``` use flexstr::{local_str, LocalStr, ToLocalStr}; // Use `local_str` macro to wrap literals as compile-time constants const STATIC_STR: LocalStr = local_str!("This will not allocate or copy"); assert!(STATIC_STR.is_static()); // Strings up to 22 bytes (on 64-bit) will be inlined automatically // (demo only, use macro or `from_static` for literals as above) let inline_str = "inlined".to_local_str(); assert!(inline_str.is_inline()); // When a string is too long to be wrapped/inlined, it will heap allocate // (demo only, use macro or `from_static` for literals as above) let rc_str = "This is too long to be inlined".to_local_str(); assert!(rc_str.is_heap()); ``` ## String Creation and Manipulation The stdlib [format] macro equivalent is used to create brand new strings. String operations like changing case and concatenation are efficiently supported (inlining when possible). ``` use flexstr::{local_fmt, LocalStr, ToCase}; // You can efficiently create a new `LocalStr` (without creating a `String`) // This is equivalent to the stdlib `format!` macro let inline_str = local_fmt!("in{}", "lined"); assert!(inline_str.is_inline()); // We can upper/lowercase strings without converting to a `String` first // This doesn't heap allocate since inlined let inline_str2: LocalStr = "INLINED".to_ascii_lower(); assert!(inline_str2.is_inline()); assert_eq!(inline_str, inline_str2); // Concatenation doesn't even copy if we can fit it in the inline string let inline_str3 = inline_str2 + "!!!"; assert!(inline_str3.is_inline()); assert_eq!(inline_str3, "inlined!!!"); ``` ## Efficient, Universal String Type Clones never copy or allocate and are very fast. Regardless of underlying storage type, all strings work together and resulting strings automatically choose the best storage. ``` use flexstr::{local_str, LocalStr, ToLocalStr}; // Clone is cheap, and never allocates // (at most it is a ref count increment for heap allocated strings) let rc_str = "This is too long to be inlined".to_local_str().clone(); assert!(rc_str.is_heap()); // Regardless of storage type, these all operate seamlessly together // and choose storage as required const STATIC_STR: LocalStr = local_str!("This will eventually end up on the "); let inline_str = "heap".to_local_str(); let heap_str2 = STATIC_STR + &inline_str; assert!(heap_str2.is_heap()); assert_eq!(heap_str2, "This will eventually end up on the heap"); ```