Самый быстрый способ проверить, существует ли данное слово в фиксированном списке слов - PullRequest
0 голосов
/ 15 октября 2018

Это может не относиться к Rust, хотя это язык, на котором я сейчас сосредоточен.

Я пишу функцию для синтаксического анализа языка (MySQL) в токенах и вывода их в отформатированном виде.и часть этого включает в себя поиск текущего рабочего токена, чтобы определить, является ли оно именем, функцией или именем столбца / таблицы.

В настоящее время я использую оператор сопоставления, например

* 1006.*

Фактический список намного, намного длиннее.

Это лучший способ сделать это?Я пытался использовать HashMap также с .contains_key(), но это было заметно медленнее


Моя HashMap реализация выглядит так:

use std::collections::HashMap;

lazy_static! {
    static ref words: HashMap<&'static str, u8> = hashmap!{
        "accessible" => 0,
        "account" => 0,
        "action" => 0,
        "active" => 0,
        "add" => 0,
        // ...
        "year" => 0,
        "year_month" => 0,
        "zerofill" => 0,
    };
}

pub fn is_word(word: &str) -> bool {
    words.contains_key(word)
}

1 Ответ

0 голосов
/ 15 октября 2018

Поскольку ваш список исправлен во время компиляции, используйте совершенный хеш , например, предоставленный phf crate :

build.rs

extern crate phf_codegen;

use std::env;
use std::fs::File;
use std::io::{BufWriter, Write};
use std::path::Path;

fn main() {
    let path = Path::new(&env::var("OUT_DIR").unwrap()).join("codegen.rs");
    let mut file = BufWriter::new(File::create(&path).unwrap());

    write!(&mut file, "static KEYWORDS: phf::Set<&'static str> = ").unwrap();
    phf_codegen::Set::new()
        .entry("accessible")
        .entry("account")
        .entry("action")
        .entry("active")
        .entry("add")
        // ...
        .entry("year")
        .entry("year_month")
        .entry("zerofill")
        .build(&mut file)
        .unwrap();
    write!(&mut file, ";\n").unwrap();
}

src / main.rs

extern crate phf;

include!(concat!(env!("OUT_DIR"), "/codegen.rs"));

pub fn is_word(word: &str) -> bool {
    KEYWORDS.contains(word)
}

Согласно предоставленному вами коду тестирования, это по крайней мере так же быстро.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...