# #clojure log - Mar 11 2011

The Joy of Clojure
Main Clojure site
IRC
List of all logged dates

0:32 sorenmacbeth: hi all

0:33 could someone help me? I'm trying to collapse a seq of seqs into a single seq like: (("a") ("b") ("a b")) -> ("a" "b" "a b")

0:37 tomoj: \$findfn '(("a") ("b") ("a b")) '("a" "b" "a b")

0:37 sexpbot: [clojure.core/flatten]

0:38 sorenmacbeth: thank you!

0:43 tomoj: sexpbot: botsnack

0:43 sexpbot: tomoj: Thanks! Om nom nom!!

0:43 tomoj: though..

0:43 if yours are only nested one deep, maybe (apply concat) is better?

1:36 amalloy: tomoj, sorenmacbeth: http://stackoverflow.com/questions/5232350/clojure-semi-flattening-a-nested-sequence/5236194#5236194

1:47 tomoj: "usually" because you're usually using map?

1:48 sorenmacbeth: amalloy: simple! thanks much

1:48 amalloy: tomoj: that often turns out to be the case, yes

1:48 even if it's at level N-2 instead of level N-1

1:54 sorenmacbeth: actually, my problem is slightly more complex. I need to go from (("a") ("b") ("a" "b")) to ("a" "b" "a b")

1:54 basically a str-join on the inner seqs, then apply concat?

1:55 amalloy: oh, i see

1:55 &(let [s [["a"] ["b"] ["a" "b"]]] (mapcat #(apply str %&) s))

1:55 sexpbot: ⟹ (\[ \" \a \" \] \[ \" \b \" \] \[ \" \a \" \space \" \b \" \])

1:55 amalloy: hm

1:56 &(let [s [["a"] ["b"] ["a" "b"]]] (mapcat #(apply str %) s))

1:56 sexpbot: ⟹ (\a \b \a \b)

1:56 amalloy: bah

1:57 tomoj: don't cat

1:57 amalloy: oh right

1:57 thanks tomoj

1:57 &(let [s [["a"] ["b"] ["a" "b"]]] (map #(apply str %) s))

1:57 sexpbot: ⟹ ("a" "b" "ab")

2:00 sorenmacbeth: awesome

2:03 just need to add a space between the last "ab", so result should be ("a" "b" "a b")

2:03 amalloy: sorenmacbeth: yeah, so use clojure.string/join instead of apply str

2:04 sorenmacbeth: amalloy: thanks again

2:07 perfect, that works :)

2:13 amalloy: hey here's a neat little "macro-do" macro i just put together. anyone interested in either the code or a blog post about it?

2:13 (macroexpand '(macro-do [[f & args]] `(def ~(symbol (str "basic-" f)) (partial ~f ~@args)) [f "test"] [y 1 2 3]))

2:13 (do (do (def basic-f (clojure.core/partial f "test")) (def basic-y (clojure.core/partial y 1 2 3))))

2:16 basically it's c.c.macro-utils/macrolet wrapped up to make it easy to create an anonymous macro and call it once on an arglist

3:22 tsdh: If I have an instance of ITransientVector in Java, how can I remove one given Object o?

3:23 Or, if that doesn't work, how can I remove the element at a given index?

3:23 amalloy: vectors don't like inserts and removes in the middle

3:24 if you are doing that to vectors, there's usually a better solution that involves either not using vectors or not messing around with the middles

3:26 tsdh: amalloy: I use ninjudd's ordered-set lib. That has a class PersistentOrderedSet, that is backed by a PersistentSet and a PersistentVector for the ordering. Now I want to make that support `transient'.

3:27 amalloy: so look at his impl for POS and see how he's doing it?

3:28 tsdh: Oh, indeed. :-)

3:29 amalloy: anyway, good luck. i'm off to bed

3:31 tsdh: Bye

4:05 ejackson: Good Morning Clojuristas !

4:09 tsdh: Hi ejackson.

4:11 If I want to walk some nested structure (vec of vecs), and only pick out some parts, how do I do that?

4:12 Oh, I got it.

4:28 Dranik: hi all!

4:36 clgv: good morning. what is the "default case" in a case statement?

4:36 brehaut: :else

4:36 oh, case?

4:37 raek: clgv: (case :a 1, :b 2, "default here")

4:37 clgv: raek: th

4:37 thx

4:37 tsdh: How to I check if a Var foo is bound? Both (when @foo) and (when foo) error...

4:37 raek: tsdh: what problem is that the solution for?

4:38 normally, when a fn knows about a var, it already exists

4:38 or has to exist

4:38 clgv: \$inc reak

4:38 sexpbot: ⟹ 1

4:38 clgv: ;)

4:39 ups

4:39 \$inc raek

4:39 sexpbot: ⟹ 6

4:39 tsdh: raek: There is (def foo) with no root binding, but if it is bound (to a ref), then some of my fns should record some additional information.

4:40 raek: there's 'bound?' when you have an existing var

4:40 brehaut: tsdh: if you have declared a var (such as (def abc whatever) or (declare abc) ) then (bound? #'abc)

4:41 raek: tsdh: is this done as some initialization, or are those changes going to happen while the application runs?

4:42 tsdh: brehaut: Ouch, that was too obvious. My slime just didn't want to complete it...

4:42 raek: There's an entry function that might establish a binding of that Var.

4:43 brehaut: tsdh: if you need to see if a symbol exists, then you can use (resolve (symbol "abc"))

4:43 but i think if you have reached that stage, you have probably done something wrong

4:44 actually, (resolve 'abc) would be smarter

4:44 tsdh: brehaut: Hm, (bound? foo) errors with ClassCastException: clojure.lang.Ref cannot be cast to clojure.lang.Var.

4:44 Hm, I'll poste the code...

4:44 brehaut: tsdh: you have to var quote it

4:44 #'foo

4:45 tsdh: brehaut: Ah, now that seems to do the trick!

4:46 brehaut: (defn exist-and-bound? [sym] (if-let [v (resolve sym)] (bound? v) false)

4:46 i wouldnt advise using it though

4:47 night

4:47 tsdh: brehaut: Well, it's globally def-ed without root binding, so it's existance is always true.

4:48 raek: tsdh: couldn't it be a solution to just define it as (def foo (ref ...))), and then let functions that want to change the ref do that

4:48 maintaining state wihtout a ref/atom/agent feels non-clojure-y

4:49 clgv: raek: I'd skip the "e" -> clojury ;)

4:49 tsdh: raek: I do exactly that using a (binding [foo (ref {})] ...) in the entry function.

4:50 raek: So the state is only dynamically inside the call stack of the entry fn, and it gets out of it as usual return value.

4:52 raek: (p-apply v1 --> -->) ==> reachable vertices as set. (p-apply v1 --> --> :trace-path true) ==> [<reachable vertices> <shortest paths map>]

4:53 raek: ah, I see.

5:02 hrm. what happens when you leave out a method in a proxy, and then call it?

5:03 ah. java.lang.UnsupportedOperationException

5:03 clgv: is there a general comparison functions that can handle strings, keywords and numbers?

5:04 raek: clgv: compare. but it can only compare things of the same kind

5:04 clgv: raek: there is nothing for the mixed case?

5:05 raek: don't know

5:06 hrm. java.lang.Class is not comparable

5:06 although, (.getName some-class) is

5:07 clgv: what should the order of "foo", :foo and 123 be?

5:07 clgv: raek: e.g. numbers could always be less than keyword which are less than strings

5:08 raek: I could use the string representation of the full classname ;)

5:12 raek: yeah, maybe something like (defn über-compare [x y] (try (compare x y) (catch ClassCastException _ (compare (.getName (class x)) (.getName (class y))))))

5:13 clgv: I would skip the exception part. you could first try on equality of classes

5:13 raek: ,(compare (long 1) (int 1))

5:13 clojurebot: 0

5:13 clgv: lol ok ;)

5:13 maybe except for numbers

5:14 raek: I wouldn't be surpised if, for instance, clojure.lang.PersistentArrayMap and clojure.lang.PersistentHashMap can be compared to each other

5:16 clgv: hmok. the the exception version would be the most general and short one

5:17 raek: but still, I feel bad for using exceptions for control flow

5:18 clgv: yeah, that's why I wanted to remove them in that example

5:19 but I'll use it like that now. It's just for an inspection tree.

5:21 I hated it when my maps/structs... showed there entries in a random order ;)

6:49 tsdh: Wow, (apply (first args) (next args)) has some noticable overhead compared to ((first args)), so that it really pays of to do (let [n (next args)] (if n (apply ...) ((first args))))...

6:55 raek: (apply apply args)

7:27 clgv: can I use robert.hooke for protocol methods?

7:27 the straight-forward approach doesnt work

7:28 (add-hook ...) doesnt complain but the hook itself isnt called either

7:42 Fossi: shouldn't the stable clojure jars be in clojars?

7:55 raek: Fossi: it's in the clojure repo

7:57 tsdh: I started using clojure and functional programming end of last week, and now my notebook makes alarming noises. Is that the way it's got to be? ;-)

8:20 Fossi: hmm, leiningen has those configured, but i'm still getting 5 required artifacts are missing.

8:20 from the specified remote repositories:

8:20 clojars (http://clojars.org/repo/),

8:20 [...]

8:26 ah, i had them as [clojure "1.2.0"] not [org.clojure/clojure "1.2.0"]

8:28 longfin: :)

8:47 tsdh: If I have something like (foo --> -->) where the arrows are functions, how can I achieve a numbering on them. I want to have a map from function to number, but now my problem is that the two arrows are identical, and so the latter --> entry overrides the former --> entry.

8:50 So basically, I need a function that gets a function and returns a copy of that function...

8:52 longfin: intersting...

8:54 tsdh: Hm, maybe I can copy `complement' without the nots?

8:59 chouser: tsdh: 'identity'?

8:59 tsdh: honestly though, I don't really understand your question yet.

9:01 tsdh: chouser: --> is a function. Now I want to create another function that is totally equal with behavior and parameters, but which is that different that I can use both function as different key in a map.

9:01 chouser: heh, ok, I see.

9:02 Chousuke: hmm

9:02 (partial -->) ?

9:02 chouser: Chousuke: there you go.

9:02 actually, that fails I think

9:02 ,(partial +)

9:02 clojurebot: java.lang.IllegalArgumentException: Wrong number of args (1) passed to: core\$partial

9:02 Chousuke: yeah :/

9:02 chouser: ,#(+ %1 %2)

9:02 clojurebot: #<sandbox\$eval3210\$fn__3211 sandbox\$eval3210\$fn__3211@22d4f0>

9:03 chouser: tsdh: So there is that, but I'm suspicious of a design that requires such contortions.

9:04 tsdh: chouser, Chousuke: Oh, wait. Instead of using a map fun -> number, I can put the number as metadata on the function, and (with-meta) returns a new function then, right?

9:04 clgv: ,(leftfn [(f [& args] (map-indexed (fn [i t] (with-meta t {:index i})) args)) (g [x] (inc x))] (f g g g))

9:04 clojurebot: java.lang.Exception: Unable to resolve symbol: leftfn in this context

9:04 clgv: ,(letfn [(f [& args] (map-indexed (fn [i t] (with-meta t {:index i})) args)) (g [x] (inc x))] (f g g g))

9:04 clojurebot: (#<sandbox\$eval3215\$g__3220 sandbox\$eval3215\$g__3220@bd648a> #<sandbox\$eval3215\$g__3220 sandbox\$eval3215\$g__3220@13b905> #<sandbox\$eval3215\$g__3220 sandbox\$eval3215\$g__3220@d82990>)

9:05 tsdh: clgv: I guess I go with clojure.walk/prewalk, but thanks for that superb tip anyway.

9:07 clgv: tsdh: just an example. and I wanted to see what the bot does with it

9:08 tsdh: Was'n there some syntax shugar for accessing a maps value by key :foo?

9:09 s/shugar/sugar/

9:09 sexpbot: <tsdh> Was'n there some syntax sugar for accessing a maps value by key :foo?

9:09 tsdh: Wow, there's a bot for everything...

9:11 pjstadig: i like it spelled shugar, but that's just me

9:13 tsdh: :-)

9:16 choffstein: Hey all, I have a question. I come from a Ruby background where it is easy to create custom behavior of standard classes using monkey patching. I am new to clojure, and I would expect that monkey patching isn't possible (partially due to the fact that clojure isn't object focused and partially because it sits on the JVM). What I am really looking to do is come up with a way to have a method run anytime an Exception

9:16 occurs (e.g. an Exception object is created). In Ruby I could just monkey-patch the Exception class and just require my library and have things taken care of. Any ideas in clojure?

9:17 It seems like it may be possible with Extension methods in Java 7?

9:17 stuartsierra: choffstein: You can set a default "uncaught exception handler" on threads in Java.

9:18 choffstein: stuartsierra: Which works, but I even want to take action if the exception is caught

9:18 stuartsierra: Then you need to alter the code that does the catching.

9:20 choffstein: Yeah, that is what I figured. I'm assuming I need to drop to the Java level?

9:20 stuartsierra: Not at all.

9:20 That is, unless you want to alter the behavior of compiled code that you didn't write.

9:21 Which is a very risky idea.

9:22 choffstein: Yeah ... I think I might just have to acknowledge that I can't do what I want. Basically, I am trying to replicate ruby's exceptional plugin (getexceptional.com) for my clojure app. It's super easy in Ruby because of monkey patching. I think I need to step back from the 'ruby frame of mind' and tackle the problem with a clojure mind-set.

9:23 Fossi: somebody already used ring/jetty with the proxy servlet that ships with it?

9:23 clgv: choffstein: I would like the idea to be able to get a debug-repl run in the place where an exception is thrown^^

9:24 Fossi: i've got a snipplet of web.xml config like http://docs.codehaus.org/display/JETTY/Asynchronous+Proxy+Servlet , but no idea how that get's set on the jetty classes

9:25 stuartsierra: choffstein: There are debugging and profiling tools that hook into the JVM that probably offer similar functionaliity.

9:28 choffstein: cigv: I was really just trying to catch all exceptions on creation, whether caught or not, and send them to either a log or an amazon s3 bucket (or both)

9:28 but dropping to a debug-repl would be awesome too

9:30 stuartsierra: IDEs like Eclipse may also offer these features.

9:32 choffstein: Well, I am really looking to use it as a deployed tool. For example, when my web service is running, on my 'status' admin page that tells me which servers are up and spinning, I also want to see a log of all exceptions raised

9:32 whether they were caught or not

9:32 stuartsierra: choffstein: Again, look at JVM-level stuff, or application containers like JBoss/Tomcat/Glassfish. I'm sure something like this exists.

9:32 choffstein: I'll check it out. Thanks.

9:33 stuartsierra: 'welcome

10:15 * abedra drops a ping

10:15 * abedra drops a pin

10:15 * wooby sneezes

10:20 stuartsierra: gazhundheit

10:27 TimMc: stuartsierra: I came across your trick for unit testing private defns -- thanks!

10:28 stuartsierra: 'welcome

10:29 I don't think I can claim credit for @#' though.

10:29 timvisher: hey all

10:29 does anyone have anything they'd suggest for trying to learn to think recursively?

10:30 recursion is a little like functional programming for me in that I often can understand a solution presented to me, but at the same time can't get to that solution on my own given the same problem

10:31 stuartsierra: Think back to Algorithms 101 — what are the loop invariants?

10:31 What changes at each iteration of the loop?

10:31 The stuff that changes will be arguments to the recursive function (or loop/recur in Clojure).

10:32 timvisher: stuartsierra: that revelation just hit me the other day

10:32 that fp uses recursion not because it's inherently attracted to elegance but because it's a natural way to do iteration without side effects

10:32 what I mean more is how to approach a problem recursively

10:33 in other words, in the SICP course they say that the key to recursion is wishful thinking

10:33 you try to think of how they problem would look if it was easy to solve

10:33 and then you see if you can reduce the problem in steps towards that degenerative case and then solve the simpler problem

10:33 goodmike_mh: timvisher: Your requirements match the raison d'etre of The Little Schemer

10:33 timvisher: it's that series of decompositions that I struggle to see

10:34 goodmike_mh: i.e. learning to think recursively?

10:34 goodmike_mh: yes

10:34 dnolen: timvisher: Little Schemer, Seasoned Schemer are great for getting comfortable w/ recursive thinking. There's more to recursion than looping. mutual recursion, continuation passing style are useful bits to understand as well.

10:34 timvisher: mmm

10:35 they've been on my reading backlog for forever. Perhaps it's finally time to pick them up...

10:35 TimMc: timvisher: HtDP teaches recursive thinking via recursive data structures. (Free to read online.)

10:36 timvisher: TimMc: nice

10:36 thanks for that pointer

10:36 i'm wondering if I'm not just coming up upon my own inadequacies. SICP seems to do a pretty good job of trying to slowly encourage the recursive decomposition of problems.

10:36 TimMc: It's the textbook for my school's Fundamentals of Computer Programming course.

10:36 timvisher: it may just be that I need to study recursive solutions over and over again

10:37 TimMc: timvisher: Do you have a lot of imperative programming background?

10:37 timvisher: all i've ever done is Algol based languages (Java, Groovy, PHP, etc.)

10:37 Dabbled in ELisp but Clojure's my chosen tool for teaching myself FP

10:38 going through SICP right now (the text) and I'm running into a lot of trouble as they go into recursion.

10:38 again, not so much the understanding of the solution when presented but being able to get there on my own.

10:38 TimMc: Yeah, so you're just having difficulty with the unlearning. :-)

10:38 timvisher: figures

10:38 i always want the answer to be 'read this paragrah and it'll all click!'. :)

10:39 alright, well on I will forge

10:39 TimMc: It's pretty common, from what I hear.

10:39 You can teach (e.g.) middle school kids either functional or imperative programming with pretty much equal ease.

10:40 paraseba: is there anything done to help declaring macros similar to defn? I mean to get the different parts of the passed forms: metadata, declarations for each arity, etc.?

10:40 TimMc: It's harder to switch styles the first time you do it. Later, you'll be able to think in both.

10:40 paraseba: name-with-attributes in c.c. is the closer I can find, but it doesn't help much

10:42 ideally, given defn like arguments I would want a name with all corresponding metadata, and a list of declarations with one element for each arity

10:43 It's pretty easy to write, but I can't believe it's not done already in clojure or c.c.

10:45 dnolen: paraseba: ?

10:45 (defmacro foo ([a b] nil) ([a b c] nil))

10:45 (meta #'foo)

10:45 {:macro true, :ns #<Namespace user>, :name foo, :file "NO_SOURCE_PATH", :line 9, :arglists ([a b] [a b c])}

10:47 paraseba: sorry, I'm not explaining it right. I want to declare a macro that will define a new function, with given name, metadata and declarations. The macro will take the same arguments as defn

10:48 the macro will define the function, using the declarations passed but adding some extra stuff

10:49 imagine something like (my-defn f "my doc" {:my :meta} ([a] nil) ([a b] nil) {:more :meta})

10:49 I have to handle all possible forms of defn declarations (single arity, multiple arity, no doc, no meta, two meta maps, etc.)

10:51 clgv: is there a command like partition that includes the remaining elements as last smaller list?

10:51 TimMc: clgv: partition-all

10:51 clgv: ,(partition 5 (range 23))

10:51 clojurebot: ((0 1 2 3 4) (5 6 7 8 9) (10 11 12 13 14) (15 16 17 18 19))

10:51 clgv: oh thx :D

10:51 paraseba: clgv: you almost always want to use partition-all

10:52 TimMc: amalloy_: Early bird gets the worm.

10:53 fbru02_: paraseba: i haven't seen it anywhere in core/or contrib all the times i have seen it is like this (defmacro generatefn [args & body] ~args ~@body))

10:53 paraseba: welcome to irc btw ! :)

10:54 defmacro `(defn generatefn [args & body] ~args ~@body))

10:55 paraseba: fbru02_: thanks for the welcome .. I'm trying new forms of not getting work done

10:56 fbru02_: yes, the problem is that it doesn't handle defn like arguments correctly. In my case I need to wrap function body with some stuff, that's why I need to get every arity declaration

10:56 fbru02_: and also, I don't want to loose doc and metadata information

10:57 fbru02_: paraseba: i kind of agree it would be nice to have that in core/contrib, maybe you should open a enhancement and see if people like it provided you can find a goodname for the macro

10:58 paraseba: which i cannot think of , at least now

10:59 paraseba: fbru02_: it would be a nice addition to c.c.macro-utils or c.c.def if it's not there already

11:02 ev4l: according to the standard clojure code conventions when should i give a function a bang sign at the end of its name? (judging by the code i've read so far, only when the function performs some side effect on a var)

11:02 . Are there any more cases?

11:03 paraseba: by the way, any idea of why defn supports two attribute maps? why the first one is not enough?

11:04 stuarthalloway: official word on bang: for fns that are not safe in an STM transaction

11:05 TimMc: stuarthalloway: Unless the name clearly implies side effects?

11:05 stuarthalloway: TimMc: honestly I don't think the bang idiom is that important

11:06 but the STM interaction was the original motivation for the bang fns in core

11:06 tsdh: Why does (clojure.inspector/inspect foo) throw a ClassNotFoundException, but (clojure.set/difference s1 s2) can be called? The clojure.inspector classes are contained in the clojure 1.2.0 jar that leiningen fetched me...

11:07 ev4l: stuarthalloway: thanks! it's funny to have the question answered to the guy who wrote the book i have opened here along with the irc client :D

11:07 stuarthalloway: all the best stuarts hang out here and answer book questions, right stuartsierra?

11:08 TimMc: stuarthalloway: Ah, interesting.

11:08 ev4l: s/to/by

11:08 sexpbot: <ev4l> stuarthalloway: thanks! it's funny by have the question answered by the guy who wrote the book i have opened here along with the irc client :D

11:09 ev4l: (haha faster than you bot... suck it xD)

11:10 wooby: tsdh: (require 'clojure.inspector) first

11:14 tsdh: wooby: But why do I have to require clojure.inspector, but I can access clojure.set functions qualified without doing so?

11:16 raek: tsdh: they are loaded automatically in versions up to 1.2, iirc

11:16 tsdh: Ok, thanks.

11:17 raek: an old detail that you should not rely upon

11:17 I think that was from the times before require and firends

11:18 abedra: where did the other stuart dissapear to?

11:19 wooby: tsdh: Because Clojure requires set for you when you start it up.

11:20 goodmike_mh: tsdh: wooby and I are not sure exactly why. sets are a major seq collection type, even though they are defined outside core

11:21 Not all libraries are quite created equal

11:23 TimMc: abedra: Quit about 50 minutes ago.

11:23 raek: since this commit clojure.(zip|xml|set) are not loaded automatically anymore

11:24 TimMc: tsdh: If it isn't in clojure.core or java.lang, you need to explicitly require, use, or import it.

11:25 Dantas: Hi everyone !!! One , newbie, question !!! - The commute form is executed in two phases. is the last phase , commit phase, will be executed in atomic way ?

11:25 tsdh: TimMc: Yes, except it's in clojure.set, in what case I can call it qualified.

11:25 Ok, gotta run.

11:49 choffstein: anyone know a good write-up on working macros in with special forms? I am trying to create a macro around try/catch but am having some trouble. Basically, I want to inject code to be executed when I use 'my-try' instead of just 'try'.

11:52 rmarianski: with-open might be a good candidate to look at for that sort of thing

11:53 not really a write up, but you might be able to do the same sort of thing

11:54 choffstein: thanks guys

11:54 err...guy

12:03 Fossi: how do you inspect java objects again?

12:04 i want to see the methods

12:04 Dantas: The COMMUTE form is executed in two phases , right ? . is the last phase , called commit phase, synchronized ? "LOCK commute fn UNLOCK"

12:11 choffstein: Can someone show me an example of a macro that takes a list of functions and executes each function? Is it possible? Basically ... I am looking for the 'do' special form as a macro...

12:13 amalloy: choffstein: doseq?

12:13 or dorun?

12:13 Fossi: clojure.contrib.repl-utils/show

12:15 choffstein: I'll check those out. Thanks amalloy.

12:16 Chousuke: choffstein: you mean like (run foo bar whatever) expanding to (do (foo) (bar) (whatever))?

12:17 choffstein: chousuke: yeah, exactly. I'm trying to figure out how to do that.

12:18 Basically, I am trying to create a wrapper around 'try' to inject some code ... but it isn't going well :D

12:18 amalloy: (defmacro run [& fs] (cons 'do (map list fs))) :P

12:19 would bring Chousuke's example to life

12:19 Chousuke: amalloy: you were just a few keypresses faster than me :P

12:20 I was counting my parens :( damn irc for not having paredit

12:20 amalloy: Chousuke: i'm working on a sexp-balancer for sexpbot

12:20 choffstein: awesome. thanks!

12:20 amalloy: by which i mean, complaining about not having one and getting brehaut to write the parser for me

12:26 choffstein: Okay, I definitely don't know enough clojure to do what I am trying to do :D

12:27 Fossi: amalloy: thanks

12:28 choffstein: Any thoughts on how to intercept a 'catch' clause and add some code to it?

12:32 amalloy: choffstein: let's say the user calls your macro with the & arglist '(/ 1 0) 'x '(catch Exception _ nil)

12:32 you can find all the catches in that list with (filter (comp first #{'catch}) arglist)

12:33 er, that's backwards. (comp #{'catch} first)

12:33 then you can mess around with them however you want and put them back in

12:33 choffstein: wow. That ... that might be perfect.

12:34 Fossi: any ring'ers herre?

12:34 i just wanna add a second servlet to a jetty

12:35 and i miss add-servlet! from compojure

12:38 amalloy: TimMc: what worm did i not get? i couldn't tell

12:38 or, i suppose, did i get

12:38 TimMc: amalloy: I got to tell someone about partition-all!

12:38 And you were probably still asleep.

12:39 amalloy: you bet i was

12:44 TimMc: Damn, I forgot to ask clgv why s/he wanted partition-all. I still haven't had a need for it

12:44 I suppose it could be useful for layout logic.

12:44 jkkramer: is http://dev.clojure.org/display/doc/Getting+Started the current, official link to give to a clojure newbie?

12:48 stuarthalloway: jkkramer: no one person probably knows if that is all up to date

12:48 Dantas: The COMMUTE form is executed in two phases , right ? . is the last phase , called commit phase, synchronized ? "LOCK commute fn UNLOCK"

12:49 jkkramer: stuarthalloway: at the very least, the assembla one is no longer official, right?

12:49 stuarthalloway: right

12:49 and please suggest (or make) edits in Confluence if you see something wrong

12:50 TimMc: Dantas: I don't know if locks are involved, per se.

12:50 stuarthalloway: Dantas: that is implementation detail

12:51 jkkramer: will do. getting a friend setup this weekend

12:51 stuarthalloway: what you can count on is that readers require no locks

12:51 er, should say that readers can *never* block

12:52 any locks down in the STM, if they exists, are about STM resources, not about your refs

12:52 Dantas: stuarthalloway: yes, but semantically, could i think that the commit phase is atomic ? ( sorry for my english )

12:53 TimMc: Dantas: Here is an excellent article on STM in Clojure: http://java.ociweb.com/mark/stm/article.html

12:53 stuarthalloway: transactions are always atomic, across the set of refs transacted upon

12:53 TimMc: The latter part is all implementation details, but there is a good high-level description as well.

12:54 Dantas: TimMc: Thanks, stm is really cool. a easy way to create concurrent applications

12:54 an*

12:55 TimMc: Dantas: Just watch out for write skew, that's the only thing that isn't obvious from most of the descriptions I've seen.

12:56 Dantas: stuarthalloway: thank you

12:56 TimMc: Thanks

12:57 TimMc: If you're not sure about commute yet, you can avoid it easily.

12:58 Dantas: TimMc: according the clojure documentation, commute is performed in two phases. the second phase is where the ref value will be changed

12:59 so, i dont want to understand the implementation detail, only if this operation is atomic ! this way avoid race conditions

12:59 TimMc: I don't understand that aspect of commute yet myself.

13:00 Dantas: if i understand right, stuarthalloway said that they are atomic

13:00 TimMc: My understanding is that commute allows some more interleaving of transactions by rescheduling commutes.

13:00 stuarthalloway: commute is for when you don't care when the change happens

13:00 TimMc: ...but I'm really not sure.

13:00 stuarthalloway: e.g. commute is for "add 100 to account"

13:02 TimMc: stuarthalloway: I assume commute should not be used when you want to keep consistency constraints between refs?

13:02 stuarthalloway: probably right

13:03 Dantas: i asked about that cause i came from shared state way. so commute is really new from my background !

13:07 stuarthalloway: commute is still atomic, but you might not know its result

13:08 Fossi: ring/jetty is driving me crazy :/

13:10 Dantas: stuarthalloway: but, after commit phase, the commute result is the same located in the memory

13:10 ??

13:10 stuarthalloway: Dantas: the return value of your call to commute is not necessarily the final result

13:11 because commute says "feel free to retry this independently of everything else"

13:16 Dantas: stuarthalloway: TimMc thank

13:16 cya

13:17 Fossi: anybody know if it's even possible to use another servlet with ring?

13:17 the leiningen task seems to have only one of them as well

13:17 and everything i try resets the original servlet

13:19 * hugod is still cursing at 1.3.0-testbuild1-SNAPSHOT

13:19 ndimiduk: Fossi, another servlet, or another web container?

13:20 Fossi: ndimiduk: just another servlet

13:20 one jetty is fine

13:30 choffstein: is there a way to add an element to the back of a list?

13:31 this seems like an easy google ... but I just can't find it...

13:33 ataggart: not without rebuilding the list

13:34 spewn: choffstein: If you were using a vector, conj would append to the end. Is there are reason you're using a list instead?

13:34 stuarthalloway: hugod: what is testbuild1-SNAPSHOT?

13:34 choffstein: spewn -- it's in a macro. Basically, I have something like (1 2 3) and (4 5 6), and want to create (1 2 3 (4 5 6)). It just seemed easier to add (4 5 6) to the back of (1 2 3) rather than three cons.

13:35 TimMc: choffstein: concat?

13:35 spewn: TimMc: Wouldn't that make (1 2 3 4 5 6)?

13:35 Chousuke: choffstein: are you doing that in a macro?

13:35 choffstein: Chousuke: Yes.

13:35 Chousuke: then you might be able to use splicing

13:35 amalloy: choffstein: it's awkward for a reason: adding to the back of an immutable linked-list is not cheap

13:35 TimMc: spewn: Yes, I suppose so.

13:36 amalloy: but Chousuke is probably right

13:36 choffstein: amalloy: I know ... you have to iterate the list.

13:36 Chousuke: ,(let [a '(1 2 3)] `(1 2 3 ~a ~@a))

13:36 TimMc: spewn: Unless you wrap it first. :-)

13:36 clojurebot: (1 2 3 (1 2 3) 1 2 3)

13:36 hugod: stuarthalloway: org.clojure:clojure:jar:1.3.0-testbuild1-SNAPSHOT

13:36 on oss snapshots

13:36 choffstein: hmm ... that might work.

13:36 amalloy: Chousuke: fwiw that's just concat under the covers

13:37 stuarthalloway: hugod: do you have projects that are resolving dependencies to that

13:37 Chousuke: amalloy: yeah, but it's a bit simpler to use

13:37 amalloy: it's totally reasonable to use inside a macro though, cause the lists are going to be short (the user actually typed them in!)

13:37 choffstein: Yeah, the list is only 3 elements long...

13:37 stuarthalloway: hugod: the goal of releasing alphas is for you to have non-snapshot targets.

13:37 hugod: I depend on enlive, which uses a dependency range for clojure, which pulls it in

13:37 stuarthalloway: If that isn't working for you, but something could be fixed to make it better, would like to do it

13:38 choffstein: Okay, maybe I can get some help then ... because I can't figure out how to splice this in. Basically, it comes down to: (->> catch-clause# (list 'println `(. ~exception-name# toString)) (list 'do) (list ~@catch-phrase#))). It's the last part I am having trouble with...

13:38 TimMc: jkkramer: Any stable releases of loom?

13:38 hugod: my dependencies are all clojure-1.2.0

13:39 amalloy: you can't splice a gensym#

13:39 jkkramer: TimMc: not yet. i may still rewrite a bunch of the underlying code. e.g., using deftype instead of defrecord

13:39 __name__: jo, mc tim, wassup?

13:39 hugod: stuarthalloway: is it possible to remove the testbuilds?

13:39 choffstein: amalloy: oh...didn't know that. Hmm ... (new to clojure, if you couldn't tell :))

13:39 amalloy: unless you have two levels of backticks in there somewhere, and only showed one?

13:39 stuarthalloway: hugod: just pinged stuartsierra and cemerick to ask that very question

13:39 jkkramer: TimMc: I don't plan on changing the API much, though

13:39 choffstein: Nope. Just one amalloy.

13:39 hugod: thanks

13:40 amalloy: choffstein: gensyms# only exist inside the expanded scope - you can't do things like splice them while expanding, because you don't know what they are

13:40 choffstein: amalloy: ah, that makes sense.

13:41 Gotta get better at really understanding what exactly is going on with macros. Practice, practice, practice i guess...

13:41 TimMc: wassup, __name__?

13:41 amalloy: actually i don't understand why you have a gensym# outside of any backtick-scopes. that can't be working ro you

13:41 for

13:42 hugod: stuarthalloway: btw, I would use a 1.2.1 for pallet - users have been hit before with the stackoverflow keyword issue

13:42 __name__: TimMc: Weekend :-)

13:42 stuarthalloway: hugod: working on the patch for it now

13:42 hugod: :)

13:42 stuarthalloway: but would also love to know what we need to do to get people using 1.3 branch :-)

13:43 hugod: maven exclusions should be viable as a workaround

13:43 choffstein: amalloy: https://gist.github.com/866348

13:43 hugod: stuarthalloway: exclusions don't seem to work

13:43 stuarthalloway: yikes

13:44 technomancy: exclusions in maven must be specified for every single dep that pulls clojure in

13:44 choffstein: amalloy: warning -- I am very green on macros. This is my first macro ever.

13:44 technomancy: (but global exclusions were just added to Leiningen this morning.)

13:44 amalloy: choffstein: yeah, that's never going to work. try replacing it with (defmacro my-try [& args] (let [thing# args] thing#))

13:44 choffstein: amalloy: but basically, I am trying to deconstruct a catch clause, inject some code using a do, and reconstruct it.

13:44 amalloy: it works now...

13:44 TimMc: jkkramer: Leiningen is going to yell at me if I try to make a non-SNAPSHOT release. :-P

13:44 amalloy: oh hm

13:44 &(let [x# 1] x#)

13:44 sexpbot: ⟹ 1

13:45 amalloy: hah, i guess # is legal in symbol names

13:45 hugod: technomancy: does that work when you dependencies are themselves using dependency ranges?

13:45 TimMc: &x#

13:45 sexpbot: java.lang.Exception: Unable to resolve symbol: x# in this context

13:45 choffstein: oh, does it work for all the wrong reasons?

13:45 amalloy: but don't do it outside of backtick scopes - they're usually used for gensumming

13:45 symming

13:45 choffstein: yeah...I was trying to gensym

13:45 TimMc: &(quote x#)

13:45 sexpbot: ⟹ x#

13:45 technomancy: hugod: that's orthogonal, I think.

13:45 TimMc: &`x#

13:45 sexpbot: ⟹ x__17725__auto__

13:45 technomancy: exclusions don't involve versions

13:46 choffstein: Lot's to learn here...

13:46 hugod: stuarthalloway: I shalln't switch pallet to 1.3 until it is released - I don't need the 1.3 features, and can wait for stability

13:47 technomancy: is that in lein HEAD?

13:47 pjstadig: people really need to respond to the ML thread instead of coming out of the woodwork after a decision has been made :)

13:47 hugod: I can't post on the dev list

13:47 amalloy: &(let [[_ e-class e-name & e-ret :as catch-clause] '(catch Exception _ x)] `(catch ~e-class ~e-name (do (println ~e-name) ~e-ret)))

13:47 technomancy: hugod: yeah

13:47 sexpbot: java.lang.SecurityException: You tripped the alarm! catch is bad!

13:48 danlarkin: yay

13:48 amalloy: choffstein: https://gist.github.com/866354 ?

13:49 amalloy: oops, i missed a @ in there. gist updated

13:50 and i guess i don't need the :as at all since i'm not using it, but you might want it for some reason

13:50 choffstein: amalloy: thanks, I'll take a look at that guy

13:52 amalloy: basically, I am trying to iterate through all given catch clauses in a try/catch/finally and inject some code. So I was trying to use gensym to make sure I didn't get any symbol clashing

13:52 but I guess I don't need to, since the let's make everything local, huh?

13:55 amalloy: right, as long as you put them in the *macro* scope and not the expansion scope

13:55 choffstein: expansion scope being `?

13:55 I think I am getting this. Come on enlightenment, hit me!

13:56 amalloy: choffstein: the difference is between (let [x 1] `(+ ~x ~user-arg)) and `(let [x# 1] (+ x# ~user-arg))

13:57 in the former, x belongs to your macro, and no trace of it will ever show up in the expansion

13:57 in the latter, you want to create a new binding in the expansion scope, which will be used in the user's code - there, you have to avoid clashing with one of their names

13:58 choffstein: amalloy: Awesome. That makes perfect sense.

13:58 jkkramer: TimMc: hmm, I guess I could cut a 0.1 release. I was also going to take out the ubigraph stuff, which adds a dependency on apache xml-rpc. I'll see about doing that this weekend

13:58 TimMc: jkkramer: That would be awesome.

13:59 choffstein: amalloy: one quick last question, if you don't mind. In my macro, I am trying to map over all the catch-clauses ... how can I use splicing in my anonymous function? e.g. line 6 @ https://gist.github.com/866348 -- which obviously doesn't work, but I don't know how to make it work.

13:59 TimMc: No rush on my end -- my project is very new, and the only known dependent is a homework assignment I haven't really started on. :-P

14:01 choffstein: Ah, whoops, didn't see those ~ on arglist

14:01 amalloy: choffstein: it obviously doesn't work? looks reasonable to me

14:01 ah

14:01 nor did i :P

14:02 choffstein: Well, it was obvious it didn't work to me because I thought I understood what the hell I am talking about, but I obviously don't :P

14:02 Thanks for all the help. I'll keep studying this bad boy.

14:02 amalloy: you can avoid the (first arglist) with some destructuring: (defmacro my-try [execute-clause & more] ...)

14:03 stuarthalloway: hugod, pjstadig, danlarkin, technomancy, + anyone else wanting 1.2.1: please make sure http://dev.clojure.org/jira/browse/CLJ-754 looks right

14:03 choffstein: haha. love some good old refactoring :)

14:03 amalloy: refactoring is my favorite vice. improve old code instead of writing new

14:08 tsdh: Is there something like a this pointer for functions?

14:08 choffstein: If I am writing a library that would have global configuration, what is the clojure way of doing it? For example, in ruby, we would use a yaml file, or something like that. How do you do it in clojure?

14:09 tsdh: choffstein: Why not a possibly nested map?

14:09 spewn: stuarthalloway: Could we get https://github.com/clojure/clojure/commit/6d300332f810a68869c11ddfcc55f4439b70fdb3 ? Especially since http://clojure.org/special_forms assumes def can take a docstring.

14:09 technomancy: stuarthalloway: excellent; thanks. giving it a go.

14:10 amalloy: choffstein: yeah, just a hashmap

14:10 write it to a file, read it in, you're good to go

14:10 choffstein: And just have the library user pass it in?

14:10 stuarthalloway: spewn: probably not. If we start doing enhancements on a past branch I don't know where to stop

14:11 also makes the documentation more confusing, not less

14:11 amalloy: i don't think that's necessary. have your library read from "myconfig.clj", and if they want it to behave differently they can write the file before calling you

14:11 just like a yaml

14:11 pjstadig: stuarthalloway: you stop when you don't have a bug that has no user workaround

14:12 stuarthalloway: pjstadig: works for me, and excludes the suggested enhancement by definition

14:13 proposed by spewn a few minutes ago

14:13 pjstadig: stuarthalloway: agreed probably not bugfix worthy

14:20 tsdh: How can I access the currently running function's metadata in its own body in the presence of more than one instances of that function, which hinders referring to it by its name?

14:23 amalloy: tsdh: that has no particular meaning, because anything nontrivial is nested within many layers of functions

14:24 raek: ,((fn f [] (meta f)))

14:24 clojurebot: nil

14:24 raek: ,(^{:a 1} (fn f [] (meta f)))

14:24 clojurebot: {:a 1}

14:25 raek: tsdh: note that metadata on a function object and metadata on a var holding it is not the same thing

14:26 tsdh: I think, I can solve my problem in a better way. :-)

14:49 simard: is there a unique? predicate in clojure ? I would do: (defn unique? [coll x] (= nil (second (filter #(= % x) coll))))

14:49 ieure: What’s the recommended way to produce XML in Clojure? It seems that clojure.xml/emit is semi-deprecated.

14:49 clojure.contrib.lazy-xml/emit

14:49 Perhaps?

14:49 amalloy: ieure: prxml?

14:50 ieure: amalloy, Seems reasonable, I’ll check it out.

14:50 amalloy: it's pretty convenient and flexible. it's what i used the one time i needed to make xml

14:50 ieure: I guess I have to rebind *out* to capture it as a string.

14:50 amalloy: ieure: i think so, yeah. but you have with-out-str, so...

14:56 brehaut: simard: my best effort so far is (defn unique? [s x] (-> (get (group-by identity s) x) next nil?))

14:58 amalloy: (= 1 ((frequencies s) x))

14:58 brehaut: bah :P

14:58 * brehaut feels a little stupid right now

14:59 amalloy: meh. my version is wasting a lot of computational effort on data you don't care about

15:01 simard: yup

15:01 anything wrong with it ?

15:01 it's lazy, right ?

15:02 choffstein: Any thoughts on what I am doing wrong here? (def l '(#(+ 1 %) #(+ 2 %))) / (apply (first l) 3)? I am getting a "clojure.lang.Cons cannot be cast to clojure.lang.IFn" ... which makes me think I am not actually creating a list of anonymous functions like I thought I was...

15:03 amalloy: choffstein: use [x y] instead of '(x y)

15:03 choffstein: *slaps face*

15:03 really?

15:04 amalloy: simard: yes, it will stop early if it finds any duplicates, but it can't really be lazy because it will have to search the whole list to confirm that there are no duplicates

15:04 TimMc: So, fail-fast.

15:04 simard: amalloy: well, yes that's as good as I can do I guess

15:04 amalloy: choffstein: only old common-lisp codgers use '(anything) :). when you want to bundle up some data objects into a list, vectors are usually the way to go

15:04 TimMc: But all solutions have a best worst-case of O(n)

15:05 choffstein: amalloy: i'll remember that. thanks.

15:05 TimMc: Er... "Best solution will be O(n)."

15:07 choffstein: Okay ... now i'm just getting stupid here. How can I pass a function if I don't create a function object? Pass the symbol? I wouldn't expect apply to work on that...

15:07 raek: simard: I would write (= nil (second ...)) as (not (next ...))

15:07 brehaut: ,(let [myinc (fn [x] (+ 1 x))] (map myinc [1 2 3]))

15:07 clojurebot: (2 3 4)

15:08 brehaut: choffstein: does that make sense?

15:08 raek: then it also works for checking the uniqieness of nil

15:08 choffstein: brehaut: yeah, that makes perfect sense...but you are creating a function object.

15:08 simard: raek: nice, I'll change that

15:08 choffstein: brehaut: basically, I am trying to construct a list of dispatch functions

15:08 brehaut: so I construct the list, and on a certain event, call all the functions

15:09 brehaut: so for instnace you have [inc dec], and then later you want (map #(% arg) my-fns) ?

15:10 choffstein: yeah

15:10 TimMc: JUXT

15:11 brehaut: TimMc: probably :)

15:11 choffstein: ##(let [fs (juxt inc dec)] (fs 1))

15:11 sexpbot: ⟹ [2 0]

15:11 TimMc: ,((juxt [* + - /]) 4 6)

15:11 clojurebot: java.lang.IllegalArgumentException: Wrong number of args (2) passed to: PersistentVector

15:12 choffstein: brehaut: but let's say I have a ref to an empty vector -- how do I add 'inc' and 'dec' to that vector?

15:12 TimMc: bah

15:12 ,((juxt * + - /) 4 6)

15:12 clojurebot: [24 10 -2 2/3]

15:12 brehaut: choffstein: (def fs (ref [])) (dosync (alter rs conj inc dec))

15:13 ieure: Next question… Is there a simple way to create a WAR file from a Leiningen/Compojure project?

15:13 TimMc: ieure: I think there's a lein-war plugin.

15:15 brehaut: choffstein: (def ref-juxt [r] (fn [& args] (dosync (map #(apply % args) @r)))) ; the dosync is kind of optional there

15:15 choffstein: brehaut: yeah, I have that. But I am trying to pass in a variable function. So something like: (defn add-dispatch [fn] (dosync (alter *dispatchers* conj fn))).  ... or something like that

15:16 jcromartie: how does dosync work in the context of a lazy seq (map)

15:16 brehaut: choffstein: what do you mean 'variable function'?

15:16 choffstein: brehaut, so I could call (add-dispatch 'inc) or (add-dispatch #(+ 3 %))

15:17 brehaut: you dont need to quote in there

15:17 err

15:17 inc

15:17 ieure: TimMc, Beautiful, thanks.

15:17 brehaut: (add-dispatch inc) would work just fine

15:17 amalloy: brehaut: in happened to work in context

15:17 brehaut: amalloy: wait what?

15:17 amalloy: as in, "in that instance/function-call"

15:17 choffstein: brehaut: Really? Herm. Okay ... thanks.

15:18 amalloy: even if you meant inc, in was a viable substitute, is what i meant

15:18 brehaut: choffstein: you want to pass the fn not the smybol right?

15:18 choffstein: right

15:18 stuartsierra: stuartsierra has returned!

15:19 stuarthalloway: stuartsierra: so glad you are back, I have work for you :-)

15:20 stuartsierra: stuarthalloway: the correct response is "And there was much rejoicing."

15:21 hiredman: and snicker about pictures where people grab their chins

15:21 snickering

15:22 stuarthalloway: stuartsierra: specifically, could you look at http://dev.clojure.org/jira/browse/CLJ-755

15:22 which is, in fact, about maven :-)

15:23 choffstein: holy crap, my code works.

15:24 brehaut: choffstein: well done

15:24 choffstein: brehaut: thanks for the help

15:24 stuartsierra: stuarthalloway: mvn -Pdistribution package

15:24 choffstein: clojure is blowing my mind.

15:25 I thought meta-programming in ruby was cool. But damn ... I think I am starting to understand what all the hub-bub about macros is...

15:25 gregh: macros are "hey! I can write bits of a compiler."

15:26 stuarthalloway: stuartsierra: did that run on Hudson? where do I grab the artifact?

15:26 jweiss: anyone here use clojure.contrib.logging? i have a potential fix where stack inspection seems to work at least for java.util.logging. More informative than just printing the name of the logger. i'd like to submit it but havne't signed the CI yet.

15:27 stuartsierra: stuarthalloway: It doesn't run on Hudson by default. I can change that.

15:27 stuarthalloway: stuartsierra: that would be great, if not a lot of trouble

15:27 stuartsierra: no problem

15:27 stuarthalloway: otherwise people have to get the release build built from my laptop, which is gross

15:27 jweiss: is this the current CA? https://github.com/weissjeffm/webui-framework/blob/unify/src/com/redhat/qe/logging.clj

15:27 doh

15:28 stuarthalloway: jweiss: logging became its own top-level project this morning; https://github.com/clojure/tools.logging

15:28 stuartsierra: stuarthalloway: Just for release builds, right? Not snapshots.

15:28 stuarthalloway: stuartsierra: right. and with instructions for where I go to grab the bits

15:30 stuartsierra: is inclusion of the file "clojure.iml" by design?

15:31 stuartsierra: yes. I think I tried to include everything that was included in previous releases.

15:31 jweiss: stuarthalloway: good timing then :) so do i still need to sign the CA to submit a patch (I see the new project could still use it)

15:31 stuarthalloway: jweiss: yes

15:31 jweiss: was that the right url for it?

15:31 stuartsierra: FYI, the definition of what goes in the ZIP is in src/assembly/distribution.xml

15:32 stuarthalloway: jweiss: yes

15:33 jweiss: great, thx

15:38 i am kinda surprised no one else has wanted to see ns and fn name in their logs. you can get it by (-> (Thread/currentThread) .getStackTrace second .getClassName (split #"\\$"))

15:39 (from within clojure.contrib.logging or clojure.tools.logging

15:39 ataggart: stuarthalloway: regarding the chars bug with case, the issue is that character literals are ConstantExprs, thus cannot emit as primitives. I'm going to remove support for the all-chars case, and we can revisit if we ever add support for literal character primitives.

15:39 jweiss: it's slow, that's why it's not used

15:39 xkb: any of you going to dyncon2011?

15:39 stuarthalloway: ataggart: thanks

15:39 jweiss: ataggart: isn't that exactly what the loggers themselves do?

15:39 stuarthalloway: ataggart: did you see you have a logging repo now?

15:39 jweiss: (if you use the location in your log config)

15:40 ataggart: stuarthalloway: what does "have" mean, and where would I see that?

15:40 stuarthalloway: :-)

15:40 Aaron sent you a direct email

15:40 and copied the dev list

15:40 and it got mentioned here a few minutes ago: logging became its own top-level project this morning; https://github.com/clojure/tools.logging

15:40 ataggart: jweiss: if you configure it to do so, but it's rarely used due t the performance hit. Class:linenum usually suffices

15:41 stuarthalloway: and I just told you directly :-)

15:41 ataggart: heh

15:41 jweiss: ataggart: java.util.logging does not support line numbers - that was my patch - to add the ability to do stack inspection for j.u.l because it allows you to pass in the location if you calculate it yourself.

15:43 ataggart: jweiss: ok, open an enhancement once you're able. Aside: j.u.l sucks.

15:43 jweiss: but I do see your point ataggart that using that patch will mean slowness all the time, not just when the formatter uses it

15:43 ataggart: yeah i know, we've been using it just because it made one less dep

15:44 with java code it worked fine. w clojure not so much.

15:44 mlimotte: I'm confused by the conj implementtaion. The source from RT.java is: static public IPersistentCollection conj(IPersistentCollection coll, Object x){ if(coll == null) return new PersistentList(x); return coll.cons(x); } So, it looks like conj is equal to cons. So how does it achieve different behavior? In a PersistentVector, for example, conj adds to the end, and cons adds to the front.

15:44 amalloy: mlimotte: coll.cons is polymorphic

15:45 List implements it by adding to the front, Vector by adding at the end

15:46 jweiss: ataggart: afaik log4k does not support any metadata (aka params) in logs. j.u.l does

15:46 s/log4k/log4j

15:46 sexpbot: <jweiss> ataggart: afaik log4j does not support any metadata (aka params) in logs. j.u.l does

15:46 mlimotte: amalloy: thanks for the response. not sure i get it, though. i thought cons was always supposed to ad to the front.

15:47 amalloy: mlimotte: (cons foo bar) doesn't call the collection's cons method

15:47 it creates a new Cons object

15:47 \$source cons

15:47 sexpbot: cons is http://is.gd/yyphKM

15:49 mlimotte: amalloy: ahh, i see. "cons" on the collection class is really a "conj" implementation; and the cons fn is imlpemented in RT.

15:49 thankks for the explanation.

15:50 amalloy: yeah. not an ideal state of affairs imo, but not *too* confusing once you realize

15:51 mlimotte: Yea. Fine once you know it. I jumped to some conclusions based on names without reading all the code.

15:52 ataggart: stuarthalloway: CLJ-426 updated

15:58 stuarthalloway: could you please provide an example to reproduce the errors with CLJ-445

16:00 stuarthalloway: ataggart: not quickly or simply, but I will get to it

16:19 TimMc: Someone please write a program prover (like ACL-2) in Clojure and call it "Conjecture". :-P

16:20 companion_cube: :D

16:20 stuartsierra: stuarthalloway: so it seems that including the distribution ZIP in the release build will include it in the build artifacts that get pushed to Central

16:21 stuarthalloway: stuartsierra: awesome

16:21 is that just a config change, or will you be sending me a patch

16:21 stuartsierra: Just Hudson config.

16:21 We won't really know if that works until the next release.

16:30 abedra: stuartsierra, can you give tools.logging a once over

16:30 stuartsierra: yes

16:30 Deleting stuff in the -testbuild-SNAPSHOT chain on oss.sonatype.org.

16:30 abedra: ok cool

16:40 edbond: how to execute raw sql in clojureql?

16:41 fliebel: thanks for the alpha. are these fn meta changes in there?

16:45 ataggart: stuarthalloway: given how many of the numeric functions can be inlined, removing certain overloads from Numbers might cause problems with extant compiled code. That might be what you're seeing as well.

16:45 stuarthalloway: ataggart: ruling that out was my next todo item

16:47 ataggart: stuarthalloway: having nothing better to do, I'll make a patch with those overloads put back in place.

16:48 fliebel: dnolen: ping

16:48 dnolen: fliebel: hullo

16:49 fliebel: dnolen: How is logos coming along? I noticed you made some commits, but the delay branch gives me IllegalArgumentException Don't know how to create ISeq from: clojure.lang.Delay clojure.lang.RT.seqFrom

16:49 (just randomly trying that)

16:50 stuartsierra: abedra: There's more in the pom.xml than you need.

16:50 dnolen: fliebel: heh, I wouldn't mess w/ anything in the delay branch :) I thought about it a LOT more. I have some serious thinking to do. delay branch won't work.

16:50 stuarthalloway: stuartsierra, abedra: make sure what's needed is documented somehere, I will be trying to promote jmx over the weekend

16:50 fliebel: dnolen: Totally cool, I was just checking out :)

16:52 stuartsierra: stuarthalloway: should all be on the wiki, which just stopped responding again

16:53 dnolen: fliebel: Yeah, delays and lazy-seqs can't really mix in the current design. Trying to figure out how to accomplish it with just lazy-seqs. Tricky.

16:55 fliebel: dnolen: Interesting, I love lasy seqs :) What was the name of the paper you mentioned again? I might want to read it tomorrow.

16:56 dnolen: fliebel: http://pqdtopen.proquest.com/#abstract?dispub=3380156