use smallvec::{Array, SmallVec};
pub const BASE62ALPH: &[u8; 62] = b"0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ";
pub fn base62uenc<A: Array<Item=u8>> (mut ui: u64, sv: &mut SmallVec<A>) -> Result<(), String> {
let start = sv.len();
loop {
sv.push (BASE62ALPH[(ui % 62) as usize]);
ui /= 62; if ui == 0 {break}}
let end = sv.len();
sv[start..end].reverse();
Ok(())}
pub fn base62udec (bv: &[u8]) -> Result<u64, String> {
let mut uv = 0;
for &ch in bv.iter() {
let v = if ch >= b'0' && ch <= b'9' {
ch - b'0'
} else if ch >= b'A' && ch <= b'Z' {
ch - b'A' + 36
} else if ch >= b'a' && ch <= b'z' {
ch - b'a' + 10
} else {
return ERR! ("!base62: {}", ch)};
uv = uv * 62 + v as u64}
Ok (uv)}
#[cfg(all(test, feature = "nightly"))] mod test {
extern crate test;
use super::*;
#[bench] fn base62uencᵇ (bm: &mut test::Bencher) {
let mut buf: SmallVec<[u8; 32]> = SmallVec::new();
bm.iter (|| {
buf.clear();
base62uenc (451488, &mut buf) .unwrap()});
assert! (&buf[..] == b"1Ts4");
assert_eq! (base62udec (b"1Ts4"), Ok (451488))}}