Last active
February 8, 2020 03:36
-
-
Save samwhaleIV/127d02ffdad9d30673470cfc4c3bd056 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
use std::fs::File; | |
use std::io::{self, prelude::*, BufReader}; | |
const TEST_WORD: &str = "pears"; //The word to check for anagrams of, should be changed to program arguments instead of a constant | |
const FILE_NAME: &str = "words_alpha.txt"; //A file containing new line delimited words list with alpha characters only | |
const ALPHABET: &str = "abcdefghijklmnopqrstuvwxyz"; //The English 26 character alphabet | |
const ALPHABET_SIZE: usize = ALPHABET.len(); | |
const LOOKUP_ORDER: [usize; ALPHABET_SIZE] = [ | |
//Allows for faster dictionary processing due to the letter frequency of the English language | |
2,19,11,9,0,15,16,7,4,22,21,10,13,5,3,18,24,8,6,1,12,20,14,23,17,25 | |
]; | |
const SUMMARY_OFFSET: usize = 'a' as usize; | |
type WordSummary = [u8; ALPHABET_SIZE]; | |
fn summarise_characters(word: &String) -> WordSummary { | |
let mut summary: WordSummary = [0u8; ALPHABET_SIZE]; | |
for index in word.char_indices() { | |
let character: char = index.1; | |
if character.is_ascii_lowercase() { | |
let mut code_point = character as usize; | |
code_point -= SUMMARY_OFFSET; | |
code_point = LOOKUP_ORDER[code_point]; | |
summary[code_point] += 1; | |
} | |
} | |
summary | |
} | |
fn summaries_match(a: &WordSummary, b: &WordSummary) -> bool { | |
//Relies on the speed of LOOKUP_ORDER | |
let mut matched = true; | |
for i in 0..ALPHABET_SIZE { | |
if a[i] != b[i] { | |
matched = false; | |
break; | |
} | |
} | |
matched | |
} | |
fn main() -> io::Result<()> { | |
let file = File::open(FILE_NAME)?; | |
let reader = BufReader::new(file); | |
let test_word_summary = { | |
let test_word = String::from(TEST_WORD); | |
let summary = summarise_characters(&test_word); | |
summary | |
}; | |
let matches = { | |
let mut matches: Vec<String> = Vec::new(); | |
for line in reader.lines() { | |
let word = line?; | |
let summary = summarise_characters(&word); | |
let is_match = summaries_match(&test_word_summary,&summary); | |
if is_match { | |
matches.push(word); | |
} | |
} | |
matches | |
}; | |
for word_match in matches { | |
println!("{}",word_match); | |
} | |
Ok(()) | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment