Search code examples
clojure

clojure map transformation with Input values from sequence


Need Help in transforming data from map using a function

(defn transform-map-1 [past-step dir]
  (cond (= dir "v")
        (list (first (first past-step))
              (+ -1 (first (first past-step))))
        (= dir "^")
        (list (first (first past-step))
              (+ 1 (first (first past-step))))
        (= dir ">")
        (list (+ 1 (first (first past-step)))
              (first (first past-step)))
        (= dir "<")
        (list (+ -1 (first (first past-step)))
              (first (first past-step)))))

This function takes two input co-ordinates in x,y format as past step and dir up down left right to give the updates co-ordinates

what I would like to do have a series of directions and for each dir return updated co-ordinates

Input Sting "^>v<" , output should be ((0,1) (1,1) (1,0) (0,0)

we start with co-ordinates (0.0) Output from the first transformation becomes the input for the second char

The best I could come for is but it gives me an error

(map (transform-map-1 ['(0, 0)] %1)(char-array string-test))

Solution

  • You were close with your implementation.

    The issues I see are:

    • The %1 in your call to transform-map-1 is valid only in an anonymous function which uses this format: #( ... use %1 %2 %3 etc inside)

    • Your function expects the direction to be a String, but mapping over a String will result in an iteration over a sequence of Characters, which is not what your function expects. One trick to turn a single String into multiple 1-character Strings is (map str your-string), which uses str to turn each Char into a String.

    With those two changes, the call to your function will look like this:

    (def test-string "^>v<")
    
    (map #(transform-map-1 ['(0, 0)] %1) (map str test-string))
    ;; returns: ((0 1) (1 0) (0 -1) (-1 0))
    

    There are other things you can learn later on that could help you solving your puzzle:

    • Destructuring will help you break apart the arguments in the individual components and give them names so they are easier to work on
    • Style: most Clojure devs would represent a pair of coordinates as a 2-sized vector which can be written with square brackets: [x y]
    • Reduce: If you have a function that performs a single step, you can reduce a collection containing the movements and obtain the final position. With reductions you can also obtain all the intermediate steps, if you need the full trail.