This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2020-12-09
Channels
- # adventofcode (197)
- # announcements (25)
- # aws (1)
- # babashka (21)
- # beginners (138)
- # calva (21)
- # cider (5)
- # clara (1)
- # clj-kondo (35)
- # clojure (97)
- # clojure-australia (4)
- # clojure-dev (37)
- # clojure-europe (100)
- # clojure-nl (2)
- # clojure-spec (7)
- # clojure-uk (36)
- # clojurescript (11)
- # conjure (15)
- # cursive (20)
- # datomic (12)
- # emacs (10)
- # events (2)
- # fulcro (83)
- # graalvm (14)
- # jobs (1)
- # jobs-discuss (27)
- # kaocha (75)
- # lambdaisland (21)
- # off-topic (27)
- # pedestal (5)
- # reitit (2)
- # reveal (20)
- # rewrite-clj (24)
- # sql (9)
- # tools-deps (37)
- # xtdb (93)
It’s vacuously true. An easy way to think of it is to list a counter example. Name an element that is in the empty set that is not in your other set
@st3fan empty sets of things often have surprising behavior at first glance. (and) ; true
, (or) ; nil
for example.
Similarly,
user=> (some some? [])
nil
user=> (every? some? [])
true
The latter is often more surprising, given the docstring says "Returns true if (pred x) is logical true for every x in coll, else false." because no elements are logical true.
And it can be confusing that (every? nil? [])
is of course also true
-- so every element is nil and not-nil at the same time 🙂
But it is true
because there are no elements in []
for which the predicate isn't "logical true".
Is there a way to evaluate a symbol to use as a keyword? For example, if I have '("A" "some data")
can you give a literal example of what you want to accomplish? is some data a map with keywords and you have a string and you want to look up the value at that keyword entry?
Never mind I found it: (keyword (first '("A" "some data")) gives me what I want: A:
Hi, What is the idiomatic way to convert :two-word
keyword to Two Word
strings?
You can also use this library for similar conversions: https://clj-commons.org/camel-snake-kebab/.
str it, split on "-", map capitize, and then join it back together with a string
this often comes up when converting keywords into display items in a UI. You can probably create a better regex to match on underscores and some other common separators if applicable
Hey guys,
Why does :
(first {:a 1, :z 2})
return [:a 1]
(val (first {:a 1, :z 2}))
return 1
BUT (val [:a 1])
throw a ClassCastException
instead of returning 1
as the two statements above would suggest ?
I guess it has to do with the underlying types (PersistentVector vs Map),
But wouldn't it be more consistent to have val
being equivalent to second
in case of a vector with 2 elements ?
Same thing for key
and first
I believe (class (first {:a 1, :z 2})
is a MepEntry class, not PersistentVector, and that key
and val
have special behavior for MapEntry objects that they do not have for regular vectors.
MapEntry objects have a default printed representation that looks like a two-element vector, and I believe operations that you can do on a vector also work on a MapEntry, e.g. nth, first, second, assoc.
But the converse is not true -- some operations like key
and val
work on MapEntry, but not on vectors.
it's kind of funny that this works
user=> (conj (first {:a 1}) :b)
[:a 1 :b]
I think it auto-promotes to persistent vector
yes, many operations that work on persistent vectors also work on MapEntry, but return an object with class clojure.lang.PersistentVector, not clojure.lang.MapEntry.
user=> (type (first {:a 1}))
clojure.lang.MapEntry
user=> (type [:a 1])
clojure.lang.PersistentVector
clojure has many examples where you can use a generic (second) or specific (val) function
i'm trying to get the sums of all possible pairs of numbers in a vector between i
and i-25
(let [subv (subvec v (- i 25) i)
a (transient [])]
(for [b subv
c subv
:when (> c b)]
(conj! a (+ b c)))
(persistent! a))
where v
is the input vector
why does this return an empty vector?
does that mean i have to use loop
and handle indices manually?
i think if you just use the for loop without the transient you have exactly what you want: a collection of (+ b c)
when (> c b)
. you don't need to accumulate this into another collection if the for builds this collection in the first place
you're building a collection and then for each element in that collection putting it into another collection. just use the first collection without the unnecessary extra collection
cool, but now those sums are in vectors
turns out i dont need a vector at all
(let [subv (subvec v (- i 25) i)]
(for [b subv
c subv
:when (> c b)]
(+ b c)))
is enoughit returns a list which i then turn into a vector
uhh idk actually
i'll go forward with the list
thanks !!
(defn my_filter
"filters a collection on a predicate"
[collection predicate]
(let [new_collection (seq collection)]
(for [element collection]
(if (predicate collection)
(conj element new_collection)
new_collection))
new_collection)
; Syntax error compiling at (chapter4.clj:13:24).
; Unable to resolve symbol: collection in this context
You’re also calling the predicate on the entire collection each time rather than the element
user=>
(defn my_filter
"filters a collection on a predicate"
[collection predicate]
(let [new_collection (seq collection)]
(for [element collection]
(if (predicate collection)
(conj element new_collection)
new_collection))
new_collection)
)
#'user/my_filter
user=>
hmm, I still see a error :
; Syntax error (ClassNotFoundException) compiling at (output.calva-repl:51:22).
; Thread.java:834
nope, I see only this :
; Syntax error (ClassNotFoundException) compiling at (output.calva-repl:51:22).
; Thread.java:834
clojure.lang.Compiler/analyze (Compiler.java:6808)
clojure.lang.Compiler$InvokeExpr/parse (Compiler.java:3820)
clojure.lang.Compiler/analyzeSeq (Compiler.java:7108)
clojure.lang.Compiler/analyze (Compiler.java:6789)
clojure.lang.Compiler$BodyExpr$Parser/parse (Compiler.java:6120)
clojure.lang.Compiler$FnMethod/parse (Compiler.java:5467)
clojure.lang.Compiler$FnExpr/parse (Compiler.java:4029)
clojure.lang.Compiler/analyzeSeq (Compiler.java:7104)
clojure.lang.Compiler/analyze (Compiler.java:6789)
clojure.lang.Compiler/eval (Compiler.java:7173)
clojure.core/eval (core.clj:3214)
clojure.core/eval (core.clj:3210)
nrepl.middleware.interruptible-eval/evaluate (interruptible_eval.clj:87)
clojure.core/apply (core.clj:665)
clojure.core/with-bindings* (core.clj:1973)
nrepl.middleware.interruptible-eval/evaluate (interruptible_eval.clj:87)
clojure.main/repl (main.clj:414)
clojure.main/repl (main.clj:435)
clojure.main/repl (main.clj:345)
nrepl.middleware.interruptible-eval/evaluate (interruptible_eval.clj:84)
nrepl.middleware.interruptible-eval/evaluate (interruptible_eval.clj:56)
nrepl.middleware.interruptible-eval/interruptible-eval (interruptible_eval.clj:152)
nrepl.middleware.session/session-exec (session.clj:202)
nrepl.middleware.session/session-exec (session.clj:201)
java.lang.Thread/run (Thread.java:834)
it will show a data representation of the last exception that bubbled up to the top of the repl loop
then I see this :
clj::chapter4=> *e
#error {
:cause "Thread.java:834"
:via
[{:type clojure.lang.Compiler$CompilerException
:message "Syntax error compiling at (/home/roelof/clojure/Learning_in_public/ground_up/.calva/output-window/output.calva-repl:51:22)."
:data #:clojure.error{:phase :compile-syntax-check, :line 51, :column 22, :source "/home/roelof/clojure/Learning_in_public/ground_up/.calva/output-window/output.calva-repl"}
:at [clojure.lang.Compiler analyze "Compiler.java" 6808]}
{:type java.lang.ClassNotFoundException
:message "Thread.java:834"
:at [java.net.URLClassLoader findClass "URLClassLoader.java" 471]}]
:trace
[[java.net.URLClassLoader findClass "URLClassLoader.java" 471]
[clojure.lang.DynamicClassLoader findClass "DynamicClassLoader.java" 69]
[java.lang.ClassLoader loadClass "ClassLoader.java" 589]
[clojure.lang.DynamicClassLoader loadClass "DynamicClassLoader.java" 77]
[java.lang.ClassLoader loadClass "ClassLoader.java" 522]
[java.lang.Class forName0 "Class.java" -2]
[java.lang.Class forName "Class.java" 398]
[clojure.lang.RT classForName "RT.java" 2207]
[clojure.lang.RT classForName "RT.java" 2216]
[clojure.lang.Compiler resolveIn "Compiler.java" 7394]
[clojure.lang.Compiler resolve "Compiler.java" 7357]
[clojure.lang.Compiler analyzeSymbol "Compiler.java" 7318]
[clojure.lang.Compiler analyze "Compiler.java" 6768]
[clojure.lang.Compiler analyze "Compiler.java" 6745]
[clojure.lang.Compiler$InvokeExpr parse "Compiler.java" 3820]
[clojure.lang.Compiler analyzeSeq "Compiler.java" 7108]
[clojure.lang.Compiler analyze "Compiler.java" 6789]
[clojure.lang.Compiler analyze "Compiler.java" 6745]
[clojure.lang.Compiler$BodyExpr$Parser parse "Compiler.java" 6120]
[clojure.lang.Compiler$FnMethod parse "Compiler.java" 5467]
[clojure.lang.Compiler$FnExpr parse "Compiler.java" 4029]
[clojure.lang.Compiler analyzeSeq "Compiler.java" 7104]
[clojure.lang.Compiler analyze "Compiler.java" 6789]
[clojure.lang.Compiler eval "Compiler.java" 7173]
[clojure.lang.Compiler eval "Compiler.java" 7131]
[clojure.core$eval invokeStatic "core.clj" 3214]
[clojure.core$eval invoke "core.clj" 3210]
[nrepl.middleware.interruptible_eval$evaluate$fn__964$fn__965 invoke "interruptible_eval.clj" 87]
[clojure.lang.AFn applyToHelper "AFn.java" 152]
[clojure.lang.AFn applyTo "AFn.java" 144]
[clojure.core$apply invokeStatic "core.clj" 665]
[clojure.core$with_bindings_STAR_ invokeStatic "core.clj" 1973]
[clojure.core$with_bindings_STAR_ doInvoke "core.clj" 1973]
[clojure.lang.RestFn invoke "RestFn.java" 425]
[nrepl.middleware.interruptible_eval$evaluate$fn__964 invoke "interruptible_eval.clj" 87]
[clojure.main$repl$read_eval_print__9068$fn__9071 invoke "main.clj" 414]
[clojure.main$repl$read_eval_print__9068 invoke "main.clj" 414]
[clojure.main$repl$fn__9077 invoke "main.clj" 435]
[clojure.main$repl invokeStatic "main.clj" 435]
[clojure.main$repl doInvoke "main.clj" 345]
[clojure.lang.RestFn invoke "RestFn.java" 1523]
[nrepl.middleware.interruptible_eval$evaluate invokeStatic "interruptible_eval.clj" 84]
[nrepl.middleware.interruptible_eval$evaluate invoke "interruptible_eval.clj" 56]
[nrepl.middleware.interruptible_eval$interruptible_eval$fn__995$fn__999 invoke "interruptible_eval.clj" 152]
[clojure.lang.AFn run "AFn.java" 22]
[nrepl.middleware.session$session_exec$main_loop__1062$fn__1066 invoke "session.clj" 202]
[nrepl.middleware.session$session_exec$main_loop__1062 invoke "session.clj" 201]
[clojure.lang.AFn run "AFn.java" 22]
[java.lang.Thread run "Thread.java" 834]]}
which was part of earlier stacktrace, which is why I didn't recognize it as part of the error message
(ns chapter4)
; Write a function to find out if a string is a palindrome–that is, if it looks
; the same forwards and backwards.
(defn palindrome?
"checks if a string is a palingdrome"
[word]
(= (seq word) (reverse word) ))
(defn my_filter
"filters a collection on a predicate"
[collection predicate]
(let [new_collection (seq collection)]
(for [element collection]
(if (predicate element)
(conj element new_collection)
new_collection))
new_collection))
because that error says the expression Thread.java:834
literal appears in your program, and for whatever reason clojure is trying to resolve it as a class, which it isn't, which is why you get the error
I give up
(my_filter [(1 2 3 4) (fn [x] (even? x)) ])
error :
; Execution error (ClassCastException) at chapter4/eval17683 (form-init1042520059576704410.clj:20).
; class java.lang.Long cannot be cast to class clojure.lang.IFn (java.lang.Long is in module java.base of loader 'bootstrap'; clojure.lang.IFn is in unnamed module of loader 'app')
(1 2 3 4)
is calling 1
as a function on the arguments 2 3 4
. The error message is saying that 1
a "java.lang.Long" can't be invoked (cast to clojure.lang.IFn)
use [] instead
that's the normal way in clojure also
there's also '(1 2 3 4)
but that's a more limited approach
oke, I give up on clojure . on the code that worked I see now suddenly
; Syntax error compiling at (chapter4.clj:10:1).
; Unable to resolve symbol: defn in this context
thanks for the help butI do not like to fight the whole day against a compiler with error messages that makes no sense
For whatever it's worth, you are defining my_filter to take two arguments, collection and predicate, but you only try to pass one argument when you call it, a vector containing the collection and predicate. After fixing the syntax issue with [1 2 3 4]
either use deconstruction in in my_filter, (defn my_filter [ [ collection predicate ] ] (...))
or pass the two parts separately as two different arguments.
@roelof in-ns
is only for debugging, in code it creates broken namespaces
they are fixable, but the easier fix is to just not use in-ns
@roelof You need to load the file before things start to work. (`ctrl+alt enter` if using Calva).
I feel ya about the error messages. But otherwise I kinda like how I am in control of what is defined where, using Clojure.
hi 🙂 I checked https://github.com/bbatsov/clojure-style-guide but didn’t find the following … what do you think about this as a suggestion?
> Only return a literal true
or false
from the body of an if
when you actually need a literal as a result and the if
’s condition doesn’t already evaluate to a literal.
>
> Bad — if a truthy non-literal result works in your context:
> (if (some pred coll) true false)
i'm not sure i'm following. but that repo is open to issues with suggestions for new guidelines and will most likely get some feedback
Hi I wonder what's the best candidate in Clojure to ceate a loop like in this Java snippet:
public static Socket getListeningSocket() {
for ( int port = MIN_PORT ; port <= MAX_PORT ; port++ )
{
try {
ServerSocket s = new ServerSocket( port );
return s; // no exception means port was available
} catch (IOException e) {
// try the next port
}
}
return null; // port not found, perhaps throw exception?
}
for
? loop
?How can I break on first success (first free port assigned)?
loop
requires a manual recur. recur in your catch
and you'll stop on the first successful port
ah sorry, can't recur from the catch. so just catch and return a sigil and check that against the sigil
Thx @dpsutton What is a "sigil"?
some recognizable value that can't come from starting a server. can do (Object.)
or ::bad
Thanks @dpsutton, it's exactly what I needed! And TIL sigil too. 😉
Hi community. I am trying to make a https://docs.oracle.com/javase/7/docs/api/javax/swing/filechooser/FileNameExtensionFilter.html with Java interop. This is what I’m doing:
(ns filter.core
(:import (javax.swing.filechooser FileNameExtensionFilter))
....
(def fnef (FileNameExtensionFilter. "CSV files", "csv"))
However, I’m getting the following error message:
Cannot cast java.lang.String to [Ljava.lang.String;
Can someone please tell me what I’m doing wrong? I’m a bit flummoxed! 😩https://clojure.org/reference/java_interop#_vararg_methods
that constructor uses varargs: FileNameExtensionFilter(String description, String... extensions)
(javax.swing.filechooser.FileNameExtensionFilter. "CSV files" (into-array String ["csv"]))
Ah, I see you cross-posted this in #interop as well. We prefer folks not cross-post questions since it can waste people's time replying in one channel, not realizing someone else has already helped you in another channel.
Thanks for your help!
(saved you the trouble -- I deleted your Q and my responses from there @UH0FTE610)
Great, thanks. Sorry for the faux pas, @U04V70XH6
The variadic interop catches folks out all the time. No worries!