Skip to content

Instantly share code, notes, and snippets.

@Engelberg
Created December 27, 2013 01:50
Show Gist options
  • Save Engelberg/8141352 to your computer and use it in GitHub Desktop.
Save Engelberg/8141352 to your computer and use it in GitHub Desktop.
Why namespaces are not as good as classes
(ns mark.grid)
; I'm working with grids that are primarily 3x4.
; I get up and running with the following simple code.
(def rows 3)
(def cols 4)
(def cells (for [row (range rows), col (range cols)] [row col]))
(defn select-cells-by-row [row]
(filter (fn [[r c]] (= row r)) cells))
(defn print-cells-by-row [row]
(doseq [cell (select-cells-by-row row)]
(println cell)))
; But now, I realize that I want to work with other size grids.
; If this namespace were a "class", the change would be trivial:
; just add a constructor that sets the rows and cols
; In Clojure, we end up with this kind of nonsense:
(defrecord GridSize [rows cols])
(def default-grid-size (->GridSize 3 4))
(defn cells
([] (cells default-grid-size))
([{rows :rows cols :cols}]
(for [row (range rows), col (range cols)] [row col])))
(defn select-cells-by-row
([row] (select-cells-by-row default-grid-size row))
([grid-size row]
(filter (fn [[r c]] (= row r)) (cells grid-size))))
(defn print-cells-by-row
([row] (print-cells-by-row default-grid-size row))
([grid-size row]
(doseq [cell (select-cells-by-row grid-size row)]
(println cell))))
; IMHO, this is an obscene amount of additional code to scale
; a project that relies on mutual functions seeing the same
; vars to one in which those vars become parameters.
@johnwalker
Copy link

Hi Mark, maybe you want this sort of thing? https://gist.github.com/johnwalker/8142143

(The idea being that you can store the methods according to a protocol referencing the records parameters.)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment