色々見ました記事基本的なLinuxコマンド(grepとregex)がWordleパズルを解決する方法を説明します。ゲームに初めてアクセスする場合は、この質問の最後にあるメモを確認してください。私はこの目的でawkを使用することにしました。最初の試みは次のとおりです。
awk 'length($0)==5' /usr/share/dict/words | awk '!/\-|\x27|[A-Z]/' | awk '!/[isbou]/' | awk '/a/&&/l/&&/e/&&/e/&&/t/' | awk '/...a/' | cat -n
最初の2つのawkは、標準のUbuntuインストールの辞書から5文字の単語リスト(大文字、ハイフン、アポストロフィを除く)を生成します。
awk '/a/&&/l/&&/e/&&/t/'
(黄色の文字の場合)文字のある単語をフィルタリングします。言葉の中にありますが、書かれた場所にはありません。この例では、文字a、l、e、t
awk '!/[isbou]/'
(グレー文字の場合)この例では、i、s、b、o、u文字を含む単語をフィルタリングします。
awk '/...a/'
(緑色の文字の場合)は、文字があり、正しい位置にあることを意味します。
私は簡単にコードを維持するために5文字の単語リストを辞書として使用することにしました。いくつかの方法でこれらのリストを準備できます。たとえば、
awk 'length($0)==5' /usr/share/dict/words | awk '!/\-|\x27|[A-Z]/' > fives.txt
または
curl -s 'https://random-word-api.herokuapp.com/word?number=100000' | awk -v RS=',' '{gsub(/[]["]+/,"")}1' | awk 'length($i)==5' > fives.txt
このファイル( Fives.txt )をホームディレクトリに配置すると、コマンドが短くなります。
cat ~/fives.txt | awk '!/[isbou]/' | awk '/a/&&/l/&&/e/&&/e/&&/t/' | awk '/...a/' | cat -n
これは素晴らしい作品です。しかし、これを短縮できますか?次の推測コマンドを編集するときに黄色の文字チェックをよりエレガントにし、エラーが発生する可能性を減らすにはどうすればよいですか?
注:ルールは非常に簡単です。 6番(通常5番)の中に隠された単語を推測する必要があります。まず、最初の行に任意の単語を入力してください。文字が正しく推測され、正しい位置にある場合は緑色で強調表示され、文字が単語にあるが間違った位置にある場合は黄色で強調表示され、文字が単語にない場合はそのまま残ります。グレー。 6回の試みの終わりに隠された単語を打つことはできますか?
答え1
すべてのAWKフィルタとマージ機能を組み合わせることで、cat
この時間を短縮できます。
awk '!/[isbou]/ && /a/&&/l/&&/e/&&/t/ && /^...a.$/ { printf("%6d %s\n", ++i, $0) }' ~/fives.txt
具体的には、5つの位置を確認するために緑色のフィルタを修正しました。
AWK部分をより単純化する代わりに、3つのパラメータ(灰色の文字リスト、黄色の文字リスト、正しい場所にある緑色の文字)を持つシェルスクリプトを使用します。
#!/bin/bash
awkcmd=""
if [[ ${#1} -gt 0 ]]; then
awkcmd="${awkcmd}!/[$1]/ &&"
fi
if [[ ${#2} -gt 0 ]]; then
for (( i=0; i < ${#2}; i++ )); do
awkcmd="${awkcmd} /${2:$i:1}/ &&"
done
fi
if [[ ${#3} -gt 0 ]]; then
awkcmd="${awkcmd} /$3/"
else
awkcmd="${awkcmd} 1"
fi
awkcmd="${awkcmd} { printf(\"%6d %s\n\", ++i, \$0) }"
awk "$awkcmd" ~/fives.txt
より一般的な単語のリストを表示するには、awkcmd="/^[a-z]{5}$/ &&"
3行目に使用してください。
答え2
非常に粗雑なスクリプト(スタブに似ています)は、次のように起動できます。
#!/bin/bash
conditions='/^[a-z]{5}$/'
while getopts "c:i:e:" opt; do case "${opt}" in
c) conditions+=" && /^${OPTARG,,}/" ;;
i) conditions+=$(sed 's|.| \&\& /&/|g' <<<"${OPTARG,,}") ;;
e) conditions+=" && !/[${OPTARG,,}]/" ;;
esac; done
shift $((OPTIND-1))
awk "${conditions} { print toupper(\$0) }" /usr/share/dict/words
呼び出しの./wordle.sh -c "...a" -i "alet" -e "isbou"
結果は次のとおりです。
CLEAT
FETAL
METAL
PETAL
PLEAT
この例で生成されたawkは次のとおりです。
awk '/^[a-z]{5}$/ && /^...a/ && /a/ && /l/ && /e/ && /t/ && !/[isbou]/ { print toupper($0) }' /usr/share/dict/words
...スクリプトへの不正な呼び出しは次のとおりです。./wordle.sh -c...a -ialet -eisbou
もちろん、{ print toupper(\$0) }
スクリプト部分は完全に装飾的なので、削除することができます。 WordleがGUIで大文字のみを使用することを選択したため、追加されました。 :)
答え3
すでに5文字の単語しかないので、何!/[isbou]/
も除外する必要はありません。二重。両方を含むケースを見つけるには必要です。したがって、これらすべてを組み合わせると、おそらく次のようになります。/a/&&/l/&&/e/&&/e/&&/t/
/e/ && /e/
e
e
/e.*e/
awk '/...a./ && /l/ &&/e.*e/ && /t/{print ++k,$0}' ~/fives.txt
答え4
ただこのように書きたい場合:
awk 'length($0)==5' /usr/share/dict/words | awk '!/[A-Z]/' | awk '/[:alpha:]/' | awk '!/[isbou]/' | awk '/a/&&/l/&&/e/&&/e/&&/t/' | awk '/...a/' | cat -n
もっと簡潔に言えば、
awk '!/[A-Zisbou]/ && /l/&&/e/&&/t/ && /^...a.$/ {print ++n, $0}' /usr/share/dict/words
ただし、小文字以外のアルファベット文字を含む「単語」を除外するには、次のようにします。
awk '/^[[:lower:]]+$/ && /l/&&/e/&&/t/ && /^...a.$/ {print ++n, $0}' /usr/share/dict/words
または必要に応じて:
awk '/l/&&/e/&&/t/ && /^[[:lower:]]{3}a[[:lower:]]$/ {print ++n, $0}' /usr/share/dict/words