Fork me on GitHub
#beginners
<
2022-07-02
>
cheeze200009:07:22

hello, i created a new project with leiningen and i have always wondered what this (:gen-class) thing is. i deleted it and my project still runs. what could i possibly miss if i deleted that? is it okay to delete it?

Mattias10:07:55

Hi, what is a good example of lazy XML parsing? I am parsing some RDF/OWL/etc type data, which typically (as far as I’ve seen) are in a fairly flat XML structures but a lot of logical connections (ie IDs connecting things via XML attributes). Anyway, what is the up-to-date choice of function/library/method? Thanks! 🙂

1
emccue14:07:15

clojure.data.xml, methinks

Mattias20:07:56

Cheers 🙂

rafalw11:07:01

Hi Clojure collections are immutable so if I have something like that

(def a [1 2 3])
(def b (conj a 4 5 6))
is there a way to find difference between b and a without using clojure.data/diff or simillar ?

lsenjov11:07:29

You could convert them to sets and use clojure.set/difference

lsenjov11:07:49

Depends exactly what you're after, since sets will ignore ordering/duplicates

rafalw13:07:30

thanks, I was wondering if it's possible to leverage fact that those collections are immutable and b i "derivative" of a, so for big collections with big set of changes we can get very fast diff

lsenjov13:07:40

Not quite. Vectors are b32 trees with a tail, so it doesn't actually know that b is derived from a

lsenjov13:07:01

You could do something with linked lists, as those are done element by element

lsenjov13:07:11

And you can go rest until the hashes match

andy.fingerhut13:07:19

I have heard of some immutable collection implementations that can leverage the fact not that one is derived from the other, but if they are both hash sets or hash maps, for example, that their implementation has trees with the same structure for the same sets of keys, and optimizes determining differences based on that. The Clojure built-in implementations do not do that, though.

lsenjov13:07:04

I mean, the clojure ones do do that, I just don't believe it's applicable to this case

peterh13:07:26

Does anyone know why it is not possible to refer to an argument list with :as like you can in vector destructuring?

(defn foo [a b :as args] args) ; error!
(defn bar [[a b :as args]] args)
When evaluating foo, I get “Syntax error macroexpanding clojure.core/defn”. I wonder if there is a reason why this is not allowed/implemented. Sometimes I’d like to refer to all arguments as a list in a multi-arity function:
(defn foo
  ([x y] ...)
  ([_ _ & _ :as args] ...))
What could I do instead to avoid having to conjoin all bindings in the second arity?

dpsutton14:07:24

Destructuring allows reaching into and not creating new ones. There is no mechanism to create a list from individuals in destructuring.

dpsutton14:07:52

As for your request, you'll have to do it manually I believe. Why do you want a collection of the args?

peterh14:07:13

Sometimes I need to treat the arguments as a collection (for recursion, reductions, etc.) but still need to refer to them individually in another arity. I wonder if Clojure would need to actually create a new list or if it would have the argument list/vector already in memory. If that is the case, :as ... should be free and more efficient than manually creating a new list. But I guess they had their reasons not to provide this.

dpsutton14:07:23

It's not a list. Those are individual arguments I believe

teodorlu16:07:04

In general, I like using a map as input when I might want to pull out individual things -- or not. > What could I do instead to avoid having to conjoin all bindings in the second arity? If you mean "use a let binding" I think you probably have to. Here's two options:

;; if you want to communicate to the consumer that a and b are special
(defn foo [a b & rest]
  (let [args (concat [a b] rest)]
    ;; a, b and args are in scope
    {:a a :b b :args args}))
(foo :a :b :c :d)
;; => {:a :a, :b :b, :args (:a :b :c :d)}

;; if you want to communicate to the user that is just a sequence
(defn foo [& args]
  (let [[a b & _] args]
    ;; a, b and args are in scope
    {:a a :b b :args args}))
(foo :a :b :c :d)
;; => {:a :a, :b :b, :args (:a :b :c :d)}