This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2018-02-19
Channels
- # beginners (134)
- # boot (4)
- # cider (23)
- # clara (2)
- # cljs-dev (2)
- # cljsrn (4)
- # clojure (147)
- # clojure-austin (9)
- # clojure-berlin (2)
- # clojure-dusseldorf (2)
- # clojure-france (2)
- # clojure-italy (11)
- # clojure-russia (1)
- # clojure-spec (18)
- # clojure-uk (182)
- # clojurescript (40)
- # community-development (5)
- # cursive (29)
- # datascript (6)
- # datomic (18)
- # duct (6)
- # emacs (4)
- # events (1)
- # fulcro (46)
- # hoplon (5)
- # jobs-discuss (12)
- # keechma (1)
- # luminus (7)
- # lumo (1)
- # off-topic (11)
- # onyx (9)
- # parinfer (5)
- # protorepl (1)
- # re-frame (18)
- # reagent (23)
- # reitit (2)
- # ring (5)
- # ring-swagger (20)
- # schema (1)
- # shadow-cljs (32)
- # spacemacs (1)
- # specter (2)
- # vim (26)
Does the new clj
tool support the building of uberjars or similar? Or is the idea to always run programs with the clj
tool, even in production?
i've been working on a tool for uberjars, and dominic_m already released one, can't remember the github coords tho
@eigenhombre you can do java -cp "$(clj -Spath)" ....
if you want for production
thanks @ghadi
@ghadi I haven’t looked into clj much yet (but I think I should). Does that approach support AOT-ing things as well?
Will clj with the necessary plugins be able to replace lein and boot completely? The thing I like about boot is being able to program your builds. Is the same thing possible with clj?
hey guys, is it possible to extend a Java class with an Interface instead of a protocol? I am trying to make a custom Class have Clojure’s assoc syntax but I cannot find a protocol for it 😞
An existing class? Not really
@carocad you would typically use deftype
or defrecord
for that
or proxy
@val_waeselynck I think proxy is what I am looking for. Do you know if It can be used even for final
classes? I dont see anything in the docs 😕
I guess not, but why guess when you can try 🙂
However, why would you want to extend a final class? Final classes are only meant to be instantiated, not extended
well I want to be able to implement Clojure’s assoc, contains and other functions on a class that has already been defined and made final.
So I thought that I had two options: - create a Type and wrap the original instance - create a Proxy and implement the necessary interfaces
I would go with option 1 - trying to extend a final class sounds like asking for trouble to me
from your comment it seems that it is not possible (dont have a REPL at hand right now). But in any case the option 1 is still on the table so I guess it would work
even though we have protocols in Clojure, most of the time composition is still better than inheritance in my experience
@carocad the interface for assoc
is clojure.lang.Associative i believe: https://github.com/clojure/clojure/blob/master/src/jvm/clojure/lang/Associative.java
ok so I’ve got some massive data structures I keep printing out. Being as we don’t have a nice `.toString()’ in Clojure - what’s the best way to do custom pretty printing of big data structures?
clojure.pprint/pprint
or go with this https://github.com/eggsyntax/datawalk
in cljs use console.log
and explore the data with the cljs-devtools
custom formatter
ok datawalk looks like a dream. Thanks @joelsanchez!
I'm surprised there's no (clojure.util/webserver-dom-print ...) yet, where it fires up a ring server, sets up web sockets, loads up a chrome window, and prints the data structure in an interactive gui where you can click +- to expand/close nodes
zprint might be able to do that, not sure. Since it can highlight specific keys and order them in various ways, if it currently cannot do what you want, I'm sure it could and the author is always open to suggestions: https://github.com/kkinnear/zprint
OK, the :key-ignore-silent option for maps seems to provide what you want - except it goes the other way 'round. You tell it which to 'skip'; not which to keep...
Yeah, zprint is kind of amazing...
I’m looking at some disassembled Clojure code and I see this:
invokestatic clojure.lang.Numbers.and(long, long) : long [244]
and when looking at the compiler source code I see this: https://github.com/clojure/clojure/blob/master/src/jvm/clojure/lang/Intrinsics.java#L24Yeah, zprint is kind of amazing...
I'm writing a small utility app for parsing our local banks bank statement pdf:s and my GF is interested in using that also. So what is best way nowadays to pack Clojure app for use for non-technical people?
https://github.com/BrunoBonacci/lein-binplus there is a nice plugin for leiningen that does that
https://github.com/clojure/clojure/blob/master/src/jvm/clojure/lang/Intrinsics.java#L114-L135 those guys only affect IfExprs
okay, so
(defn foo []
(bit-and 1 2))
does not get an intrinsic, but if you type hint the function with ^long
it doeshmm… ok. so here’s the actual code I’m doing, all variables are primitive longs:
(loop [i robot]
(cond
(or (< i 0) (>= i BOARD-SIZE)) -1
(not= (bit-and (aget ^longs board i) (dir->byte dir)) 0) i ;; dir->byte is map keyword -> long
(and (not= i robot) (or (= i blue) (= i green) (= i red) (= i yellow))) (- i step)
:else (recur (+ i step))))))
cool! shouldn’t be hard to make one since it’s a 20 line fn that basically just compares a bunch of longs
im debugging some code and i think i may see a race condition — it would be great if someone could help by confirming my understanding of the semantics of swap!
and atoms:
(declare bar) ;; does some stuff
(defn bar-until [foo]
(when (pos? @foo)
(bar)
(swap! foo dec)))
(def foo (atom 10))
(in-a-tight-loop
(bar-until foo))
i am using a counter in an atom to only run some function a limited number of times
this function is called in a tight loop and the issue i think i may be seeing is that control passes back into bar-until
while there are outstanding updates to foo
i realized i don’t understand the exact concurrency semantics of atom
s — is the guarantee that foo
will be updated before swap!
returns? or just that it will be updated some time
i essentially want to block until that happens — but it seems like i should avoid something like busy waiting on compare-and-set!
@alexstokes atoms are not blocking, they run optimistically and retry if there is contention
the problem with that code is that checking for positivity of foo and running the inc are totally uncoordinated actions, and that is your race condition
further, you can’t put anything in a swap! that can’t be run multiple times, so you probably don’t want to put the call of bar into the swapping function either (unless it’s idempotent)
but you wouldn’t see a problem there until multiple threads are using bar-until
@alexstokes there’s no concept of “outstanding updates” to atoms as far as I know - you have individual method bodies calling compare-and-set! repeatedly and eventually committing the result when it succeeds
so yes, if you have two threads each updating foo, the first one to attempt a modification will resume before the second one has successfully updated the value
if you need locking behavior, you don’t want any of clojure’s built in concurrency objects
(but finding a non-locking solution is highly encouraged, and immutable data makes this easier than one might think)
you might be able to do what you want in a straightforward manner with agent
plus await
- agents do lock for each updating function, and they do keep track of pending actions and let you wait on them
they are the only built in concurrency container in clojure that doesn’t retry (but with other clojure core libs there’s also core.async channels and maybe some others)
I think you've confused him @noisesmith. There is a simple fix here: check and swap the atom before running the side effect:
oh? - perhaps I’m the one confused
oh, right, checking the return value of swap! makes it much simpler doesn’t it
I was sitting here trying to figure out where the bug in doing that was which was causing you to not suggest that, @noisesmith
at least I identified the problem, so I’m half way there
"if you're dereffing an atom more than once in a function, you've probably got a race" - quote me
accessing more than once, and at least one access is a deref
two swap! calls is fine for example, if you don’t deref too (and use the return value of the most recent swap!)
(if I’m thinking this through clearly)
swap!
has to block in this case tho correct? as in the update has to occur before it can return a value for the #(< % MAX)
evaluation
swap! blocks the thread calling it, yes
so then why would the original code sample have the race condition?
because you check the value with @, then run the operation
those two operations are not synchronized, so it’s a race
ah gotcha
https://github.com/web3j/web3j/blob/07abcb50594af5966fbcea881d5e132e4b072af8/utils/src/main/java/org/web3j/utils/Convert.java How can I do the equivalent of Convert.Unit.ETHER? I've been trying for a while but I can't come up with the solution
Convert$Unit/ETHER
inner classes are fictional, they are just classes with $ in the middle of the name
(as far as the vm is concerned that is)
No such namespace, says the REPL
in that case you need to import Convert$Unit, or fully qualify it as org.web3j.utils.Convert$Unit/ETHER
Referring to Convert$Unit, anyways
ah, I see
it’s just a class with $ in the name, so importing Convert doesn’t affect its visibility
that did it
Thanks a bunch!
I have a stream of incoming data, and i want to capture an initial value, look it up in a hashmap, see how many subsequent items to capture/partition along with that value. Is this a time to write my own stateful transducer, or is there a higher level function for dealing with this that I'm missing?
(def lookup {5 3 ;;capture the next 3 values after first 5 is seen
7 1 ;;capture next value. etc.
0 5})
(def stream [5 ;;capture the next 3 values (do not look those up)
9 0 7
7 ;;capture next 1 value
1
0
4 5 8 9 5 ])
=> ((5 9 0 7) (7 1) (0 4 5 8 9 5))
I don’t think a transducer would be useful here - at least not for a first version - this is pretty simple to do with lazy-seq, drop, take
actually, i should have mentioned these will be coming in on a core.async channel. Is it still fine to do it the lazy seq way?
oh, if it’s coming off a channel then yeah, use drop / take and a volatile
but you might find it helpful to write the lazy-seq version first, it’s simpler I think
(and the transducer version will be mostly like it, except using a volatile and having more arities etc.)
I have a protocol with two different implementations, but I want to reuse the same tests for both. any standard approach for doing this with clojure.test?
@schmee if you call is inside a defn, then call the defn inside a test, it works
I’ve found it’s helpful to construct a string as the second arg to is, describing the specific args supplied - otherwise failures can be ambiguous
that is, describing the args to the function - that way you can distinguish failed calls to the same is from different tests
another option is to do all the hard work in a function returning a hash-map, then make all your assertions about the values inside that map - then the only duplicate code is the is calls, and not the code that runs the actual test
I’m looking for something like shared examples in RSpec, if you are familiar with that: https://relishapp.com/rspec/rspec-core/docs/example-groups/shared-examples#shared-examples-group-included-in-two-groups-in-one-file
but as you say I guess I could wrap everything in a huge defn and pass the implementations as an argument to that fn
the defn approach is good enough in my experience - typically the right solution with clojure.test is just using normal higher order programming
there’s also clojure.test/are if you want to make the assertions on multiple results in one test more concise https://clojuredocs.org/clojure.test/are
yeah I should definitely be using it more often
https://clojuredocs.org/clojure.template I discovered this gem a little while ago, in a similar vein 🙂
(defn evalWinVariant
""
[a b c]
(if (and (not= a 0) (not= b 0) (not= c 0))
(if (and (= a b) (= b c) )
true
false)
false)
)
I’m new to clojure and i feel like this function could be written much nicer … more the functional way … any suggestions? How would i return false/true in the first case?The inner if
could be replaced by its condition -- (if A true false)
is equivalent to A
And (if A B false)
can be replaced by (and A B)
In addition, if you want to test for a
and c
both being equal to b
, you can do (= a b c)
@sirhenry91 Can those numbers be negative?
(also, on style, we use snake-case
rather than headlessCamelCase
in Clojure, so it would be eval-win-variant
... and since it returns Boolean and we allow ?
in a function name, you could call it win-variant?
perhaps)
OK, so if they are all non-negative, you could use pos?
as a predicate instead of (not= a 0)
-- I think that would read better?
(and (pos? a) (pos? b) (pos? c)
(= a b c))
and since the result only needs to be true if they are all equal, you could get away with just testing one of the arguments...(and (pos? a) (= a b c))
Alternative golf -
(defn eval-win-variant
""
[a b c]
{:pre [(nat-int? a)
(nat-int? b)
(nat-int? c)]}
(and (= a b c)
(not= a 0)))
So we end up with
(defn win-variant?
""
[a b c]
(and (pos? a) (= a b c)))
And just in case you wanted to be really paranoid and test all three arguments are positive: (every? pos? [a b c])
perhaps?
I'm probably the odd person out here, but I find that preconditions and postconditions are super useful for debugging because they give you precise errors around where in your dataflow something went wrong.
@seancorfield That looks splendid, thank you 🙂
And welcome to Clojure @sirhenry91!
(you may find the #beginners channel helpful since folks there have opted in to helping Clojure novices in great detail)