Created
March 16, 2018 03:03
-
-
Save jgomo3/305afa6baddf893f0c6cea3d3fedffc5 to your computer and use it in GitHub Desktop.
Chapter 3 excercise for the "Clojure for the Brave and True" -- For hitting hobbits
This file contains 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
(ns clojure-noob.smash-hobbits | |
(:require [clojure.string :as str])) | |
(def asym-hobbit-body-parts [{:name "head" :size 3} | |
{:name "left-eye" :size 1} | |
{:name "left-ear" :size 1} | |
{:name "mouth" :size 1} | |
{:name "nose" :size 1} | |
{:name "neck" :size 2} | |
{:name "left-shoulder" :size 3} | |
{:name "left-upper-arm" :size 3} | |
{:name "chest" :size 10} | |
{:name "back" :size 10} | |
{:name "left-forearm" :size 3} | |
{:name "abdomen" :size 6} | |
{:name "left-kidney" :size 1} | |
{:name "left-hand" :size 2} | |
{:name "left-knee" :size 2} | |
{:name "left-thigh" :size 4} | |
{:name "left-lower-leg" :size 3} | |
{:name "left-achilles" :size 1} | |
{:name "left-foot" :size 2}]) | |
(defn set-map [f coll] (set (map f (set coll)))) | |
(defn matching-parts-by | |
[{:keys [seed-part rest-parts] :as mapping} | |
{:keys [name size] :as part}] | |
(let | |
[seed-pattern (re-pattern (str "^" seed-part "-")) | |
pattern-replacer (comp (partial str/replace name seed-pattern) #(str % "-"))] | |
(for [part-name (set-map pattern-replacer (conj rest-parts seed-part))] | |
{:name part-name | |
:size size}))) | |
(defn symmetrize-body-parts-for | |
[mapping asym-body-parts] | |
(let [matching-parts (partial matching-parts-by mapping)] | |
(reduce (fn [final-body-parts part] | |
(into final-body-parts (matching-parts part))) | |
[] | |
asym-body-parts))) | |
(def left-right-mapping {:seed-part "left" | |
:rest-parts ["right"]}) | |
(def four-parts-mapping {:seed-part "left" | |
:rest-parts ["right" "up" "down"]}) | |
(def symmetrize-body-parts (partial symmetrize-body-parts-for left-right-mapping)) | |
(defn hit | |
[asym-body-parts] | |
(let [sym-parts (symmetrize-body-parts asym-body-parts) | |
body-part-size-sum (reduce + (map :size sym-parts)) | |
target (rand body-part-size-sum)] | |
(loop [[part & remaining] sym-parts | |
accumulated-size (:size part)] | |
(if (> accumulated-size target) | |
part | |
(recur remaining (+ accumulated-size (:size (first remaining)))))))) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment