Just thought about a FizzBuzz solution written in frege which I saw on a meetup. This solution does not need any conditionals and is completely lazy, which is why I like this solution so much.
The rules are as follows:
- print all numbers from 1 to n, but...
- replace all numbers, which are smoothly divisible by 3, with "fizz"
- replace all numbers, which are smoothly divisible by 4, with "buzz"
- if the number is smoothly divisible by both numbers, replace it with "fizzbuzz"
The implementation is very simple:
- Define all numbers starting from 1
- Define lazy sequences of the fizz- and the buzz-pattern
- If there is "fizz" (x)or "buzz" in one of those list, print them instead of the number
Now in Clojure:
(def nat (iterate inc 1))
(def fizz (cycle ["" "" "fizz"]))
(def buzz (cycle ["" "" "" "buzz"]))
(def fizzbuzz (map #(if (= "" %2 %3) %1 (str %2 %3)) nat fizz buzz))
And here we are. fizzbuzz
contains now an infinite list of our desired
pattern. Let's verify the result:
(take 12 fizzbuzz)
=> (1 2 "fizz" "buzz" 5 "fizz" 7 "buzz" "fizz" 10 11 "fizzbuzz")
Yesterday we implemented FizzBuzz in a "Clojure Beginners" Session at @clojuredus and @rbialon had an improvement for this without having to use ifs. I then just simplified the anonymous function to this:
(def fizz (cycle [nil nil "FIZZ"]))
(def buzz (cycle [nil nil nil "BUZZ"]))
(def numbers (map inc (range)))
(def fizzbuzz
(map #(or (not-empty (str %1 %2))
%3)
fizz buzz numbers))
(take 13 fizzbuzz)
Always learning and seeing more fascinating solutions for easy problems :-)