I finally managed to reach level 3 in 12-13 sec (as opposed to 83)...at the moment, for level 3 there are only 4 sec separating the 2 real fns from the dummy ones that return immediately! This is very good news indeed... as for level 4, it still takes long (just over 9 min) but at least, not ridiculously long (this is the 1st time it returned without me interrupting it)... memoizing the fn that translates the positions from 2d to 1d (and vice versa) and storing the logical moves of all chess-pieces (except pawn) made a big difference...the profiler seems to think so as well...

however level 4 is still out of practical reach...I really don't want to involve Java arrays and stuff like that!

Jim


On 24/08/12 10:26, nicolas.o...@gmail.com wrote:
More optimsation ideas:

(defn next-level [b dir]

   (r/map #(Move->Board. % (core/try-move %))
              (core/team-moves @curr-game b dir))) ;;curr-game is a promise
(definline team-moves
      [game b dir]
`(let [team# (gather-team ~b ~dir)
        tmvs# (r/mapcat (fn [p#] (r/map #(dest->Move ~game p# %) (getMoves
p#))) team#)]
  (into [] tmvs#)) )
You should return tmvs# and not (into [] ...).
The beauty of reducers is that they are composable without putting
results in intermediate sequence.
So, as tmvs# is going to be passed to another reducer transformer, you
don't need to
convert it to a seq.


(definline gather-team "Returns all the pieces with same direction dir on
this board b."
[b dir]
`(into [] (r/filter #(= ~dir (:direction %)) ~b))) ;all the team-mates (with
same direction)
Same here, remove the (into []).
(Less important, you have only two directions, so you can compute the
closures for the two directions in advance
and use direction to choose. But it won't be a dramatic improvement.
For example:
(def gather-team
   (let [closure-up   #(= :up (:direction %)))) ;; use the name of your
direction here
         closure-down #(= :down (:direction %))))]
  (fn  [b dir]
    (r/filter (if (=dir :up) closure-up closure-down) ~b))))
)


(definline dest->Move "Helper fn for creating moves."
[dm p dest]  `(Move. ~p (partial move ~dm) ~dest))
You might want to see if replacing (partial move dm)
by  #(move dm %1 %2) helps a bit.
I doubt it won't change much though.

(defn move
"The function responsible for moving Pieces. Each piece knows how to move
itself. Returns the resulting board without making any state changes. "
[game-map p coords]
;;{:pre [(satisfies? Piece p)]}  ;safety comes first
;;(if  (some #{coords} (:mappings game-map)) ;check that the position exists
on the grid
(let [newPiece (update-position p coords) ;the new piece as a result of
moving
       old-pos  (getListPosition p)
       new-pos  (getListPosition newPiece)]   ;;piece is a record
(-> @(:board-atom game-map) ;deref the appropriate board atom
Why do you need an atom here?


--
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Reply via email to