#![allow(clippy::unreadable_literal)]
use multi_trait::{EncodeInto, EncodeIntoArray, EncodeIntoBuffer, TryDecodeFrom};
fn main() {
println!("=== Multitrait Basic Example ===\n");
basic_encode_decode();
sequential_operations();
buffer_based_encoding();
stack_based_encoding();
varint_efficiency();
}
fn basic_encode_decode() {
println!("1. Basic Encoding and Decoding");
println!("--------------------------------");
let value = 42u8;
let encoded = value.encode_into();
println!("Original value: {value}");
println!("Encoded bytes: {encoded:?}");
println!("Encoded length: {} byte(s)", encoded.len());
let (decoded, remaining) = u8::try_decode_from(&encoded).unwrap();
println!("Decoded value: {decoded}");
println!("Remaining bytes: {remaining:?}");
assert_eq!(value, decoded);
assert!(remaining.is_empty());
println!();
}
fn sequential_operations() {
println!("2. Sequential Encoding and Decoding");
println!("------------------------------------");
let mut buffer = Vec::new();
buffer.extend_from_slice(&42u8.encode_into());
buffer.extend_from_slice(&1000u16.encode_into());
buffer.extend_from_slice(&100000u32.encode_into());
println!("Encoded 3 values:");
println!(" - 42 (u8)");
println!(" - 1000 (u16)");
println!(" - 100000 (u32)");
println!("Total buffer size: {} bytes", buffer.len());
println!("Buffer contents: {buffer:?}");
let (val1, rest) = u8::try_decode_from(&buffer).unwrap();
let (val2, rest) = u16::try_decode_from(rest).unwrap();
let (val3, rest) = u32::try_decode_from(rest).unwrap();
println!("\nDecoded values:");
println!(" - {val1} (u8)");
println!(" - {val2} (u16)");
println!(" - {val3} (u32)");
assert_eq!(val1, 42);
assert_eq!(val2, 1000);
assert_eq!(val3, 100000);
assert!(rest.is_empty());
println!();
}
fn buffer_based_encoding() {
println!("3. Buffer-Based Encoding (Zero Allocation)");
println!("-------------------------------------------");
let mut buffer = Vec::with_capacity(100);
println!("Initial buffer capacity: {}", buffer.capacity());
for i in 0u16..50 {
i.encode_into_buffer(&mut buffer);
}
println!("Encoded 50 values (0-49)");
println!("Buffer length: {} bytes", buffer.len());
println!(
"Buffer capacity: {} (no reallocation needed!)",
buffer.capacity()
);
let mut slice = &buffer[..];
let mut count = 0;
while !slice.is_empty() {
let (value, remaining) = u16::try_decode_from(slice).unwrap();
assert_eq!(value, count);
slice = remaining;
count += 1;
}
println!("Successfully decoded and verified {count} values");
println!();
}
fn stack_based_encoding() {
println!("4. Stack-Based Encoding (No Heap Allocation)");
println!("---------------------------------------------");
let value = 42u8;
let (array, len) = value.encode_into_array();
println!("Encoded {value} to stack array");
println!("Array contents (first {} bytes): {:?}", len, &array[..len]);
println!(
"Maximum array size for u8: {} bytes",
<u8 as EncodeIntoArray>::MAX_ENCODED_SIZE
);
println!("\nMaximum encoded sizes:");
println!(
" - bool: {} byte(s)",
<bool as EncodeIntoArray>::MAX_ENCODED_SIZE
);
println!(
" - u8: {} byte(s)",
<u8 as EncodeIntoArray>::MAX_ENCODED_SIZE
);
println!(
" - u16: {} byte(s)",
<u16 as EncodeIntoArray>::MAX_ENCODED_SIZE
);
println!(
" - u32: {} byte(s)",
<u32 as EncodeIntoArray>::MAX_ENCODED_SIZE
);
println!(
" - u64: {} byte(s)",
<u64 as EncodeIntoArray>::MAX_ENCODED_SIZE
);
println!(
" - u128: {} byte(s)",
<u128 as EncodeIntoArray>::MAX_ENCODED_SIZE
);
println!(
" - usize: {} byte(s)",
<usize as EncodeIntoArray>::MAX_ENCODED_SIZE
);
println!();
}
fn varint_efficiency() {
println!("5. Varint Encoding Efficiency");
println!("------------------------------");
let test_values = vec![0u32, 127, 128, 255, 16383, 16384, u32::MAX];
println!("Value encoding efficiency:");
println!("{:>12} | {:>6} | Encoded (hex)", "Value", "Bytes");
println!("{0:-<12}-+-{0:-<6}-+-{0:-<30}", "");
for value in test_values {
let encoded = value.encode_into();
let hex_str: String = encoded
.iter()
.map(|b| format!("{b:02X}"))
.collect::<Vec<_>>()
.join(" ");
println!("{:>12} | {:>6} | {}", value, encoded.len(), hex_str);
}
println!("\nKey insight: Smaller values take fewer bytes!");
println!(" - Values 0-127: 1 byte");
println!(" - Values 128-16,383: 2 bytes");
println!(" - Values 16,384-2,097,151: 3 bytes");
println!(" - etc.");
println!();
}