#string #set #compile-time #parser #enums

static-atom

在编译时已知字符串集合中的快速解析

3 个版本

0.1.2 2018 年 12 月 9 日
0.1.1 2018 年 11 月 12 日
0.1.0 2018 年 11 月 9 日

375#compile-time

MIT 许可证

11KB
310

static-atom

将一组字符串表示为 Rust 的 enum。高效地将传入的字符串转换为相应的 enum 情况。

基准测试

基准测试 将以下任意字符串解码为 Option<usize>

  • "BTC-EUR" 产生 Some(1)
  • "BTC-USDC" 产生 Some(2)
  • "ETH-EUR" 产生 Some(3)
  • "ETH-BTC" 产生 Some(4)
  • 其他任何内容都将产生 None

方法有

  • match_keyword - 标准的 Rust match 关键字。检查切片的长度,然后检查切片的指针与字符串字面量进行比较,然后调用 memcmp
  • trie_generated_small - 每次消耗一个或多个字节来缩小字符串剩余部分的合法后缀。如果字符串剩余部分的选项足够不同,则消耗 u16u32u64
  • trie_generated_big - 与 trie_generated_small 相似,但生成的代码测试的是 24 个字符串而不是 4 个。

有效 1

Valid 1

有效 2

Valid 2

有效 3

Valid 3

有效 4

Valid 4

无效为空

Invalid empty

无效的首字符

Invalid first char

无效的尾字符

Invalid last char

无效过长

Invalid too long

无效过短

Invalid too short

示例生成的代码

#[derive(Copy, Clone, PartialEq, Eq, PartialOrd, Ord)]
pub enum Small {
    _0, // "BTC-EUR"
    _1, // "BTC-USDC"
    _2, // "ETH-EUR"
    _3, // "ETH-BTC"
}

#[macro_export]
macro_rules! small {
("BTC-EUR") => { $crate::Small::_0 };
("BTC-USDC") => { $crate::Small::_1 };
("ETH-EUR") => { $crate::Small::_2 };
("ETH-BTC") => { $crate::Small::_3 };
}

impl FromStr for Small {
    type Err = ();

    #[allow(unused_variables)]
    fn from_str(s: &str) -> Result<Self, ()> {
        let s = s.as_bytes();
        match s.len() {
            7 => {
                if let Some(s) = s.expect(b"BTC-EUR") {
                    Ok(small!("BTC-EUR"))
                } else if let Some(s) = s.expect(b"ETH-") {
                    if let Some(s) = s.expect(b"BTC") {
                        Ok(small!("ETH-BTC"))
                    } else if let Some(s) = s.expect(b"EUR") {
                        Ok(small!("ETH-EUR"))
                    } else { Err(()) }
                } else { Err(()) }
            }
            8 => {
                if let Some(s) = s.expect(b"BTC-USDC") {
                    Ok(small!("BTC-USDC"))
                } else { Err(()) }
            }
            _ => Err(())
        }
    }
}

impl Small {
    pub fn as_str(&self) -> &'static str {
        match self {
            small!("BTC-EUR") => "BTC-EUR",
            small!("BTC-USDC") => "BTC-USDC",
            small!("ETH-EUR") => "ETH-EUR",
            small!("ETH-BTC") => "ETH-BTC",
        }
    }
}

impl From<Small> for usize {
    fn from(token: Small) -> Self {
        match token {
            small!("BTC-EUR") => 0,
            small!("BTC-USDC") => 1,
            small!("ETH-EUR") => 2,
            small!("ETH-BTC") => 3,
        }
    }
}

impl fmt::Debug for Small {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "small!({})", self.as_str())
    }
}

impl fmt::Display for Small {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        f.write_str(self.as_str())
    }
}

依赖项

~15KB