(ns spreads | |
(:use zeder)) | |
(def legal-cards | |
[:๐ก :๐ฑ :๐ :๐ | |
:๐ข :๐ฒ :๐ :๐ | |
:๐ฃ :๐ณ :๐ :๐ | |
:๐ค :๐ด :๐ :๐ | |
:๐ฅ :๐ต :๐ :๐ | |
:๐ฆ :๐ถ :๐ :๐ | |
:๐ง :๐ท :๐ :๐ | |
:๐จ :๐ธ :๐ :๐ | |
:๐ฉ :๐น :๐ :๐ | |
:๐ช :๐บ :๐ :๐ | |
:๐ซ :๐ป :๐ :๐ | |
:๐ญ :๐ฝ :๐ :๐ | |
:๐ฎ :๐พ :๐ :๐ | |
]) | |
(def goal [:๐ :๐ ]) | |
(def S (engine :schemas #{{:z/ident :card-game/deck | |
:z/valueType :z.type/keyword | |
:z/cardinality :z.cardinality/many | |
:z/doc ""} | |
{:z/ident :card-game/goal | |
:z/valueType :z.type/keyword | |
:z/cardinality :z.cardinality/many | |
:z/doc ""} | |
{:z/ident :card-game/player | |
:z/valueType :z.type/string | |
:z/cardinality :z.cardinality/one | |
:z/doc ""} | |
{:z/ident :card-game/hand | |
:z/valueType :z.type/keyword | |
:z/cardinality :z.cardinality/many | |
:z/doc ""}} | |
:facts | |
(let [mf (gen-id) | |
ca (gen-id)] | |
#{[#z/id [_] :card-game/deck legal-cards] | |
[#z/id [_] :card-game/goal goal] | |
[mf :card-game/player "Fogus"] | |
[mf :card-game/hand goal] | |
[ca :card-game/player "Craig"] | |
[ca :card-game/hand [:๐ฉ :๐น :๐ :๐ ]]}))) | |
;; Spreads | |
;; ======= | |
'[ca :card-game/hand [:๐ฉ :๐น :๐ :๐ ]] | |
;; ^ ^ | |
;; | | | |
;; +-- spread --+ | |
;; Precise spread matches | |
;; ---------------------- | |
(def exact-goal | |
'[(strict-winning-hands) | |
[?pid :card-game/player ?pname] | |
[?pid :card-game/hand [?card1 ?card2]] | |
[?gid :card-game/goal [?card1 ?card2]]]) | |
;; ^ ^ | |
;; | | | |
;; +-- spreads --+ | |
(tuples->maps (q S exact-goal)) | |
;;=> ({:z/id #uuid "40eb458b-af80-45b6-b08f-2f79f4fd7edf", | |
;; :card-game/player "Fogus", | |
;; :card-game/hand [:๐ :๐]}, | |
;; {:z/id #uuid "00000000-0000-07b7-0000-000000305ae3", :card-game/goal [:๐ :๐]}) | |
;; Front-loaded matches | |
;; -------------------- | |
(def gif '[(front-winning-hands) | |
[?pid :card-game/player ?pname] | |
[?pid :card-game/hand [?card1 ?card2]] | |
[?gid :card-game/goal [?card1 ?card2 ...]]]) | |
;; ^ | |
;; | | |
;; ... two or more cards in hand | |
(let [rh (gen-id)] | |
(assert! S | |
[[rh :card-game/player "Rich"] | |
[rh :card-game/hand [:๐ :๐ :๐ซ :๐ป :๐ :๐ ]]])) | |
(tuples->maps (q S exact-goal)) | |
;;=> ({:z/id #uuid "40eb458b-af80-45b6-b08f-2f79f4fd7edf", | |
;; :card-game/player "Fogus", | |
;; :card-game/hand [:๐ :๐]}, | |
;; {:z/id #uuid "00000000-0000-07b7-0000-000000305ae3", :card-game/goal [:๐ :๐]}) | |
(tuples->maps (q S gif)) | |
;;=> ({:z/id #uuid "8d13960f-4276-408d-9a2d-89e013a8cc04", | |
;; :card-game/player "Fogus", | |
;; :card-game/hand [:๐ :๐]}, | |
;; {:z/id #uuid "00000000-0000-07b7-0000-000000305ae9", :card-game/goal [:๐ :๐]}, | |
;; {:z/id #uuid "99b4ef01-aac1-47db-8555-ad9e5a5ea079", | |
;; :card-game/player "Rich", | |
;; :card-game/hand [:๐ :๐ :๐ซ :๐ป :๐ :๐]}) | |
;; Anywhere matches | |
;; ---------------- | |
(def anywhere '[(anywhere-winning-hands) | |
[?pid :card-game/player ?pname] | |
[?gid :card-game/goal [?card1 ?card2]] | |
[?pid :card-game/hand [... ?card1 ... ?card2 ...]]]) | |
;; | |
;; * There are some number of cards, then a goal card, then more | |
;; cards, then another goal card and then more cards. | |
(let [jk (gen-id)] | |
(assert! S | |
[[jk :card-game/player "Jamie"] | |
[jk :card-game/hand [:๐ซ :๐ป :๐ :๐ :๐ :๐ ]]])) | |
(map :card-game/hand (tuples->maps (q S anywhere))) | |
;;=> ([:๐ :๐] nil [:๐ :๐ :๐ซ :๐ป :๐ :๐] [:๐ :๐ซ :๐ป :๐ :๐ :๐]) | |
;; ### But... | |
;; ... spreads are ordered | |
'[(uber-anywhere-winning-hands) | |
[?pid :card-game/player ?pname] | |
[?pid :card-game/hand [?card1 ?card2]] | |
[?gid :card-game/goal [... ?card2 ... ?card1 ...]]] | |
;; ^ ^ | |
;; | | | |
;; +----------+ | |
;; | | |
;; cards and goals should be | |
;; pre-ordered and insertion | |
;; sorted for nice matching with | |
;; spreads |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment