Initial commit — Wordle/letter word solver and scorer
This commit is contained in:
@@ -0,0 +1,146 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using C5;
|
||||
|
||||
namespace Core
|
||||
{
|
||||
public class DictionarySearcher
|
||||
{
|
||||
static HashBag<char> GetLettersBag(string letters)
|
||||
{
|
||||
var hashBag = new HashBag<char>();
|
||||
hashBag.AddAll(letters.Canonicalize().ToCharArray());
|
||||
return hashBag;
|
||||
}
|
||||
|
||||
readonly struct DictWord
|
||||
{
|
||||
public readonly string Word;
|
||||
public readonly HashBag<char> CharBag;
|
||||
|
||||
public DictWord(string word) : this()
|
||||
{
|
||||
Word = word;
|
||||
CharBag = GetLettersBag(word);
|
||||
}
|
||||
|
||||
public static implicit operator DictWord(string s) => new DictWord(s);
|
||||
public static implicit operator string(DictWord dw) => dw.Word;
|
||||
|
||||
public char[] ToCharArray() => Word.ToCharArray();
|
||||
public bool Contains(char c) => Word.Contains(c);
|
||||
|
||||
public int Length => Word.Length;
|
||||
public bool StartsWith(string s) => Word.StartsWith(s);
|
||||
|
||||
public string Substring(int startIndex) => Word.Substring(startIndex);
|
||||
}
|
||||
|
||||
private class DictWordComprer : IComparer<DictWord>
|
||||
{
|
||||
private readonly IComparer<string> _comparer;
|
||||
public DictWordComprer(IComparer<string> comparer)
|
||||
{
|
||||
_comparer = comparer;
|
||||
}
|
||||
public int Compare(DictWord x, DictWord y)
|
||||
{
|
||||
return _comparer.Compare(x, y);
|
||||
}
|
||||
}
|
||||
|
||||
private readonly List<DictWord> _dictionary;
|
||||
|
||||
public DictionarySearcher(int? characterCount = null)
|
||||
: this(@"TWL06.txt", characterCount)
|
||||
{
|
||||
}
|
||||
|
||||
public DictionarySearcher(string filename, int? characterCount = null)
|
||||
: this(filename.GetFileLines(), characterCount)
|
||||
{
|
||||
}
|
||||
|
||||
public DictionarySearcher(IEnumerable<string> words, int? characterCount = null)
|
||||
{
|
||||
_dictionary = new List<DictWord>();
|
||||
foreach (var word in words)
|
||||
{
|
||||
if (characterCount != null && word.Length != characterCount)
|
||||
continue;
|
||||
var w = word.Canonicalize();
|
||||
_dictionary.Add(w);
|
||||
}
|
||||
}
|
||||
|
||||
public System.Collections.Generic.IList<string> GetWords()
|
||||
{
|
||||
return _dictionary.Select(d => d.Word).ToList();
|
||||
}
|
||||
|
||||
public void SortDictionary(IComparer<string> comparer)
|
||||
{
|
||||
_dictionary.Sort(new DictWordComprer(comparer));
|
||||
}
|
||||
|
||||
public IEnumerable<string> FindWords(string letters)
|
||||
{
|
||||
var hashBag = new HashBag<char>();
|
||||
hashBag.AddAll(letters.Canonicalize().ToCharArray());
|
||||
return from w in _dictionary
|
||||
where hashBag.ContainsAll(w.ToCharArray())
|
||||
select w.Word;
|
||||
}
|
||||
|
||||
public IEnumerable<string> FindWords(string includeLetters, string excludeLetters)
|
||||
{
|
||||
var excludeBag = GetLettersBag(excludeLetters);
|
||||
|
||||
return from w in _dictionary
|
||||
where w.CharBag.ContainsAll(includeLetters.Canonicalize())
|
||||
&& excludeBag.All(c => !w.Contains(c))
|
||||
select w.Word;
|
||||
}
|
||||
|
||||
public IEnumerable<string> FindWords(string includeLetters, string excludeLetters, int? len)
|
||||
{
|
||||
return
|
||||
from w in FindWords(includeLetters, excludeLetters)
|
||||
where !len.HasValue || w.Length == len.Value
|
||||
select w;
|
||||
}
|
||||
|
||||
public IEnumerable<Tuple<string, string>> MatchingWords(string firstSelector, string secondSelector)
|
||||
{
|
||||
var firstSet = _dictionary.Where(w => w.StartsWith(firstSelector.Canonicalize())).GroupBy(w => w.Length)
|
||||
.ToList();
|
||||
var secondSet = _dictionary.Where(w => w.StartsWith(secondSelector.Canonicalize())).GroupBy(w => w.Length)
|
||||
.ToList();
|
||||
|
||||
return from len in firstSet.Select(g => g.Key)
|
||||
from w1 in firstSet.Where(g => g.Key == len)
|
||||
from w2 in secondSet.Where(g => g.Key == len)
|
||||
from ww1 in w1
|
||||
from ww2 in w2
|
||||
where ww1.Substring(1).Equals(ww2.Substring(1))
|
||||
select Tuple.Create(ww1.Word, ww2.Word);
|
||||
}
|
||||
/*public Dictionary<char, int>[] GetLetterPositionFreq(int wordLen)
|
||||
{
|
||||
var ws = _dictionary.Where(w => w.Length == wordLen).ToList();
|
||||
|
||||
var freqList = new Dictionary<char, int>[wordLen];
|
||||
for (var i = 0; i < wordLen; i++)
|
||||
{
|
||||
var letters = Enumerable.Range(0, 26).Select(r => Convert.ToChar('A' + r));
|
||||
freqList[i] =
|
||||
letters.ToDictionary(c => c,
|
||||
c => ws.Count(w => w.Word[i] == c)
|
||||
);
|
||||
}
|
||||
|
||||
return freqList;
|
||||
}*/
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user