Skip to content
Browse files

Work in progress.

  • Loading branch information...
1 parent 959c3d6 commit 4876bdd3c81e15b887351d0595a0368fa5968d41 @amcnamara committed Feb 22, 2012
Showing with 47 additions and 27 deletions.
  1. +1 −0 src/Hangman/.#core.clj
  2. +34 −2 src/Hangman/core.clj
  3. +12 −25 src/Hangman/strategy.clj
View
1 src/Hangman/.#core.clj
View
36 src/Hangman/core.clj
@@ -1,5 +1,37 @@
(ns hangman.core
- (:require [hangman.initialize :as init]))
+ (:require [hangman.strategy :as strategy]
+ [clojure.string :as string])
+ (:import [com.factual.hangman HangmanGame HangmanGame$Status]))
+
+(def max-guesses 8)
+(def weight 1)
(defn -main [& args]
- (time (spit "resources/decision-tree.txt" (prn-str init/decision-tree))))
+ (if-let [secret-word-list (try (string/split (slurp (first args)) #"\s+") (catch Exception _ (if (first args) args)))]
+ (map #(let [game (HangmanGame. % max-guesses)]
+ (loop [guessed-chars [] guessed-words [] mask (.getGuessedSoFar game)]
+ (when (= HangmanGame$Status/KEEP_GUESSING (.gameStatus game))
+ (let [[answer & _ :as words] (remove (set guessed-words) (strategy/get-words mask guessed-chars))
+ branches (map
+ (fn [test]
+ [test (get-masks test mask guesses)])
+ (remove (set guessed-chars) (map char (range 65 91))))
+ total (count words)
+ dmax (max (map (fn [[_ masks]] (count masks)) branches))
+ [pick _] (reduce
+ (fn [[prev prev-n] [test masks]]
+ (let [score ()]
+ (if (or (nil? prev) (> score prev-n))
+ [test score])))
+ [nil nil]
+ branches)]
+ (if (or (nil? pick) (>= 2 (count words)))
+ (do
+ (.. game (guessWord answer))
+ (recur guesses (conj guessed-words answer) mask))
+ (do
+ (.. game (guessLetter pick))
+ (recur (conj guesses pick) guessed-words (.getGuessedSoFar game))))))))
+ (println game))
+ secret-word-list)
+ (println "Usage: lein run <words...|word-filename>, where the word file is whitespace delimited and there exists a dictionary file under ./resources/dict.txt")))
View
37 src/Hangman/strategy.clj
@@ -1,21 +1,19 @@
-(ns hangman.initialize
+(ns hangman.strategy
(:require [clojure.string :as string]))
;; A collection of all of the valid words in the supplied dictionary
-(def dictionary (distinct (map string/upper-case (string/split (slurp "/Users/amac/Workspace/dev/Hangman/resources/dict.txt") #"\n"))))
-
-(def chars (map char (range 65 91)))
+(def dictionary (distinct (map string/upper-case (string/split (slurp (str (System/getProperty "user.dir") "resources/dict.txt")) #"\n"))))
(def ^:dynamic branch-words [])
;; Takes a word mask and returns a regex (for finding the subset of valid words for the given mask)
(defn- get-mask-regex
([mask]
- (re-pattern (string/replace mask "-" "[A-Z]")))
+ (get-mask-regex mask []))
([mask guesses]
- (re-pattern (string/replace mask "-" (str "[" (apply str (remove (set guesses) chars)) "]")))))
+ (re-pattern (string/replace mask "-" (if (empty? guesses) "[A-Z]" (str "[^" (apply str guesses) "]"))))))
-;; Builds a word mask eithor of a given length or a collection of guessed chars against a given word
+;; Builds a word mask either of a given length or a collection of guessed chars against a given word
(defn- get-mask
([length]
(apply str (repeat length "-")))
@@ -32,9 +30,12 @@
(filter #(re-find (get-mask-regex mask guesses) %) words)))
;; Grabs all valid words in the dictionary for a given mask
-(defn get-words [mask]
- (filter-mask-words mask [] (get (group-by count dictionary) (count mask))))
-
+(defn get-words
+ ([mask]
+ (get-words mask []))
+ ([mask guesses]
+ (filter-mask-words mask guesses (get (group-by count dictionary) (count mask)))))
+
(defn- guess-branch [guesses rem-chars mask]
(let [[pick _] (reduce (fn [[prev prev-n] test]
(let [test-n (count (re-seq (re-pattern (str test)) (apply str (filter-mask-words mask guesses branch-words))))]
@@ -48,19 +49,5 @@
(map (fn [submask]
(binding [branch-words (filter-mask-words mask guesses branch-words)]
(guess-branch (conj guesses pick) (remove #{pick} rem-chars) submask)))
- ;;#(guess-branch (conj guesses pick) (remove #{pick} rem-chars) %)
- ;; (if (= mask submask)
- ;; (binding [branch-words (filter #(not (contains? (set %) pick)) branch-words)]
- ;; (guess-branch (conj guesses pick) (remove #{pick} rem-chars) submask))
- ;; (guess-branch (conj guesses pick) (remove #{pick} rem-chars) submask))
(distinct (map #(get-mask pick mask %) (filter-mask-words mask guesses branch-words)))))
- (first (filter-mask-words mask guesses branch-words)))]}))
-
-;; Builds a decision tree for a given collection of words (which are of equal length)
-(defn- guess-tree [words]
- (println (count (first words)) "," (count words))
- (binding [branch-words words]
- (spit (str "resources/decision-" (count (first words))) (guess-branch [] (distinct (reduce str words)) (get-mask (count (first words)))))))
-
-;; A map of decision trees keyed to masks, contains all paths to all words
-(def decision-tree (reduce into {} (map guess-tree (vals (group-by count dictionary)))))
+ (first (filter-mask-words mask guesses branch-words)))]}))

0 comments on commit 4876bdd

Please sign in to comment.
Something went wrong with that request. Please try again.