This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2017-07-27
Channels
- # aleph (3)
- # beginners (89)
- # boot (198)
- # cbus (4)
- # cider (11)
- # clara (2)
- # cljs-dev (27)
- # cljsrn (4)
- # clojure (141)
- # clojure-austin (4)
- # clojure-italy (11)
- # clojure-nl (1)
- # clojure-poland (2)
- # clojure-russia (35)
- # clojure-spec (33)
- # clojure-uk (55)
- # clojurescript (111)
- # core-logic (15)
- # cursive (2)
- # datascript (47)
- # datomic (132)
- # emacs (4)
- # jobs (1)
- # lein-figwheel (13)
- # leiningen (15)
- # lumo (20)
- # off-topic (110)
- # om (8)
- # onyx (20)
- # parinfer (2)
- # protorepl (1)
- # re-frame (36)
- # reagent (5)
- # remote-jobs (1)
- # ring (2)
- # ring-swagger (5)
- # specter (6)
- # uncomplicate (3)
- # unrepl (77)
Hi gang! I was having trouble earlier getting React to work in Figwheel with the new native :npm-deps
options, but I got it all sorted out thanks to some help from @spinningtopsofdoom and @tiagoantao . I documented how to make it work; hopefully it will help somebody else if they run into the process is not defined
error:
https://ajpierce.github.io/posts/react-figwheel-npm/
Thanks for the help, everybody 🙂
Yeah, the docs seem to indicate that it's most useful for development, but I don't see how cljsbuild would be able to distinguish between dev and min builds. https://github.com/clojure/clojurescript/wiki/Compiler-Options#preloads
I think in either case, we still need the side effect of defining process.env/NODE_ENV
in order for React to know how to behave
hello! looking for a shove in the right direction. I am trying to do this codewars kata: Collatz Conjecture https://www.codewars.com/kata/collatz-conjecture-3n-plus-1 here is my code so far:
(ns clojure.collatz)
(defn hotpo [n]
(loop [m n, count 0]
(when (> m 1)
(recur
(cond
(even? m) (int (/ m 2))
:else (int (+ (* m 3) 1)))
(+ count 1)))))
the value of count
is what i want to return. how can i do this?change the when into if, and put count as the third form in the if
you return from a loop by having a form that doesn't end in a recursion
@noisesmith sorry i don't follow, what do you mean by: > put count as the third form in the if ?
(when false :hi)
will return nil. but (if (> m 1) (recur for collatz) count)
will return the count if the collatz procedure has finally reduced the number to 1
the when form returns nil when the predicate fails. But your predicate is "do i need to reduce some more". if not, you need to return the count
@dpsutton @noisesmith got it, thanks!
so now my function looks like this:
(defn hotpo [n]
(loop [m n, val 0]
(if (> m 1)
(recur
(cond
(even? m) (int (/ m 2))
:else (int (+ (* m 3) 1)))
(+ val 1))
val)))
does this look unreadable? it looks hard to read for me. how can i make it neater?Doesn't look that bad to me. I'm not sure you need the cond
if you only have two options though. Maybe another if
?
(if (even? m)
(int (/ m 2))
(int (+ (* m 3) 1))
a lot of readability is familiarity - since you're new to clojure, it's bound to feel a little strange to begin with
in previous exercises i have made my code more readable by using thread first and last
A thing you might want to consider is separating the iteration fn from the loop
e.g. (defn hotpo-iter [n] (if (even? n) (/ n 2) (inc (* n 3))))
Then you could use the core iterate
fn and normal seq fns to identify the fixpoint
(take-while (partial not= 1) (iterate hopto-iter 23))
and if you can prove if that is an infinite sequence or not in general you can get a million bucks
another trick here is you can use (int (if p? foo bar))
to replace (if p? (int foo) (int bar))
using all your help my function now looks like this
(defn hotpo [n]
(defn hotpo-iter [n]
(int (if (even? n) (/ n 2) (+ (* n 3) 1))))
(loop [m n, val 0]
(if (<= m 1)
val
(recur (hotpo-iter m) (+ val 1)))))
it's much nicer now imodon’t put defn inside defn
defn is only able to create namespace level bindings, for local bindings use fn inside let
@rorysmith I like to put the short option first, which in this case means flipping the sense of the boolean, so something like
So if we’re done, we return val immediately. Otherwise, the rest of the code is all talking about the “else” clause, so there’s less confusion about where the “if” ends and the “else” begins.
Hey, I have kind of a dumb question, think I'm missing something obvious. Can anyone tell me what's wrong with this?
=> (let [m {:n {}}] (update m :n merge-with + {:a 1}))
IllegalArgumentException contains? not supported on type: clojure.core$_PLUS_ clojure.lang.RT.contains (RT.java:829)
@timgilbert What you wrote: (update m :n #(merge-with % + {:a 1}))
what you want: (update m :n #(merge-with + % {:a 1}))
Aha! Thanks @rauh
I am doing an exercise where I have to create a function which takes in a sequence and returns a sequence of all possible rotations.
Here's the exercise: http://iloveponies.github.io/120-hour-epic-sax-marathon/recursion.html#exercise-18
Is there anyway I can club that code into a single function ? I couldn't come up with a base condition for single function so I used count.
you can make it one function with multiple arities
also fyi you can replace '()
with ()
- it’s unambiguous so the reader accepts it
of course '(())
still needs quoting
(defn rotations ([s] (rotations s (count s))) ([s count] ...))
is the general form of the multiple arity version
@noisesmith I am not familiar with the concept of arities yet. I will look that up. Thanks 🙂 . I am going by the course I linked. It hasn't introduced arities yet.
it’s the same code you have already, both functions have the same name, they are distinct by argument count
and they are in the same defn body
I have no idea what arities are. I will look that up first. Thank you @noisesmith
Is it common to write recursive functions the way I wrote it in case I don't have a natural base condition or just use arities instead ?
@retrazil “arity” is a fancy word for “number of arguments”
@retrazil the common way is to use distinct arities, but the logic looks the same
Is this what you mean @noisesmith ?
if that runs, you got it right
@noisesmith how can i use a function local to the function i am in? i tried using let
but it seems you can't do the same thing as with defn
.
for example, can't i just put the first-letter
and last-letter
functions inside the generate-band-name
function to avoid having to pass noun
into them?
(defn first-letter [noun] (subs noun 0 1))
(defn last-letter [noun]
(def length (count noun))
(subs noun
(dec length)
length))
(defn generate-band-name [noun]
(if (= (first-letter noun) (last-letter noun))
(clojure.string/capitalize (str noun (subs noun 1)))
(str "The " (clojure.string/capitalize noun))))
yes, you can put them in there in a let
(defn generate-band-name [noun]
(let [first-letter (fn first-letter [] ...)
last-letter (fn last-letter [] ...)]
...)
also don’t use def inside defn, that’s the primary purpose of let
and like defn, def only creates namespace level bindings, it doesn’t create locals
the name inside fn
is optional, but makes stack traces more readable
@rorysmith @noisesmith Hey you can also use letfn
(defn foo [& args]
(letfn [(bar [x] ...)
(baz
([] ...)
([x y]))]
(->> args
bar
(baz 1))))
yes, that’s true
but let is more flexible since you will usually end up wanting to bind local data too
letfn is great for when two functions each need to call the other though
eg. for trampoline
(probably no longer in #beginners territory on that note)
@rorysmith but as @noisesmith said don’t you def
or defn
insisde of themselves these forms are side effects (they modify the namespace) you are better of with let
and letfn
@noisesmith I didn’t know letfn
lets you use the function as if they were declared before hand. Nice.
@rorysmith Just FYI, you can call first
and last
directly on a string, so (first noun)
and (last noun)
will work. Note: last
operates in linear time!
I believe that (get noun (dec (count noun)))
would be the constant time equivalent to (last noun)
-- just in case you care about performance enough (for long band names!).
(took me a while to trace through the source there but String
implements CharSequence
so (count noun)
is (.length noun)
and (get noun n)
is (.charAt noun n)
under the hood)
@seancorfield is there a place that can tell you the time complexity of some things oin clojure? or just knowing the source code?