#clojure log - Apr 05 2011

The Joy of Clojure
Main Clojure site
Google Group
List of all logged dates

1:04 * GaaiSensei slaps GaaiSensei around a bit with a large trout

2:42 hirak8: what's the best option for connecitng clojure to mongodb?

2:43 i've found congomongo & karras among others

2:43 but don't know which to use, if either

2:45 seems like congomongo is most popular, but the main clojars package seems out of date. makes me concerned

2:45 amalloy: hirak8: congomongo has been fine for me

2:46 hirak8: amalloy: do you pull it from clojars or github?

2:46 amalloy: clojars

2:47 hirak8: k

2:47 amalloy: do you happen to know if it supports sharding & replica sets?

2:48 amalloy: no idea. i use it for pretty basic storage. indexing is as complicated as i've gotten

2:48 hirak8: k

3:06 amalloy: anyone surprised that ##(doc inc) has x as a param, but calls it num in the docstring?

3:06 sexpbot: ⟹ "([x]); Returns a number one greater than num."

3:13 TobiasRaeder: morning

3:14 no_mind: what is the most suitable datastrucute/datatype for creating a cache

3:15 amalloy: hashmap

3:15 hi TobiasRaeder

3:15 no_mind: amalloy: but cache needs mutability. A cache will become dirty and needs to be refreshed

3:16 amalloy: no_mind: (a) that depends entirely on what you're caching; (b) so what? wrap it in an atom or a ref and you're all set

3:37 ejackson: Morning all

3:38 raek: mornin

3:44 cemerick: feh, good night :-P

3:44 :-)

3:46 ejackson: cemerick: are you just getting up, or just going to bed ?

3:46 cemerick: ejackson: the latter

3:46 ejackson: have mercy ! I hope it was some cracking code :)

3:46 * amalloy went to bed two hours ago. you can tell by the quality of his code

3:47 * cemerick is just trying to keep up

3:47 ejackson: lol I know that feeling. Or the feeling that I *wish* I'd gone to bed two hours ago....

3:47 cemerick: It's been a crazy month or two.

3:48 ejackson: know that feeling

3:48 i've got a client on my hands who fails to understand that I can only implement the spec he gives me, errors and all

4:10 w0tan_: i'm learning functional programming via SICP. how much of that should be valid in clojure? basic vocab aside

4:10 AWizzArd: You can apply those principles to Clojure.

4:11 amalloy: w0tan_: sicp is great, and translates pretty well. some of the later examples use set! all over the place, and those don't translate so well

4:11 (is what i've been told, anyway. i never got that far through the book *ashamed*)

4:13 w0tan_: heh, i'm sure i'm nowhere near that point anyway

4:13 good to know, though. thanks

4:15 ejackson: w0tan_: the other thing to watch out for is that you don't come across Clojures sequence functions which are massively powerful.

4:15 xkb: hi

4:15 I'm looking for a good example of a with-something macro, the kind that wraps a call and provides it with extra parameters

4:15 do you know any good examples?

4:16 like for example with-auth or with-user or something like that

4:17 ejackson: but its a fantastic place to start

4:17 xkb... I wrote a simple once last week.... one second

4:17 https://gist.github.com/897978

4:18 that binds *connection* dynamically for use is wrapped functions

4:18 most basic example

4:18 xkb: ejackson: thanks, I'll check it out

4:18 seems like most of these macro's rebind a var to some global

4:18 amalloy: xkb: also https://github.com/amalloy/amalloy-utils/blob/master/src/amalloy/utils/transform.clj#L31

4:18 which is not doing any var binding, just a let

4:19 xkb: I'm working on a Last.FM api wrapper

4:19 where some of the calls are oauth based and others arent

4:24 amalloy: thanks for the link!

4:24 gotta love github :)

5:10 pyr: hi

5:10 I forget what the idiom is to do the equivalent of apply on a member function

5:11 (on a java instance method i mean)

5:17 amalloy: pyr: don't?

5:18 Dantas: Hi everyone !!! One noob question: To create a lazy-seq the function could not be optimized to use tail call : (defn list-generator [base increment coll] (lazy-seq (list-generator (+ increment base) increment (cons base coll))))

5:18 i try to generate this list-generator with tail call and the lazy doesn't works

5:18 :(

5:19 pyr: amalloy: i mean

5:19 i can (apply str [some seq elements])

5:19 Dantas: s / try / tried

5:19 pyr: but I can't (.someMethod object [list of elements])

5:19 but I can't (apply .someMethod object [list of elements])

5:19 sorry

5:20 amalloy: pyr: indeed. java objects don't know about clojure seqs, so this makes sense. there are a few ways to do something *like* it

5:20 but they mostly involve reflection or, if the class method supports varargs, mucking with java arrays

5:20 pyr: meh

5:20 ok

5:24 amalloy: or you could do something like (defn variadic-add-method ([obj] (.add obj)) ([obj x] (.add obj x)) ([obj x y] (.add obj x y))) ... (apply variadic-add-method my-obj [some args])

5:25 angerman: hm. next coding gig will likely involve cakephp.

5:26 pyr: amalloy: yeah i get the point

5:26 thx

5:27 amalloy: pyr: yeah. in short, it's kinda gross. but it occurs to me you could easily write a macro version of variadic-foo-method

5:27 which would expand into a version of foo taking up to N arguments

5:33 pyr: amalloy: that's what i concluded, meaning it's a wrong path :)

5:33 i'll do it another way

5:33 amalloy: good idea :)

5:58 nachtalp-: hmm... where did clojure.org go? %)

5:59 ejackson: nowhere ?

6:02 nachtalp-: ejackson: i get redirected to some register.com site...

6:03 fliebel: me to

6:03 Fossi: muhaha

6:03 seems somebody forgot to renew...

6:03 ejackson: i do not.

6:03 fliebel: ejackson: What if you refresh your dns cache?

6:03 nachtalp-: Fossi: guess so :)

6:03 ejackson: why would I want to break clojure.org :)

6:04 i like it

6:04 fliebel: :)

6:04 Fossi: good they have a grace period

6:04 nothing worse than having your domain snatched from under your ass

6:12 fliebel: ??? (isa? (reify actor (act [this world] this)) actor) => false

6:14 uh? oh… (instance? begame.object.actor (reify actor (act [this world] this))) => true

6:15 So do I have to use the interface rather than the protocol to check for a relationship?

6:18 joodie: does anyone know of a clojure library containing string "formatting" predicates, like numeric / email / url that sort of thing?

6:30 Dantas: Hi everyone !!! One noob question: To create a lazy-seq the function could not be tail called ? : (defn list-generator [base increment coll] (lazy-seq (list-generator (+ increment base) increment (cons base coll))))

6:31 joodie: Dantas: yes. The tail call in a lazy seq lazy-seq.

6:31 *is* lazy-seq

6:32 Dantas: joodie: so cant be tail call ?

6:32 joodie: right

6:33 joodie: the point of lazy-seq is that it typically wraps *around* where you'd normally put your tail call.

6:33 note that lazy-seq isn't a function.

6:48 xkb: whats the emacs keybinding for clojure aware autocomplete again?

6:48 so not meta-/

6:51 danbell: when I have swank running, C-C tab

6:51 xkb: does that also work in clojure-mode?

6:51 danbell: you mean w/just normal core symbols?

6:51 not sure

6:52 xkb: ah it does

6:52 thanks

6:52 danbell: cool

6:52 xkb: seems meta-tab has the same binding

6:52 danbell: I noticed it's C-C tab when I'm editing a .clj file

6:53 meta-tab when I'm in the repl

7:36 Chousuke_: eh, clojure.org seems to have expired :|

7:36 joodie: http://clojure.org/ works for me

7:37 Chousuke_: I get a generic squatter page thingy.

7:37 joodie: hmmm

7:37 Fossi: yeah

7:37 markskilbeck: likewise

7:38 joodie: wierd. maybe someone's messing with the DNS.

7:38 Fossi: no, it went into autorenew

7:38 bartj: likewise

7:40 joodie: ?

7:40 bartj: http://www.whois.net/whois/clojure.org

7:41 Expiration Date:03-Apr-2012 14:24:30 UTC

7:41 Chousuke_: Last Updated On:05-Apr-2011 09:34:35 UTC this one is more interesting

7:42 so yeah, it probably expired today and that service grabbed it automatically.

7:42 joodie: ah. now it has switched to for me to

7:42 too

7:42 clgv: clojure.org looks fine right now - but 1.2.1 is missing on downloads page still ;)

7:42 joodie: grrr

7:43 ttmrichter: Doesn't look fine from here.

7:43 Looks like a squatter.

7:43 Chousuke_: clgv: your dns is probably not updated yet. :/

7:43 clgv: ping clojure.org

7:43 PING clojure.org ( 56(84) bytes of data.

7:43 64 bytes from wikispaces.com ( icmp_req=1 ttl=51 time=131 ms

7:45 ttmrichter: PING clojure.org ( 56(84) bytes of data.

7:45 64 bytes from CAPAHOJE.COM ( icmp_seq=1 ttl=43 time=267 ms

7:45 Chousuke: clgv: yeah, that's the old ip, but it seems it expired this morning.

7:46 I hope rhickey can get it back :/

7:47 clgv: lol first signs of IP4 address shortage?

7:48 Chousuke: nah, just someone forgetting to renew the domain :P

7:48 clgv: tststs ;)

7:49 fliebel: What would be the most zen way to align 2 maps when iterating? So that {:foo 1 :baz 2} {:foo 3 :bar 4 :baz 1} gets me :foo, 1, 3 first, and then :baz, 1, 2, in some form.

7:50 Chousuke: hmmh

7:50 AWizzArd: fliebel: you could combine the (vals of-your-maps) into a set and map over that.

7:50 That fn would lookup all vals and combine those too.

7:51 Chousuke: that would lose the key information though

7:51 AWizzArd: ah, not vals but keys I mean

7:52 In general: if this is not an operation you don't need to do often, then don't care much about maximum efficiency. Just write some code that can do it and continue with other tasks.

7:52 Chousuke: If it is an operation you need to do often, consider finding another data structure. P

7:53 fliebel: something like (map (juxt identity (partial get m1) (partial get m2)) (intersection (keys m1) (keys m2))

7:53 Chousuke: (partial get m1) = m1

7:54 fliebel: ih, right, IFn

7:59 Hm, why doesn't keys return a set?

7:59 okay, I know...

8:05 Chousuke: re data structure: any suggestions?

8:07 Chousuke: hard to say, since I don't know what else you do with it :)

8:09 fliebel: Chousuke: I iterate over it, do collision detection with it, retrieve items by key, align the keys so I can transition from one to the other. So, quite a lot.

8:09 Chousuke: hmm, you might be able to use a sorted map though

8:09 that way you can at least get a seq of items in key order

8:10 fliebel: Chousuke: I don't care about key order much. With a sorted map, two asymmetric maps still don't align.

8:11 AWizzArd: fliebel: why do you have two maps m1 and m2 in the first place?

8:11 A potentially suitable data structure might be a MultiMap

8:11 pdk: by collision detection

8:11 are we talking in the physics sense or detecting collisions in the map

8:11 AWizzArd: You can easily simulate one.

8:12 Chousuke: fliebel: Maybe you could even use finger trees? (no idea if you can, but they seem pretty flexible.)

8:13 fliebel: AWizzArd: They represent frames, and in between frames, I generate more frames that smooth the transition. So I can get away with running the game logic a few times per second and still have smooth movement.

8:13 pdk: physics, the values of my map have an java.awt.Rectangle.

8:14 Chousuke: That would be awesome.

8:15 Chousuke: fliebel: Maybe you can find a suitable measure that will help you determine if a branch in the finger tree needs to be considered for collision detection, or something.

8:17 Fossi: fliebel: i'd really look into literature

8:17 there's a ton of specialised data structures for this

8:18 might not be immutable though

8:18 fliebel: Chousuke: Right now I sort my map values by the x of the objects and limit the collision detection to the y axis. I had a priority map to do this a while back.

8:19 Fossi: but i guess you could at least look into wings 3d or the like whether they have some clever things

8:21 fliebel: Fossi: Okay, I could study CS and come up with an awesome data structure. But since this is only a 2D game, and not big-data, I'd rather use something that does the job and move on.

8:22 But it;s interesting to do nonetheless. I built a quad tree, and then decided it is not what I want.

8:23 Chousuke: I think that would be an R-tree. Every branch has a rectangle that contains all its children, if your node is in there, go down.

8:23 AWizzArd: If you do extreme concurrent updates, then locking will do as well as what Clojure already does. If no concurrent updates are required, then a single thread working on a mutable data structure is even faster.

8:23 fliebel: http://en.wikipedia.org/wiki/R-tree

8:24 Fossi: hmm, so this is 2d anyway?

8:25 fliebel: yes

8:26 Fossi: i guess that makes things a tad easier :)

8:26 _fogus_: Anyone want to help me proof a draft of a blog post that I want to post today?

8:27 fliebel: _fogus_: Proof? As in checking grammar? I'd like to, but I think you'd better ask a native.

8:28 _fogus_: fliebel: Well, a set of eyes will help tremendously

8:29 http://ietherpad.com/jUpl9dXraQ Please add comments to the document directly. :-)

8:33 kephale00: Isn't one of the primary tasks of a programmer to write new functions for specific tasks? What these people you are addressing call "bloat" stems from the fact that there are indeed many functions that are frequently reused.

8:37 ejackson: _fogus_: I'm game if you're still needing a hand.

8:37 _fogus_: ejackson: Indeed.

8:37 ejackson: shoot

8:38 _fogus_: ejackson: http://ietherpad.com/jUpl9dXraQ

8:40 joodie: I don't see the problem with "bloat". Even Common Lisp isn't halve as large as the JRE.

8:41 ejackson: do you mind if I just put in suggestions ? I'll assume if you disagree you can just pull them out

8:41 joodie: Bloat's only important when you can't *find* the function you're looking for.

8:41 We're not living in the early 80s anymore.

8:42 besides, "clean" != "small"

8:44 since we're asking for feedback anyway: does anyone have comments on https://github.com/joodie/pretzel ?

8:44 kephale00: Well, the counter argument is that some people haven't upgraded their brain's RAM, so remembering too many functions is an issue for them.

8:44 joodie: and those people use what language? C without the std lib?

8:44 kephale00: as fogus notes, Scheme

8:45 joodie: scheme isn't that small either

8:45 fliebel: I thought scheme was about 90 functions or so?

8:45 kephale00: i dont remember off-hand

8:47 chouser: kephale00: I think that's closer to the source of the consternation

8:48 or at least a useful question: *why* do people complain about the "size" of CL (and now Clojure?)

8:49 do they just hate these languages and will throw anything at them hoping something will stick?

8:49 kephale00: How many people actually are complaining about the size of these languages? The vast majority of active programming languages are growing in size at some rate.

8:49 chouser: i think the last point is more on target

8:50 Well, i have to admit that i don't have numbers to back up that statement, but from what i've seen at least most languages seem to be growing

8:50 chouser: or do they want to like the language, but find themselves frustrated by something, and (falsely?) identify the source of the problem as the "size"?

8:51 kephale00: It's probably fair -- what software is shrinking? :-)

8:51 kephale00: BTW, whats the deal with swank-clojure? I saw technomancy talking about it last night, but my dependencies on 1.3.0 are having issues

8:52 fliebel: chouser: What I know for myself, is that it was just the task of finding a function that gets you from x to y.

8:53 When you don't know half clojure/core yet, it can be hard a times to find the correct function.

8:53 chouser: fliebel: fair enough. For me, I found reading Common Lisp code nearly overwhelming, and haven't yet pinned down all the reasons.

8:54 fliebel: So I'd say size is not the problem, organization and documentation is.

8:54 kephale00: chouser: well there are some oddities with CL just because of historical artifacts in the language

8:55 chouser: But probably included were: unfamiliarity with parens, no visual distinction between flow-control forms and regular functions, no visual distinction between words defined by the language vs. the user (compounded by the ability to use first and define later)

8:56 and honestly, complete lack of type declarations probably doesn't help either.

8:57 it adds up to a whole lot of unfamiliar-looking code, and very few hints about how to start breaking it apart so it can be understood.

8:58 kephale00: chouser: WRT type declarations… people don't seem to complain about that much in Python

8:58 chouser: kephale00: true, but many of those other hints are provided. Flow control looks very different (except perhaps for list comprehension)

8:59 joodie: kephale00: I think that's because clojure attracts more Java programmers

8:59 ttmrichter: chouser: You've hit my historical reason for not liking Lisps there. There's nothing in the code to catch my eye to alert me to "syntactical" elements, etc. It's hard for me to break apart CL and/or Scheme code as a result. It looks like a morass of words, not like structured code.

8:59 TimMc: ttmrichter: I think a lot of that has to do with the terseness, the semantic density.

9:00 chouser: also, foo.bar.baz gives you some "context" for understanding (or guessing) what baz means, in a way that (baz (bar foo)) doesn't really.

9:00 _fogus_: http://blog.fogus.me/2011/04/05/_-count-common-lisp-count-clojure/ Thanks all!

9:00 TimMc: I'm used to skimming Java at high speed, picking up for loops and such, and I have to slow down for Lisps.

9:00 kephale00: Sorry to toss this in the middle of the discussion, but: [WARNING] POM for 'swank-clojure:swank-clojure:pom:1.3.0:compile' is invalid. It will be ignored for artifact resolution. Reason: Not a v4.0.0 POM.

9:00 ttmrichter: TimMc: In terms of semantic density I'll pit Haskell against Lisp any time.

9:00 TimMc: Haha, true.

9:00 ttmrichter: But I don't get this "morass of words without differentiation" vibe from Haskell.

9:01 TimMc: Interesting.

9:01 joodie: morass of punctuation, though :)

9:01 chouser: Clojure does help a little, I think. Square brackets for bindings are a nice little hint.

9:01 joodie: I'm not really kidding.

9:02 ttmrichter: joodie: True. :)

9:02 But avoiding the pointless style helps in avoiding the more egregious overuse of punctuation.

9:02 Fossi: actually i have the same problem with haskell when i pick it up

9:02 chouser: A very small standard library could help, but of course that has costs that _fogus_ has eloquently described.

9:02 kephale00: ttmrichter: well if you're going to rag on Haskell for punctuation then APL needs to be brought up

9:03 ttmrichter: Part of what attracts me to Clojure -- the first "real" Lisp (and the second Lisp) to do so -- is that there's a small smattering of actual syntax in the language.

9:03 Fossi: because you have to know that the type Webapplication is something like Request -> Response and a whole load of monads

9:03 ttmrichter: () and [] have meanings and can thus catch my eye when reading code, as a simple example.

9:03 _fogus_: EEEPPP! http://clojure.org/

9:03 Fossi: but i guess that's also just not knowing the libraries

9:03 ttmrichter: Some Lisps let me use (), [] and {} at will, but there's no semantic difference between these at all.

9:04 TimMc: _fogus_: WTF

9:04 kephale00: _fogus_: whoa

9:04 chouser: _fogus_: yeah, oops. get someone on that, if it's not too late

9:04 kephale00: i wonder if this has anything to do with my dependencies breaking...

9:04 ttmrichter: Clojure adds some and this shapes my ability to read Clojure code.

9:04 fliebel: (inc clojure.org-discussions) => 3

9:05 clgv: $dec fliebel

9:05 sexpbot: ⟹ -1

9:05 clgv: ;)

9:05 ttmrichter: In ways I could never read CL or Scheme when I gave them a shot.

9:05 joodie: I know you're not kidding. There is a certain breed of Haskell programmer (long may they rot in Hell!) who thinks it's somehow meaningful to make "operators" like {{{__^^)))()))))))())}.

9:05 fliebel: clgv: :( Now I feel negative

9:05 * TimMc bids on the domain name

9:05 clgv: $inc fliebel

9:05 sexpbot: ⟹ 0

9:05 clgv: better?

9:05 fliebel: yea

9:06 ttmrichter: Fossi: That's a different level of problem.

9:06 That's just not knowing the domain the code is embedded in.

9:06 clgv: humm university DNS seems to have cached clojure.org still

9:06 ttmrichter: My problem with Lisps, Fossi, is that I can't even read SIMPLE code. I have to decode it. Every time.

9:07 TimMc: ttmrichter: That's partly a lack of familiarity, I'd guess.

9:07 Fossi: hmmm. dunno, most code in clojure i've seen is pretty application specific

9:07 TimMc: There are a *lot* of functional idioms that I'm still getting used to.

9:07 Fossi: and if your indention style is sane it's better than java

9:08 ttmrichter: TimMc: Partially, yes. But I have honestly given CL and Scheme the old college try using my standard approach: do all personal projects in the language being targetted for three months at least.

9:08 It's not functional idioms that bug me.

9:08 I do Haskell. I do Erlang.

9:08 I just can't read Lisps. I have to decode them.

9:08 TimMc: huh

9:09 ttmrichter: Take two reasonably complex functions: one in a Lisp (but not Clojure as much) and one in Erlang.

9:09 I'll be able to skim the Erlang code without much effort, picking out the key things I need to understand in depth.

9:09 clgv: lol the guy linked in fogus' post from Loper OS recommend Mathematica? :P

9:09 ttmrichter: The Lisp code I'll have to read every word in-depth to decode.

9:09 It's probably a mental defect on my part. :)

9:10 chouser: ttmrichter: are you having any more success with Clojure than with Scheme or CL?

9:11 ttmrichter: Hell yes.

9:11 dnolen: clgv: rhickey recommends Mathematica as well.

9:11 chouser: I hadn't tried Scheme, but had tried CL a couple times and never gotten any traction.

9:11 ttmrichter: I *LIKE* Clojure.

9:11 Whereas in the past I've admired Lisps intensely but didn't like them.

9:12 chouser: ttmrichter: very interesting.

9:12 ttmrichter: Lisps are insanely elegant (minus some historical cruft, of course).

9:12 kephale00: does lein check clojure.org for dependencies?

9:12 clgv: dnolen: for real? for what purposes? I'd only recommend Mathematica for symbolic algebra and other tightly math realted tasks

9:12 dnolen: ttmrichter: I used to think similar things about the readability of Lisps, until I read a lot of Scheme. The shape of the code does have meaning.

9:12 ttmrichter: But I've never warmed up to them (Dylan aside) until Clojure.

9:13 dnolen: I've done Scheme. Had the same problem.

9:13 dnolen: ttmrichter: but did you *read* a lot of Scheme.

9:14 as in not your own code.

9:14 kephale00: gagh.. it does… i guess a custom leiningen until clojure.org comes back up is in order

9:15 ttmrichter: dnolen: I always do. For Scheme I always tried to read library implementations. I think I was using Gambit at the time?

9:15 Something like that.

9:15 Fossi: kephale00: so leiningen depends on clojure.org being up?

9:15 that's pretty bad

9:15 kephale00: Fossi: yeah it does, and yeah it is pretty bad

9:16 [WARNING] *** CHECKSUM FAILED - Checksum failed on download: local = '2819a4be8ef8de2268f8d5a91d62cee0026ab531'; remote = '<html>

9:16 <head>

9:16 <meta' - IGNORING

9:16 [WARNING] POM for 'swank-clojure:swank-clojure:pom:1.2.0:compile' is invalid. It will be ignored for artifact resolution. Reason: Not a v4.0.0 POM.

9:16 it looks like it is picking up HTML pages in dependency checks

9:16 Fossi: good i didn't start of with a clean deps today :/

9:16 ttmrichter: That's a bit embarrassing having the main web site down and camped.

9:16 Where by "embarrassing" I mean "infuriating".

9:16 Fossi: it's only the providers page

9:17 so, they are the good guys

9:17 ttmrichter: So, find out where these guys are and for a round-trip airline ticket I'll commit an untraceable assassination. :)

9:17 kephale00: lol

9:17 Fossi: basically without them the domain would be up for registration right now

9:17 devn: domains are taken care of

9:17 Fossi: and that would get snaged in a minute :)

9:18 devn: FYI

9:18 ttmrichter: I think they're in Portugal.

9:18 I'd love to take a trip to Portugal in springtime. :D

9:19 chouser: yay. That was a lot less painful than I feared.

9:20 devn: chouser: lol yeah, a little scary

9:21 chouser: I didn't realize it was the original registrar's page.

9:21 devn: chouser: yeah i thought a squatter had snagged it

9:22 ttmrichter: Ah, if it's not a squatter that's fine.

9:22 I thought it was a squatter.

9:22 Damn! No trip to Portugal. :(

9:22 kephale00: fine is a relative term here… : P

9:24 dnolen: ttmrichter: I actually meant like papers - where readability and convention is more important. Libraries not necessarily the best place. I see now that Clojure source follows good Lisp style.

9:26 ttmrichter: Reading papers isn't helpful if I have to read real-world code -- mine and others -- day in and day out while working.

9:26 Syntax by convention isn't, to my mind, a viable approach to making things work out.

9:26 I have similar issues with real-world languages, incidentally.

9:27 English grammar is a nightmare of wasted, "useless" words like "a" and "the" and half the prepositions.

9:27 dnolen: ttmrichter: heh, papers often have a lot of good real world code.

9:27 ttmrichter: Chinese is far simpler as a grammar.

9:27 I submit that Chinese is harder to learn BECAUSE it has fewer structural words.

9:28 Even though Chinese is far more regular a language than English could ever hope to be.

9:28 TimMc: ttmrichter: Redundancy plays a big role in readability.

9:28 devn: chinese is hard. trust me on that. :)

9:28 ttmrichter: I don't have to trust you on it devn. I'm living the nightmare. ;)

9:28 TimMc: That's why we have initial capital letters in our sentences.

9:28 ttmrichter: A quick "/whois ttmrichter" can explain why I said that, devn. ;)

9:29 TimMc: Redundancy and structure signifiers.

9:30 Words like the articles have no real useful purpose -- but they announce the beginning of a noun phrase.

9:30 It's obvious we don't need articles, given the huge number of languages that don't have them.

9:31 But they stick around in Indo-European languages because they do serve a signalling purpose. They provide some structure you can hang your thoughts on, basically, while you're trying to comprehend what someone's saying.

9:31 TimMc: ttmrichter: Your /whois was unenlightening.

9:31 ttmrichter: TimMc: Hmm... It used to have the domain name. You'll have to do a whois on the IP now it seems.

9:31 clgv: ttmrichter: articles carry information in languages like german and french

9:31 ttmrichter: One thing I've noticed with my students (Chinese): if they say something (in English or Chinese) that I don't quite catch, they start over right from the beginning.

9:32 TimMc: hah

9:32 ttmrichter: clgv: In German and French they carry "gender" (which is utterly useless grammatically) and in German they also signal case (which is not so useless, but confusing when mixed with gender).

9:32 fliebel: isa? instance? extends? How do I tell if a record implements a protocol?

9:33 clgv: ttmrichter: why is information about gender useless?

9:33 fliebel: clgv: For 'things' that is, like, a tree is female.

9:34 ttmrichter: German: a man is masculine, a woman is feminine, a boy is masculine, a girl is ... neuter? The f...?

9:35 Grammatical gender is pointless.

9:35 Being able to identify gender isn't the same thing as grammatical gender.

9:37 lucian: ttmrichter: i disagree

9:37 fliebel: Can someone *please* explain me what the difference is between all these type-telling functions?

9:38 lucian: ttmrichter: most latin languages have "configurable" redundancy. you can drop things like pronouns if they're obvious

9:38 TimMc: fliebel: Maybe once clojure.org is back.

9:38 ttmrichter: lucian: How does this make grammatical gender useful?

9:38 fliebel: TimMc: What has clojure.org to do with it?

9:38 ttmrichter: How does marking a tree as feminine (I think) communicate anything of use whatsoever?

9:38 TimMc: fliebel: It's down currently, and I wanted to visit the protocols page. :-)

9:39 lucian: ttmrichter: not a tree, but persons

9:39 ttmrichter: for the tree it's only a little useful

9:42 fliebel: TimMc: Oh, right… *checks his cache*

9:44 ttmrichter: lucian: You are confusing grammatical gender and having gender-identifying pronouns.

9:44 (Although strictly speaking even the latter are optional.)

9:44 lucian: ttmrichter: no, i'm not. english is very crap at this, which is likely why you don't realise the difference

9:44 fliebel: hah! Works for me… They mention extends? as the right thing, but then I need to to (extands? record (class obj))

9:45 ttmrichter: lucian, I am amply familiar both with German and with French.

9:45 lucian: in most latin languages verbs, adjectives, nouns, pronouns, etc. most signify gender and number

9:45 ttmrichter: And passingly familiar with Chinese the hard way.

9:45 lucian: ttmrichter: right, good

9:45 TimMc: fliebel: extends? is the one

9:45 ttmrichter: And, despite this familiarity, I still think that grammatical gender is pointless.

9:45 lucian: ttmrichter: french is a bit the odd one out, sadly. there's less optional than in portuguese or romanian

9:46 ttmrichter: BECAUSE it extends to "things".

9:46 lucian: ttmrichter: it's great for disambiguation

9:46 even for things

9:46 ttmrichter: Where you get ridiculous things like feminine trees but masculine windows. (Or was it the other way around?)

9:46 lucian: when i say 'want "this female" and "that male"' while pointing, in romanian it's very likely that whoever is next to me knows exactly what i'm saying

9:47 ttmrichter: There's no ambiguity in distinguishing a tree from a window.

9:47 What, precisely, does grammatical gender add?

9:47 lucian: ttmrichter: redundancy

9:47 and very cheaply

9:47 ttmrichter: You cut the prospective nouns by 50%.

9:47 And what happens when you want to talk about a doctor?

9:47 lucian: actually 66%

9:47 ttmrichter: In German a doctor is masculine, if memory serves.

9:48 But the doctor I'm talking about is female.

9:48 lucian: i'm not familiar with german

9:48 ttmrichter: Suddenly I'm using grammatical masculine and feminine pronouns.

9:48 lucian: there's a similar phenomenon in french, yes

9:48 ttmrichter: This doesn't help, it confuses.

9:48 lucian: but you say 'madame le docteour'

9:49 it doesn't confuse natives :)

9:49 ttmrichter: Of course it doesn't.

9:49 lucian: but yes, in this case 'le' doesn't help

9:49 but the 'madame' bit helps

9:49 ttmrichter: Just like the tonal system in Chinese doesn't confuse the Chinese.

9:49 Much.

9:49 lucian: and when when you say 'elle', it's clear

9:49 bah, the tonal system is dreadful

9:49 clgv: it's profession nouns that are almost all male except the ones that are historically typical female jobs ;)

9:49 nachtalp-: ttmrichter: german words for both

9:50 has words, even :)

9:50 ttmrichter: Hell, the Chinese aren't confused despite the fact that the third-person pronoun is THE SAME (in spoken Chinese) for he, she and it.

9:50 It's amazing what the human brain can internalize.

9:50 lucian: ttmrichter: because they stuff the redundancy somewhere else

9:50 ttmrichter: Well, they don't actually. They just repeat a whole lot more context in cases of misunderstanding.

9:51 lucian: hungarians have the same issue, but they repeat "female" or "male" a lot

9:51 ttmrichter: EXACTLY

9:51 more redundancy somewhere else

9:51 ttmrichter: The Chinese language is, to me, like a Lisp, complete with that pudding-like feel. :)

9:51 There are very few linguistic cues in structure.

9:51 Which makes it hard to learn if you've learnt anything else first.

9:52 lucian: ttmrichter: if lisp were case and font-sensitive, i might agree :)

9:52 no_mind: if I define a symbol in a namespace dynamically (generated by code), will it be possible to access the defined symbol later from that namespace ?

9:52 waxrose: Lisp is the first language I actually understood.

9:52 Scheme to be more accurate.

9:55 clgv: no_mind: you have to intern it for that purpose ##(doc intern)

9:55 sexpbot: java.lang.SecurityException: You tripped the alarm! intern is bad!

9:55 clgv: $source intern

9:56 sexpbot: intern is http://is.gd/ILW2Di

9:56 waxrose: I think most people that are turned off by a Lisp either lack a mathematical background or struggle reading text inside out. :3

9:57 clgv: waxrose: yeah the inside-out isn't natural for europeans or americans, since we read from left to right ...

10:00 thorwil: perhaps too many people make the mistake of expecting to be able to make at least some sense of lisp code, before even reading an explanation of the basics

10:00 waxrose: That too

10:01 ttmrichter: Or, perhaps, but this is probably just crazy talk, not every approach suits every person?

10:02 Some people are verging very strongly on stereotypical "Smug Lisp Weenie" talk here. This is something that has been refreshingly absent from the Clojure community in the past. It might be nicest if it stayed that way.

10:02 thorwil: ttmrichter: sure, but often approaches are rejected without understanding. which can be reasonable, regarding investment

10:03 ttmrichter: The problem is that this starts to become the assumption followed by the conventional wisdom followed by the perceived truth.

10:03 Then we get Eric Naggum.

10:07 chouser: thorwil: I think that is the key. There are far too many programming langauges for it to be useful to learn them all.

10:07 So you have to reject learning some of them without knowing them well enough to be 100% sure for yourself that they ought to be rejected

10:08 thorwil: programming languages are not pokemons!

10:08 chouser: Any conversation trying to convince someone to learn a language (or discussion about someone who has chosen not to) really ought to respect this fact.

10:08 waxrose: chouser, Great book btw... got mine yesterday. :P

10:08 chouser: waxrose: ah great, thanks!

10:10 waxrose: chouser, np :)

10:12 ttmrichter: thorwil: They're not?!

10:12 Damn, I've been doing this wrong!

10:12 gtrak: clojure, I choose you!

10:12 * ttmrichter has a USB stick with about 35 different language on it last count.

10:12 ttmrichter: s/language/languages/

10:12 sexpbot: <ttmrichter> has a USB stick with about 35 different languages on it last count.

10:13 gtrak: immutable concurrency attack is super effective

10:13 ttmrichter: chouser: You're the author of which book?

10:13 If it's The Joy of Clojure, I've got that near the top of my reading queue right now.

10:14 clgv: ttmrichter: look up the names on its cover ;)

10:14 ttmrichter: I choose my languages based on what problem I'm trying to solve.

10:14 I wouldn't want to write an embedded control system in Clojure for example. :D

10:15 gtrak: yea, real-time and GC just don't go well together

10:15 thorwil: ttmrichter: that's what i want to do, too. though it's not easy to even get there, where you really understand the strengths and weaknesses

10:15 * waxrose going to get his books signed one of these days

10:15 ttmrichter: OK, that was mildly unnerving, sexpbot.

10:16 I'm assuming sexpbot is the 'bot that people use here to do Clojure code snippets?

10:16 waxrose: yar

10:16 Raynes: sexpbot or clojurebot. Either one works.

10:16 ttmrichter: Cover?

10:17 Raynes: I prefer sexpbot, but I'm biased. ;)

10:17 waxrose: How's Meet Clojure doing? :P

10:17 Raynes: waxrose: Smoothly.

10:17 ttmrichter: clgv: Oh, never mind.

10:17 I wasn't thinking on the right thread there.

10:17 waxrose: great

10:17 ttmrichter: Ah. Chris Houser.

10:17 Got it.

10:17 clgv: ^^

10:18 ttmrichter: Well, I have that book (e-form) solely on the recommendation of a drooling fanboi. :)

10:18 He basically said it's the best way to learn idiomatic Clojure thinking.

10:18 So I got it sight unseen (something I don't usually do).

10:19 waxrose: ttmrichter, I'm not allowed to fully read it till I finish Practical & Programming Clojure first. :/

10:19 ttmrichter: Now in my Copious Free Time&trade; I have to explore it.

10:21 There's no "Learn You An Clojure" or something like that?

10:21 I thought that's what all the cool kids did these days. :)

10:21 TimMc: waxrose: Learning to read programs from the bottom up is also a stumbling block for beginners.

10:21 Raynes: ttmrichter: I'm writing something along those lines.

10:21 TimMc: I like to joke that lispies pick up a book and immediately read the ending, then work backwards through the plot. :-)

10:22 Raynes: TimMc: Sounds like something Factor programmers would do.

10:22 waxrose: TimMc, Good point... and lol @ reading it backwards

10:22 clgv: ttmrichter: I am still not formatting in an idiomatic to simplify reading and understanding for myself ;)

10:23 Raynes: Factor programmers would work from beginning to end, but read each chapter from end to beginning.

10:23 clgv: s/idiomatic/idiomatic way/

10:23 sexpbot: <clgv> ttmrichter: I am still not formatting in an idiomatic way to simplify reading and understanding for myself ;)

10:23 ttmrichter: OK, Chapter 1 is reading very nicely.

10:24 thorwil: i wonder if that feature is a blessing

10:24 s/blessing/curse/

10:24 sexpbot: <thorwil> i wonder if that feature is a curse

10:24 ttmrichter: waxrose: I've got enough experience in picking up languages that I'll just dive into Joy. (That and I've already read Programming. I leave the decision as to which factor is more important as an exercise.;))

10:24 Raynes: I'm wondering why that feature has been around for around 7 months and everybody is just now noticing it all at once.

10:25 ttmrichter: Raynes: Fads.

10:25 Someone semi-influential noticed Factor and now it's everybody's toy.

10:25 chouser: thorwil: I generally precede my s///'s with a space

10:25 Raynes: no offense intended. :-)

10:26 ttmrichter: Me, I looked at Factor and said, "Cool! Someone made a Forth for the 21st century!"

10:26 Raynes: chouser: That's actually what I told people to do. I'd totally disable it if it really bothered anybody. It isn't a huge deal. I do the same thing for title scraping.

10:26 ttmrichter: chouser: Your first chapter bodes well for the book.

10:27 Raynes: It's one of those things that some people really like and others really hate.

10:27 chouser: ttmrichter: thanks! I hope you enjoy it.

10:27 ttmrichter: Well, given the drooling fanboism of the guy who recommended it to me (I really respect his opinions on these matters), I rather think I will.

10:27 chouser: I was pleased to see the printed book takes up no more space on a shelf than Halloway's

10:28 We really didn't want to create a tome, but seemed frequently in danger of it.

10:28 ttmrichter: I may have to get a hard copy of it actually.

10:28 mefesto: chouser: congrats on the book, just received my copy last friday :)

10:28 ttmrichter: I'm just switching jobs to a Java shop and it may be time to ... subvert. :D

10:29 waxrose: ttmrichter, I will go crazy if I don't read every available book on the subject even if it's outdated. Maybe I suffer from OCD? :3

10:29 ttmrichter: waxrose: You're a programmer. You'd BETTER have OCD!

10:31 waxrose: lol

10:31 * ejackson checks whether he really does have OCD

10:31 waxrose: haha

10:32 * ejackson checks again to make sure that the really does have OCD

10:32 ttmrichter: There's a simple test to see if you've got OCD or not.

10:32 Just answer one simple question: does "anal retentive" properly have a hyphen or not?

10:32 * ttmrichter counts down from five....

10:32 joodie: -

10:32 :)

10:33 waxrose: Sorry, I stopped reading after the an...

10:33 ttmrichter: joodie: That was the wrong ansewr.

10:33 s/ansewr/answer/

10:33 sexpbot: <ttmrichter> joodie: That was the wrong answer.

10:33 ttmrichter: The correct answer is "nobody cares!"

10:34 * waxrose confused then shakes ejackson to check if he has OCD or not

10:39 ttmrichter: I'm a little confused by 1.2.3, chouser. How can "code is data" be difficult to grasp for anybody who's ever used an assembler?

10:39 Or Forth, for that matter. :)

10:39 TimMc: ttmrichter: A great diagnostic image for OCD: http://gallery.burrowowl.net/index.php?q=/image/23547.png

10:39 ttmrichter: Is just going to it proof that you've got it?

10:39 TimMc: Naw, your reaction is diagnostic.

10:40 Basically, whether or not the image enrages you. :-)

10:41 chouser: ttmrichter: what percentage of our readers have used assembler, do you think?

10:41 ttmrichter: OK, I'm probably projecting, yeah.

10:41 I started with and still fall back to assembler.

10:41 TimMc: It's not "code is data" in the same way, though.

10:41 ttmrichter: I mean Hell, I'm trying to relive my youth so I'm writing a cross-assembler for Interdata 16-bit machines so I can program an emulated one. :D

10:42 Well, no, of course it isn't TimMc. It's a higher-level abstraction of what the Von Neumann architecture posits.

10:42 waxrose: I have yet to have a course on assembler. :/

10:42 ttmrichter: But the NOTION of code and data being one and the same shouldn't be alien.

10:43 Just some of the implications specific to Lisp's implementation of the concept are going to be weird.

10:43 Raynes: TimMc: That image is agonizing.

10:43 ttmrichter: But the same applies to pretty much any homoiconic language, which includes the Forths and the Prologs.

10:43 TimMc: Raynes: :-D

10:43 ttmrichter: That pencil on the left pisses me off. The rest are fine.

10:43 waxrose: TimMc, That makes me slightly annoyed. :3

10:43 * ttmrichter </lie>

10:44 TimMc: waxrose: Same here.

10:44 waxrose: mostly because of the "2 HB" on some pencils and some with out.

10:45 TimMc: ttmrichter: Are you asserting that assembly/machine code is homoiconic?

10:45 ttmrichter: No, but Prolog and Forth are.

10:46 waxrose: Speaking of Neumann... I bought Knuth's AoCP vol 4a yesterday... my brain already hurts

10:46 chouser: I think the brain's tendency to pattern-match without being asked can complicate the understanding of a homoiconic language the first time.

10:47 Or perhaps it's weaknesses in English when trying to explain it, I'm not sure.

10:47 ttmrichter: chouser: Yeah, that could be a problem. It's a problem that's so far in my past now that I can't recall it, probably.

10:47 clgv: waxrose: lol. you don't love his assembler? ;) I hate it as well, that he didn't just use mathematical pseudocode ...

10:47 ttmrichter: I do know that self-modifying machine language hurt my brain when I first hit it, but it probably prepared me for homoiconic languages.

10:48 waxrose: clgv, lol...He's quite a character to say the least

10:49 clgv: waxrose: I still didn't read his books because of it ;)

10:52 nickik: im reading Interduction to Alorithems and that allready kills me. AoCP is just crazy but if you start reading now you will know a lot about compilerwriting in 2050.

10:52 waxrose: lol

11:01 choffstein: cemerick: any idea why I might be getting "ava.lang.ClassNotFoundException: com.amazonaws.ClientConfiguration (rummage.clj:9)" when I am trying to compile a project using rummage?

11:13 joodie: choffstein: did you do a "lein deps" first?

11:13 choffstein: joodie: yeah, but I can't seem to download the aws-java files. So I just grabbed 1.1.5 from the maven repo and installed it myself

11:13 which worked before

11:13 and doesn't seem to work now...

11:13 joodie: hmmmm

11:14 choffstein: for some reason, the internet connection I am on in my office can't pull the aws jars ... but can pull everything else

11:14 and I don't feel like going home just to pull that jar file

11:19 joodie: then I don't know what's going on

11:22 * fliebel thinks it would probably be good to have some sort of paint order...

11:24 kephale00: oh yeah

11:25 watch out for lein deps today

11:25 until clojure.org come back lein deps will break things for you

11:26 comes back*

11:27 choffstein: not saying anything, just tagging you so you get a notification if thats part of your irc prog

11:29 choffstein: alright. thanks :)

11:36 ttmrichter: kephale00: Clojure.org is back for me already.

11:36 Raynes: It depends on your ISP, of course.

11:37 ttmrichter: But it's a sign that things are being returned to normalcy soon.

11:37 kephale00: yes

11:37 my day is not lost!

11:37 but i am still waiting for it to come back up here

11:37 err… to resolve correctly i should say

11:38 TimMc: DNS propagation?

11:39 kephale00: mmm

11:39 TimMc: FOr me, dig retrieves which gets me to wikispaces.com, but my browser still gets the register.com page.

11:40 kephale00: presumably there are some DNS caches that need to be refreshed somewhere in the pipeline

11:40 waxrose: clojure.org is down? Hasn't gone down for me all morning. O_o

11:41 Fossi: that ip shows the wikispace page for me as well

11:41 and is what i'm getting from dig

11:41 but just clojure.org works again

11:42 kephale00: bah… my dig still gives me ;; AUTHORITY SECTION:

11:42 clojure.org. 74187 IN NS ns1.expireddomains.register.com.

11:42 clojure.org. 74187 IN NS ns2.expireddomains.register.com.

11:42 TimMc: Aha, my proxy is caching it.

11:42 I proxy most of Firefox's connections through a school server.

11:43 kephale00: I wonder if there's a way to request fresh data.

11:45 kephale00: TimMc: I think I'll just wait it out. I lost enough time regrabbing dependencies from machines that I hadn't tried to do a refresh on.

11:58 choffstein: Anyone using sandbar that could answer a flash question for me?

11:59 Namely, I am trying to use hiccup to build my pages and I want to integrate my flash messages, but flash-get always seems to return nil.

12:04 fliebel: Can I Type-hint records?

12:05 ehm ,protocols

12:08 choffstein: I am trying to send a string "comma,separated,values" as part of a query string to my RESTful API. When I post it, however, my API gets it in as "comma%2Cseparated%2Cvalues", which my API can't parse

12:08 are there any libraries to automatically convert the encoding?

12:10 Ahhh...java URLDecoder

12:10 TimMc: choffstein: I see ring.util.codec/url-decode

12:10 choffstein: Ahhhh....even better :D

12:15 dnolen: fliebel: you can type-hints fields to a defrecord/type, you can't type hint args to protocol method.

12:16 fliebel: dnolen: Oh, okay. Weird.

12:18 ttmrichter: It is rare for a computing book to require my looking up a non-computing term in a dictionary....

12:19 And now I want to pun about Haskell programming and Maenadic approaches.

12:19 Raynes: ttmrichter: You haven't seen anything yet. Wait until cemerick's book is out.

12:22 ejackson: i'm embarrased to have to ask....

12:22 but how do I do this:

12:22 (repeatedly 20 (fn [] nil))

12:22 like a sane person

12:23 amalloy: ejackson: (repeat 20 nil)?

12:23 ejackson: genius !

12:23 thank you noble sir

12:24 amalloy: ejackson: see also ##(doc constantly)

12:24 sexpbot: ⟹ "([x]); Returns a function that takes any number of arguments and returns x."

12:24 TimMc: ejackson: clojuredocs.org has a good "related functions" feature: http://clojuredocs.org/clojure_core/clojure.core/repeat

12:24 ttmrichter: Raynes: What's cemerick's book?

12:24 ejackson: groovy

12:25 The Kickass of Clojure

12:25 Raynes: ttmrichter: Clojure Programming. While being a walking dictionary, he isn't much for naming things.

12:26 amalloy: ttmrichter: see if you can work in a joke about how dryads make the driest maenad jokes

12:26 TeXnomancy: at least it's not called Programming Clojure

12:26 ejackson: yes, but its within commutation.

12:27 i'll never keep those straight

12:28 speaking of this Raynes.... I had o thought about your title. I know I've used the idea before, but: (meet clojure)

12:29 Raynes: ejackson: Meet Clojure has grown on me significantly.

12:29 ejackson: oh oh... so does foot fungus, if unchecked ;)

12:30 just kidding, just kidding.

12:30 Raynes: :>

12:31 ttmrichter: OK, which is Clojure Programming? Is that the old Pragmatic book?

12:31 ejackson: Yeah, Stuart Halloways

12:31 ttmrichter: No, that's Programming Clojure. My bad.

12:31 ejackson: i knew what you meant :)

12:33 ttmrichter: And what is Meet Clojure? Another book? A web site?

12:33 ejackson: that is Raynes' book in production

12:35 given that chouser was paid in cookies there are many enthusiastic authors out there... :p

12:35 ttmrichter: Warts too, ejackson.

12:35 And cancer.

12:36 ejackson: I doubt even a book publisher would pay their authors in warts.

12:37 now, the recording industry, well maybe.

12:37 fliebel: ?? When I add a type hint to the arg of a type, it gives me IllegalArgumentException: Can't find matching method: foo, leave off hints for auto match.

12:38 ejackson: wrong type ?

12:38 fliebel: Doing the exact same hint in hte places where it's used, it works fine.

12:39 TimMc: fliebel: Gist some example code?

12:39 fliebel: TimMc: I'll distill something.

12:46 no_mind: is there a way to check if a given symbol exists in a namespace ?

12:47 TeXnomancy: (doc resolve)

12:47 ,(doc resolve)

12:47 fliebel: TimMc: https://gist.github.com/903973

12:48 no_mind: TeXnomancy: resolve throws an exception if symbol does not exist. I am looing for a neater way

12:48 TeXnomancy: ns-resolve looks to be safer, though it will throw if the ns doesn't exist.

12:50 no_mind: TeXnomancy: ns-exists for sure

12:50 cemerick: choffstein: the AWS jar isn't on your compilation classpath. It's baffling to me that you continue to have dependency issues there. :-(

12:51 choffstein: cemerick: it's only when I am at my office. it's crazy.

12:51 cemerick: ttmrichter, Raynes: I think you'll find that our book is going to be mostly lacking in esoterica.

12:51 choffstein: cemerick: but not when I am at home.

12:51 cemerick: choffstein: That is quite the crazy network issue.

12:51 choffstein: I know

12:52 cemerick: But, it makes me feel a little better that it's isolated.

12:52 choffstein: maybe your office's network blocks any url with "amazon" in it?

12:52 TimMc: That would be nuts.

12:52 cemerick: bad browsing filters gone amok, etc

12:52 choffstein: nah, I'm on AWS right now ;)

12:52 ejackson: cemerick: what's the focus/theme/flavour gonna be ?

12:52 cemerick: oh well :-)

12:53 TimMc: fliebel: Interesting. I've never worked with reify, but that is odd behavior.

12:53 cemerick: choffstein: it'd be interesting to see a tcpdump of you attempting to pull dependencies from the office.

12:53 TimMc: I verified that it does indeed use reflection there.

12:54 fliebel: TimMc: Yea, weird, eh?

12:55 Maybe cemerick or ejackson know… https://gist.github.com/903973 < type hint blows

12:55 ejackson: fliebel: lemme have a look.... don't hold your breath :)

12:55 TimMc: Clojure doesn't complain when I put ^String in the protocol's definition instead, interestingly -- but it still ends up using reflection.

12:55 * fliebel holds breath

12:56 TimMc: fliebel: Hold someone else's. :-P

12:56 ejackson: do you have to typehint the protocol definition perhaps ?

12:56 just guessing here

12:56 TimMc: ejackson: I tried that.

12:56 fliebel: TimMc: Yea, the protocol hint just gets ignored.

12:56 ejackson: :)

12:56 cemerick: ejackson: oriented towards engaged Java devs and those that use popular dynamic languages like Ruby and Python. It's also something of a duplex book; part is purely language-related, part is purely domain-specific.

12:56 fliebel: Putting the hint on the substring s works.

12:57 cemerick: s/purely/mostly

12:57 sexpbot: <cemerick> ejackson: oriented towards engaged Java devs and those that use popular dynamic languages like Ruby and Python. It's also something of a duplex book; part is mostly language-related, part is mostly domain-specific.

12:57 ejackson: cemerick: that tremendous. It was a double whammy for me coming from the ruby world to have to learn lisp and the java ecosystem in one bite.

12:58 cemerick: ejackson: Yeah, we're hoping to take the sting out of that process a bit, though it's not in the drafts at all yet.

12:58 TimMc: Indeed. Most Clojure guides I've seen assume a Java background.

12:58 It makes Clojure seem like an auxiliary language rather than its own thing.

12:59 Raynes: TimMc: Mine doesn't! :D

12:59 TimMc: Yay!

13:00 cemerick: TimMc: well, in a lot of ways, it's not. Clojure without the JVM or its libraries (or, those of *some* host) wouldn't be even a tenth as useful or popular.

13:01 i.e. go throw together a genius of a language with its own runtime, and see how the crickets sing

13:01 TimMc: fair

13:01 ejackson: its true. coming from ruby where the runtime is a dog, having the JVM is magic.

13:01 dnolen: fliebel: like I said earlier protocol fns cannot be type hinted.

13:02 kephale00: speaking of Clojure off of the JVM, has anyone been playing with the CLR version

13:02 cemerick: That's why ClojureScript – when it's revisited and fully-baked – will be a revelation.

13:02 fliebel: dnolen: I know, but you said their implementations cant;right?

13:02 *can, right?

13:03 dnolen: fliebel: no, you can't type hint defprotocol, nor implementations.

13:03 TimMc: So, that does "leave off hints for auto match" mean then?

13:03 *what

13:03 dnolen: if you need to hint something you need to hint the symbol, or hint in a let binding as usual.

13:04 TimMc: Does it mean that type hints interfere with connecting up implementations with specifications?

13:04 cemerick: kephale00: there are a couple of people on the ML that are using it -- I can't say I've ever seen much chatter about it in the channel.

13:04 dnolen: TimMc: the type hint stuff is for definterface as far as I can tell.

13:05 kephale00: aha

13:06 no_mind: technomancy: ns-reolve works but I have another problem. I need to check for a symbol which is the value of a var

13:07 TimMc: dnolen: I think I understand, thanks.

13:12 dnolen: TimMc: fliebel: an example, https://gist.github.com/904024

13:13 fliebel: dnolen: Cool, so when I do a record, it also does this?

13:14 dnolen: fliebel: if you are implementing an interface yes you can do that. but interfaces are about methods, methods are not first class.

13:14 protocols create functions.

13:15 fliebel: right, so unless I need Java interop, no type hints on records

13:32 Raynes: http://www.clojure-conj.org/ Now accepting talk submissions.

13:32 cemerick: Quick, convince me to submit a talk before I get stage fright.

13:34 cemerick: Raynes: do it now so you can beat yourself into a robust public speaker. Life sucks just a little more if one is afraid of / not good at public speaking.

13:34 Not that I'm good at it, just a lot better than I used to be.

13:34 Raynes: cemerick: Me and amalloy were talking about talks a while back. I actually do have one idea that I might propose. The second one will be tricksy.

13:35 amalloy and I* inb4grammarnatzi

13:35 amalloy: nicely done, sir

13:36 Raynes: I only wish they'd allow for a joint talk with amalloy and I both, that way I could hoist him up on my shoulders and we could talk in unison.

13:36 amalloy: sounds way too creepy for me

13:38 cemerick: I think there should be an author's roundtable at the start of the conj, so that everyone can throw their rotten fruit at their least favorites in the beginning and get it over with. :-D

13:49 ejackson: this conj sounds better-and-better all the time :)

13:50 redinger: cemerick: Please send that proposal and a list of all the authors I need to get on board. :)

13:50 Raynes: You could certainly do a joint talk with amalloy. Up to you if you really need to hoist him up

13:50 cemerick: redinger: Ha! They're all going to stand in a line, with me in front with a big umbrella. ;-)

13:51 amalloy: haha

13:52 ejackson: hmmm.... I'll see if I can come up with anything interesting to propose saying

13:52 cemerick: ejackson: will you be making the trip?

13:52 ejackson: that is a function of money :)

13:53 i maintain my optimism, though, and hope to make it.

13:53 cemerick: That'd be stellar. :-)

13:53 ejackson: thank you, yes it would be awesome.

13:54 cemerick: All of the eurozone Clojure folks should pool in for a netjets (or whatever) booking. Might actually be cheaper than commercial tickets if there's enough people interested.

13:54 ejackson: I freaking love it

13:56 cemerick: do you have Dutch ancestry ?

13:56 cemerick: ejackson: German, Russian, French, Native American

13:58 Along with some North African if that kooky "heritage" genetic test was worth anything.

13:59 ejackson: hmmm...

14:33 fliebel: cemerick: What is that airplane pooling you proposed? I'd love a java.util.concurrent.AirplanePoolExecutor. http://airplanepoolexecutor.eu/ is still free :)

14:34 (fly! AirplanePoolExecutor conj fliebel)

14:35 cemerick: fliebel: netjets is the one that comes to mind, though IIRC they're fundamentally U.S.-based.

14:39 ejackson: cemerick: no they operate here too

14:39 but I don't think I can afford to even ask what they charge

14:40 cemerick: ejackson: A friend of mine whose company used them for a brief period said that it was definitely cheaper than commercial tickets as long as you maximized capacity.

14:41 ejackson: Well then ! I shall investigate :)

14:41 * cemerick denies any claim of accuracy of heresay, of course :-)

14:41 cemerick: If that actually happens though, I want to be on the tarmac to see lpetit, cgrand, fliebel, and ejackson stepping off the jetway. :-P

14:41 fliebel: In that case I love the idea. If I can find out more, I could set up a simple registration/pledge service on http://airplanepoolexecutor.eu/ :P

14:42 ejackson: lol - that would be rather magical

14:43 * fliebel is exited

14:43 ejackson: i suspect fliebel is in for an icy shower.

14:46 fliebel: ejackson: puh, we'll see :)

14:46 Raynes: I took icy showers for the majority of the summer before last in an attempt to raise my cold tolerance.

14:47 ejackson: Raynes: in preparation for .... ?

14:47 Raynes: Winter?

14:47 Nothing in particular.

14:47 fliebel: Ah, some numbers finally… http://answers.yahoo.com/question/index?qid=20071210142517AAkga0Y

14:47 ejackson: :) I like your stiyle.

14:48 fliebel: Any europeans with a pilot license? :D

14:48 ejackson: cemerick: see what madness you have wrought !

14:50 cemerick: ejackson: gawd, that almost sounds plausible. 6 hrs * $2k / 10 people maybe?

14:51 It'll probably get nuked by it being functionally two one-way trips (at least as far as the charter company is concerned).

14:53 technomancy: if we're seeing checksum mismatches downloading a pom from maven central... is that the kind of thing that deserves a bug report?

14:53 * technomancy is a little weirded out

14:54 ejackson: cemerick: ok, I just called NetJets to figure it out. They won't tell me immediately, but are preparing a quote

14:54 cemerick: ejackson: ha, this is great

14:54 fliebel: ejackson: cool!

14:54 cemerick: technomancy: yeah, that's no good

14:55 ejackson: my wife's face was a study...

14:55 TimMc: I totally need to make it to the Conj.

14:56 I'm going to see about taking Amtrak down.

14:58 Uh... is the conj free?

14:58 ejackson: pish - cemerick will fly you in his jet.

14:59 Raynes: cemerick: As of the 2010 census, the population is listed as 130 here in Eldridge now. :o

14:59 TimMc: I understand the organizers are "still putting the finishing touches on the logistical details", but it would be nice to know the order of magnitude of the cost of attending.

14:59 cemerick: Raynes: not a lot for people to stay for, I guess? :-(

15:00 ejackson: 130 !

15:00 cemerick: TimMc: last year was, what, $200 each?

15:00 amalloy: TimMc: probably about the same as last year

15:00 TimMc: Maybe my company will spring for it. :-P

15:01 technomancy: just confirmed the checksum mismatch in straight maven. it's (ironically) on bouncycastle

15:01 cemerick: technomancy: of all things! :-O

15:02 amalloy: technomancy: genius

15:02 fliebel: oh, dang, documentation… *goes of writing* ejackson, let me know when you get the quote.

15:03 ejackson: fliebel: you got it.

15:03 fliebel: huh, I got the quote?

15:03 amalloy: fliebel: american idioms tricking you again, sounds like

15:03 TimMc: fliebel: No, you'll get it. :-)

15:04 amalloy: "you got it": "okay, i'll do what you just said"

15:04 fliebel: I guess so… can;t we do the conj in Europe next time :P

15:04 Fossi: +1 ;D

15:05 raek: I need to make it to the conj too

15:05 in Europe would be nice...

15:05 Fossi: if it weren't such a pain to organise such a thing :/

15:06 fliebel: Fossi: I never tried it. What is the pain?

15:07 Raynes: Fossi: Wrong.

15:07 (inc fliebel)

15:07 sexpbot: ⟹ 1

15:07 amalloy: Raynes: only if you think he was +1 ing fliebel, rather than the idea of a euroconj

15:08 Raynes: raek: Man, Europe would require a passport and all sorts of nasty things, like a really long flight. You aren't worth it.

15:08 Fossi: i totally wouldn't want to +1 fliebel

15:08 Raynes: (dec euroconj) ; cause I'm selfish

15:08 Fossi: fliebel: mostly getting a location i guess, and then some

15:09 like talks/topics, food, etc pp

15:09 Raynes: I was almost hoping for a California conj this year. Would have given me an excuse to go to California.

15:10 gtrak: (inc inc)

15:10 sexpbot: ⟹ 1

15:10 ejackson: a caliconj

15:11 amalloy: Raynes: you need excuses? california is great, qed

15:11 Fossi: i've just been to the European Lisp Symposium, which was great, but that's because it was in town :)

15:11 TimMc: In Europe, everything is in town.

15:11 Fossi: more like, literally

15:11 Raynes: amalloy: I need a significant reason to spend money to travel to California.

15:12 TimMc: Where was the last conj held?

15:12 amalloy: come rob a bank

15:12 TimMc: same location

15:12 Fossi: :D

15:12 TimMc: Oh right... Rich lives in NC, yeah?

15:12 Fossi: best reason ever to go anywhere

15:12 "come here, rob a bank"

15:12 i can even see it in television ads

15:13 amalloy: Fossi: it worked for vegas. "come here, steal us silly, we're bad gamblers"

15:13 Fossi: did it?

15:13 americans must be dumber than i thought on average

15:14 all people i know from vegas are really good gamblers/poker players

15:14 cemerick: TimMc: Rich lives outside of NYC

15:14 TimMc: Who lives in NC then!

15:14 cemerick: Most of Relevance.

15:14 TimMc: aha

15:18 amalloy: Fossi: i don't think the residents are especially good gamblers; the point is that the casinos have a clear edge

15:19 Fossi: well, there are quite some people living in vegas making a living off bad poker players

15:19 amalloy: sure

15:19 Fossi: but yeah, that's more or less the only game where that's the case

15:19 and there's more money in the others

15:32 fliebel: Can I put docstuff on records? The docstuff of defrecord does not mention it.

15:33 kotarak: Records are classes not Vars.

15:34 fliebel: kotarak: But they implement IObj

15:34 kotarak: fliebel: the instances

15:35 fliebel: true

15:36 kotarak: fliebel: functions now also contain metadata (including the docstrings), but you can't type (doc MyRecord).

15:36 fliebel: maybe some kind of javadoc might emerge sometime...

15:36 fliebel: :)

15:36 I'll start writing /** doc */ above my record and see what happens.

15:39 raek: fliebel: you can put docstuff on protocols, though

15:39 fliebel: raek: I know, but thanks :)

15:48 gigamonk`: Hmmm, is there a design philosophy that leads 'get' to return nil if its first argument is not a map?

15:48 amalloy: gigamonkey: clojure hates exceptions

15:49 gtrak: gigamonkey, also it doesn't use {}

15:49 amalloy: &(get {:a 1} :b) ; same reason as this, i think

15:49 sexpbot: ⟹ nil

15:49 gtrak: or (), rather, nil is preferred over the empty set

15:50 gigamonkey: amalloy: well, there's a distinction one could draw--if one wished--between looking for a key that's not present in a map and looking for a key in something that is not a map.

15:50 amalloy: gigamonkey: fwiw, you can make it return something other than nil if you prefer, though i don't think you can easily distinguish between not-found and not-a-map using just get - ##(get 10 :k "Wait what?")

15:50 sexpbot: ⟹ "Wait what?"

15:51 hiredman_: gigamonkey: get is not map? if you want to test for the mappiness of a thing, get is not the tool to do it

15:51 amalloy: gigamonkey: feel free to draw that distinction yourself before calling get

15:51 hiredman_: ,(doc map?)

15:51 ,(doc get)

15:51 clojurebot: ping?

15:52 amalloy: or, if you want an exception, you could call the "maybe-map-thing" as a function: ##(10 :k)

15:52 sexpbot: java.lang.ClassCastException: java.lang.Integer cannot be cast to clojure.lang.IFn

15:52 gigamonkey: hiredman_: sure. And I can see the convenience of its behavior. On the other hand it makes it harder to catch inadvertant type errors.

15:52 amalloy: &({:k :v} :k)

15:52 sexpbot: ⟹ :v

15:52 hiredman_: gigamonkey: then go use scala, please /part the channel on your way out

15:52 gigamonkey: E.g. (get :foo {:foo 10}) => nil

15:53 amalloy: gigamonkey: wut. that's not a type error

15:53 is it? maybe it is. i never use get

15:53 &(get :foo {:foo 10})

15:53 sexpbot: ⟹ nil

15:53 gigamonkey: amalloy: well, it is if you meant to say (get {:foo 10} :foo)

15:53 amalloy: gigamonkey: i rarely need to actually use get

15:54 i just write ##(:foo {:foo 10})

15:54 sexpbot: ⟹ 10

15:54 hiredman_: https://github.com/clojure/clojure/blob/master/src/jvm/clojure/lang/RT.java#L620

15:54 gigamonkey: amalloy: well, the same thing happens with (:foo whatever) since it turns into a call got get, presumably.

15:54 cemerick: hiredman_: in a channel-purging mood, I take it?

15:54 amalloy: gigamonkey: yes, but you won't get the parameters out of order this way

15:54 gigamonkey: hiredman_: this isn't about static vs dynamic typing. It's about API design. You can make everything mean *something* bat that's not always the best policy.

15:55 s/bat/but/

15:55 sexpbot: <gigamonkey> hiredman_: this isn't about static vs dynamic typing. It's about API design. You can make everything mean *something* but that's not always the best policy.

15:55 amalloy: which is what you objected to in the (get :foo m) case

15:55 hiredman_: cemerick: I smell common lisp

15:55 gigamonkey: heh. Didn't know that would trigger the bot.

15:55 cemerick: hiredman_: Good enough. This is a polyglot boarding house.

15:56 amalloy: gigamonkey: pop quiz: do you find the execution of your s/foo/bar thing to be a desirable feature or annoying?

15:57 fliebel: Is this grammatically valid? "Returns a seq of pairs. Every pair is a set of keys whose objects' Rectangles intersect"

15:57 gigamonkey: amalloy: seems a little silly to me. But kind of cute.

15:57 hiredman_: cemerick: common lispers have an annoying habbit of complaining that clojure isn't common lisp

15:58 amalloy: fliebel: definitely okay grammatically. not sure i follow the actual meaning, specifically "every pair is a set of keys"

15:58 cemerick: hiredman_: And some people who like python complain that sexprs don't look like python. In neither case is it reason to wave someone away.

15:58 fliebel: amalloy: I'm open to better explanations. It returns somwthing like [#{:a :b}] which means :a and :b are colliding.

15:58 hiredman_: cemerick: if that is all they do, and they do it very vocally, I think it is

15:59 gigamonkey: hiredman_: and some folks just want to understand the difference. Certainly Lisps other than Common Lisp have a tradition of typechecking arguments dynamically.

15:59 Thus my question about whether there was a design philosophy that lead to the (slightly surprising) choice in the 'get' API.

16:00 cemerick: hiredman_: Well, gigamonkey isn't anywhere near being a troll, or a disturbance. Inviting a /part is just rude.

16:00 amalloy: fliebel: i'd say "returns a seq of sets. each set contains two objects whose rectangles intersect"

16:00 * cemerick gives way to on topic conversation

16:00 amalloy: saying that a pair "is a set" reads confusingly, to me

16:00 fliebel: amalloy: Not objects, they keys corresponding to the objects.

16:01 thorwil: fliebel: that "whose" makes me uneasy. how about "Returns a seq of pairs. Every pair is a set of keys belonging to intersecting rectangles (/rectangle objects)"

16:01 dnolen: gigamonkey: get is actually more generic in it's behavior than just applying to maps, it should

16:01 the docstring should probably updated

16:01 internally the runtime refers to coll, not map as the first arg.

16:01 gigamonkey: dnolen: so what else can it fruitfully be applied to?

16:02 amalloy: gigamonkey: anything that implements ILookup

16:02 builtins include maps, sets, and vectors

16:02 dnolen: instance of Map, array, string, objects that implement ILookUp, IPersistentSet

16:02 amalloy: &(get [1 5 8] 2)

16:02 sexpbot: ⟹ 8

16:03 fliebel: thorwil: The problem is that there are keys to look up an object and the objects have a Rectangle.

16:04 dnolen: gigamonkey: in your own code if you wish to enforce maps, preconditions are definitely worth looking into, just redefine get.

16:05 gigamonkey: define your own get in your own namespace I mean.

16:05 gigamonkey: I guess another question I could have asked is: is it considered good or poor form to take advantage of the fact that get (or :keywords as functions) will happily return nil if passed a non-map?

16:05 fliebel: "Returns a seq of sets. Every set contains two keys of objects that have intersecting Rectangles."

16:06 amalloy: fliebel: sounds okay to me. it seems a little awkward to be passing around keys to objects instead of the objects themselves, but that's part of your API (though it influences the docs)

16:06 gigamonkey: I was looking at some code that walked a tree of maps calling (:type node) as it went. I was wondering what was going to happen when it hit the leaves which were not maps.

16:06 So in this case it was handy, if a bit surprising to me, that it worked that way.

16:07 Speaking of which, could one use :foo as a dispatch function in a multi-method?

16:07 fliebel: amalloy: Objects "change", keys don't, so only keys are a reliable way to tell which object you're colliding with.

16:07 amalloy: gigamonkey: yes, for sure

16:08 gigamonkey: also, you've just made me realize that some code i wrote yesterday could have made use of the get-works-on-non-maps feature

16:08 gigamonkey: amalloy: great, I've unleashed a monster! ;-)

16:08 amalloy: probably not worth the extra documentation it would need, though

16:09 fliebel: I always assume everything works on everything unless proven otherwise. I'm still disappointed you can't dissoc a vector.

16:09 dnolen: gigamonkey: seems like fairly reasonable to think that get will always return nil based on what's going on the Java source if not given a type which it can handle. but perhaps something to bring up on the ML and get some more informed opinions.

16:11 gigamonkey: dnolen: I'd say the docs should at least say what types it accepts as arguments. If it's all types, that's fine but they should say so.

16:12 (Is the clojure type system a latice and if so what's at the top?)

16:12 dnolen: gigamonkey: sure, like I said worth bringing up on the ML.

16:12 amalloy: gigamonkey: lattices don't necessarily have a top; that would be a tree

16:12 however, it is in fact a tree, and the top is Object, since it's hosted on java

16:13 gigamonkey: amalloy: and all primitives are boxed?

16:13 amalloy: gigamonkey: ish

16:13 dnolen: gigamonkey: clojure interface and their relationships are quite slick, tho not well documented beyond Java source.

16:13 gigamonkey: 1.3 allows unboxed primitives to flow in and out of functions.

16:14 amalloy: real-java has primitives, and clojure can use them, but we're fairly limited in how. 1.3 will improve the situation but it still won't make primitives as first-class

16:15 dnolen: gigamonkey: Clojure version of structs, defrecord/type, can have unboxed primitive fields. you can have unboxed arrays of primitives.

16:15 ataggart: and unboxed vectors

16:16 dnolen: gigamonkey: 1.3 also ensures that float literals are treated as unboxed double, and integer literals as unboxed long.

17:59 gigamonkey: Uh, did clojure.org just go down or expire or something?

17:59 I'm getting a big fat register.com ad.

17:59 jla: looks fine to me

17:59 opqdonut_: works for me

18:00 Last Updated On:05-Apr-2011 13:09:16 UTC

18:00 Expiration Date:03-Apr-2013 14:24:30 UTC

18:00 sez whois

18:00 gigamonkey: Weird.

18:00 kephale00: its been down all day

18:00 i still don't have it

18:00 some folks have it cached

18:01 amalloy: gigamonkey: read the mailing list

18:01 there was an issue this morning, dns is propagating

18:01 jla: not cached, can do live searches

18:01 gigamonkey: amalloy: what mailing list?

18:01 kephale00: hm

18:02 clojurebot: hmm, maybe my repl is out of wack

18:02 kephale00: gotcha

18:02 amalloy: $google clojure google group

18:02 sexpbot: First out of 13300 results is: Clojure | Google Groups

18:02 http://groups.google.com/group/clojure

18:02 gigamonkey: Heh: "Discussions aren't available right now. We're sorry. Try again shortly."

18:03 amalloy: that's what happens when you use a startup like google to host your website

18:03 fwiw they load fine for me

18:03 (both the group page and clojure.org)

18:05 gigamonkey: So I was going to clojure.org to try and find more information about the implementation of maps in Clojure. Anyone have any good pointers to whre I can read about the actual data structures used?

18:06 amalloy: $google higher order persistent vector clojure hash

18:06 sexpbot: First out of 253 results is: Clojure - data_structures

18:06 http://clojure.org/data_structures

18:06 amalloy: hmph

18:06 gigamonkey: higher order is a blog someone (rich?) runs, with a good description of that topic

18:07 technomancy: gigamonkey: http://blog.higher-order.net/2009/02/01/understanding-clojures-persistentvector-implementation/ <= for vectors

18:07 I believe the others are taken from Okasaki?

18:14 gigamonkey: technomancy: yeah, I was hoping for some pointers into what things in particular to read about in Okasaki.

18:14 But thanks for the link, that's a start.

18:23 So fn? returns false for keywords. Is there a predicate for things that implement IFn?

18:23 brehaut: gigamonkey: ifn?

18:24 gigamonkey: Tada! Thanks.

18:24 amalloy: brehaut: too easy

18:24 brehaut: amalloy: im all about the low hanging fruit

18:24 seancorfield: ,(find-doc "ifn")

18:24 clojurebot: -------------------------

18:24 clojure.core/ifn?

18:24 ([x])

18:24 Returns true if x implements IFn. Note that many data structures

18:24 (e.g. sets and maps) implement IFn

18:25 gigamonkey: Though that's a pretty gross name.

18:25 How about callable?

18:25 brehaut: gigamonkey: because callable is different to IFn

18:25 gigamonkey: I don't see it in the index.

18:25 amalloy: gigamonkey: it's a java interface

18:26 brehaut: gigamonkey: callable and runable are java interfaces, ifn is a clojure interface

18:26 amalloy: gigamonkey: still: the power is yours! (def callable? ifn?) ; bam!

18:26 seancorfield: it's fairly consistent with many of the other does x implement y function names :)

18:26 ,(doc reversible?)

18:26 clojurebot: "([coll]); Returns true if coll implements Reversible"

18:27 seancorfield: ,(doc sequential?)

18:27 clojurebot: "([coll]); Returns true if coll implements Sequential"

18:27 gigamonkey: I guess I'm just wishing Clojure were not sitting on top of Java.

18:27 seancorfield: etc...

18:27 amalloy: gigamonkey: a misguided desire. it couldn't get nearly as popular that way

18:27 * technomancy remembers wishing that

18:28 gigamonkey: amalloy: sure. But I wrote a book about Common Lisp. I don't care about popular. ;-)

18:28 technomancy: now /me just wishes the JVM took unix seriously

18:28 amalloy: fine fine. couldn't have as many useful libraries available either

18:29 it's very handy to just reach out and grab some java

18:30 seancorfield: if clojure didn't run on the jvm, i wouldn't be using it (even tho' i like lisp)

18:31 brehaut: seancorfield: probably because rich would still be writing the jit, gc, binary format, build tools, etc :P

18:31 seancorfield: i can't use lisp in my day-to-day work - but i can anything that runs on the jvm

18:31 i think it's great that we have so many languages targeting the jvm (for all its faults)

18:31 i can mix clojure, scala, groovy, jruby, jython, cfml...

18:32 devn: we're living in a polyglot world

18:32 seancorfield: ok, so i'm not actually using all of those... but i have the choice, and i like choice!

18:33 devn: choice is great until you have so many of them you become paralyzed

18:33 technomancy: is jython still active?

18:33 devn: i dont believe so

18:33 err i think microsoft killed iron____

18:33 but im not sure about jython

18:33 jla: usually wish that clojure didn't run on jvm. recently been programming python. now missing maven.

18:34 technomancy: a former jython lead came to one of the early seajure meetings

18:34 devn: technomancy: does seajure make its meeting available online

18:34 brehaut: the former jython (Jim Huginin) lead stopped working on jython to work on iron python i believe

18:34 seancorfield: jython looks pretty active to me... 2.5.2 released a month ago... django 1.2.0b1 released too

18:34 brehaut: and jython isnt dead

18:35 technomancy: devn: we don't have presentations, so that wouldn't really work

18:35 unless you mean being able to SSH into the tmux session as it's happening... we could arrange something =)

18:35 gigamonkey: Does clojure have a construct you can use when you want a macro to expand into multiple top-level forms (e.g. multiple defn's or something)

18:35 devn: im trying to get a meetup group going here in Madison, WI -- we have so many folks to the south in Chicago and ive been doing the meetup group regardless

18:35 technomancy: actually... that sounds great.

18:35 brehaut: jython has just always lagged behind cython and has (for some reason) got a lot of py community antipathy, so it gets a lot less attention than it really deserves

18:36 gigamonkey: (do (def …) (def …) …)

18:36 technomancy: devn: well without audio I'm not sure how interesting it would be. crowded coffee shops aren't the best recording/speakerphone environments.

18:36 gigamonkey: brehaut: thanks.

18:36 kotarak: How can I force a full gc?

18:37 gigamonkey: Hmmmm. I don't see 'do' in the API table of contents.

18:37 devn: technomancy: what if I bankrolled a decent mic or something to help out in that department?

18:37 amalloy: gigamonkey: it's a special form: ##(doc do)

18:37 sexpbot: ⟹ "Special Form: Please see http://clojure.org/special_forms#do"

18:37 brehaut: kotarak: i think you can call System.gc() or something, but it only a hint?

18:38 gigamonkey: Yup. Just got there.

18:38 kotarak: It seems that things are not released, where they should be. But I don't know whether this some gc or not.

18:38 amalloy: gigamonkey: incidentally, aside from the valuable learning experience of doing this yourself once, you don't need to write a macro to expand into a do form yourself

18:38 technomancy: devn: sorry to backtrack on my claim; heh. I keep pretty busy running the show to add something like that, but you could post to the mailing list and see if someone could help you out there.

18:39 devn: technomancy: no worries, i dont blame you -- it would not be easy, but even just looking at the screen sessions would be nice

18:40 amalloy: http://richhickey.github.com/clojure-contrib/test-is-api.html#clojure.contrib.test-is/do-template and https://github.com/amalloy/amalloy-utils/blob/master/src/amalloy/utils/macro.clj#L26 both do that for you already

18:40 technomancy: devn: the code always goes on http://github.com/Seajure in its final form too

18:41 gigamonkey: amalloy: actually I was thinking of generating different top-level forms, not looping like those seem to.

18:41 I want to define a defn and maybe a few defmethods.

18:41 amalloy: gigamonkey: ah. for totally different forms, yes

18:43 wait, i don't get it. either you're using a macro only once, in which case either you're not saving any typing or you could use anon-macro; or you're defining a macro that expands into various things and then calling it more than once - in that case, macro-do would be useful

18:45 gigamonkey: I want, say, (deffoo bar [baz quux]) to expand into a (defn new-bar ...) and a (defmethod something :bar ...) and a (defmethod somethingelse :bar ...)

18:46 Or rather, all those things wrapped in a 'do'

18:47 Raynes: gigamonkey: You're the Practical Lisp guy, aren't you? :o

18:47 gigamonkey: Raynes: yes. Practical Common Lisp, to be absolutely precise.

18:47 Raynes: Pleasure to meet you. <3

18:47 gigamonkey: Likewise.

18:48 Raynes: Welcome to Clojureland.

18:49 amalloy: gigamonkey: that's pure gold. Raynes is always annoyed with people saying lisp when they mean common lisp, and now the tables have turned

18:50 Raynes: amalloy: I actually thought the book was called Practical Lisp. It's been a long time since I looked at it.

18:50 amalloy: i know

19:12 gigamonkey: How do I tell a multimethod to use a specific hierarchy?

19:12 Ah :hierarchy option

19:15 gmaggior: hello. Sorry for newbie question. I'm using clojure on a ubuntu bash terminal, when I press up_arrow, left_arrow ,etc to edit the line strange characters appear. Is there a way to edit the clojure REPL command line?

19:16 gigamonkey: What's wrong with this: (defmulti foo identity :hierarchy (derive (make-hierarchy) :foo :bar))

19:17 Gives me: java.lang.ClassCastException: clojure.lang.PersistentArrayMap cannot be cast to clojure.lang.IRef (NO_SOURCE_FILE:0)

19:18 amalloy: gmaggior: raw console input doesn't provide such niceties. in the long run you'll be best off installing leiningen or cake, but your path of least resistance is to run rlwrap <whatever command you use for clojure> (apt-get install rlwrap if you don't have it)

19:19 gigamonkey: derive doesn't return the hierarchy object afaict

19:19 gigamonkey: Okay, so how do I get it?

19:19 It doesn't modify the hierarchy in place.

19:19 amalloy: ,(doto (make-hierarchy) (derive ::a ::b))

19:19 clojurebot: {:parents {}, :descendants {}, :ancestors {}}

19:19 amalloy: hm

19:20 gmaggior: Thank you very much amalloy

19:21 amalloy: gigamonkey: i lied. it does return the hierarchy

19:21 $source defmulti

19:21 sexpbot: defmulti is http://is.gd/wi5uPO

19:22 amalloy: gigamonkey: defmulti is a macro; it isn't calling that code

19:22 gigamonkey: At any rate, this fails too: (defmulti baz identity :hierarchy (make-hierachy))

19:22 Ah.

19:22 amalloy: you need to pass it a literal symbol, obtained via an earlier make-hierarchy

19:22 i guess

19:23 gigamonkey: No, that's not it.

19:23 gmaggior: amalloy, rlwrap clojure worked fine!

19:23 gigamonkey: Which I'm glad about because that would be terrible.

19:23 amalloy: gigamonkey: inclined to agree

19:24 gigamonkey: i think it wants a map, not bare kv pairs

19:25 gigamonkey: java.lang.Exception: The syntax for defmulti has changed. Example: (defmulti name dispatch-fn :default dispatch-value)

19:25 amalloy: so i see. this is getting silly; i confess i don't define new hierarchies often (ever)

19:26 (defmulti foo class :hierarchy (ref (make-hierarchy)))

19:27 i can understand the design descision that led to requiring that to be a ref, but i don't especially like it

19:29 and it certainly ought to be documented better

19:30 gigamonkey: ^, if you missed it. better?

19:31 gigamonkey: amalloy: yup, that does the trick.

19:32 That seems especially goofy since defmulti is a macro. If it needs a ref, why not take care of it itself.

19:32 amalloy: gigamonkey: i suspect it's so that you can see the hierarchy developing yourself, or share it among multiple defmultis

19:32 without them each discovering their own version of the dependency tree

19:33 gigamonkey: I don't understand what you just said but that's probably just me.

19:35 amalloy: gigamonkey: i'm not sure it makes sense for keywords, but consider the hierarchy for java classes. if you have a method defined for, say, 20 different classes, then the first time that multimethod sees a class it's never seen before, it has to try isa? on all the defined dispatch values

19:35 when it finds a match, it updates the ref to reflect that (or could; i haven't read the source). if you have multiple defmultis all using the same hierarchy, it saves duplicated work to have them all use the same ref

19:37 gigamonkey: Okay. So if I say (def h (ref (make-hierarchy))) is there a way for me to modify the hierarchy?

19:38 amalloy: gigamonkey: (alter h derive ::a ::b)

19:39 gigamonkey: "No transaction running"

19:39 amalloy: (dosync (alter...))

19:39 i usually use atoms rather than refs :P

19:39 (not that you have a choice here)

19:40 but you can do all your derivings in a functional way, and then just ref the final result, if you never want to change it thereafter

19:40 gigamonkey: Right.

19:40 amalloy: ,(-> (make-hierarchy) (derive ::a ::b) (derive ::c String) ref)

19:40 clojurebot: java.lang.AssertionError: Assert failed: (instance? clojure.lang.Named parent)

19:40 amalloy: ,(-> (make-hierarchy) (derive ::a ::b) (derive ::c ::a) ref)

19:40 clojurebot: #<Ref@f6fc62: {:parents {:sandbox/c #{:sandbox/a}, :sandbox/a #{:sandbox/b}}, :ancestors {:sandbox/c #{:sandbox/a :sandbox/b}, :sandbox/a #{:sandbox/b}}, :descendants {:sandbox/a #{:sandbox/c}, :sandbox/b #{:sandbox/a :sandbox/c}}}>

20:39 ignacio: anyone used lein-axis?

20:46 pickles: bit of a (probably n00b related) issue: I have three clojure scripts: A, B and C, all three in namespace x. B defines type-b (deftype), C uses type-b, A includes both B and C. I'm getting a "No matching method found" error from the attempted use in C.

20:50 tomoj: you probably shouldn't have three scripts in the same namespace. not that this answers your question..

20:51 pickles: mmm

20:52 would you suggest one ns per script?

20:52 they're all part of the same program

20:53 tomoj: yeah, and namespaces should correspond to the filesystem, so (ns foo.bar.baz) should go in src/foo/bar/baz.clj

20:53 pickles: ah, that might have something to do with it

20:53 tomoj: also, you shouldn't have any "single-segment namespaces", like (ns foo)

20:53 pickles: one of the files is in a different directory

20:54 mmm

20:54 tomoj: when you say (use 'foo.bar) or, equivalently in the ns macro, (ns baz.bing (:use foo.bar)), clojure will look for foo/bar.clj on the classpath

20:54 if you have other files also in the foo.bar namespace, clojure won't find them, you'd have to load them yourself

20:55 pickles: mmk

20:55 i'll have to change one of the files

20:56 the other is a "config" file which I'll still probably do a load-file with

20:57 thx tomoj, i'll have to poke around

20:57 and als ortfm

20:57 *also rtfm

20:58 another quick question: the "read" function seems to be reading in symbols, whereas the documentation iirc lead me to believe it would read a single character at a time?

20:58 *led

21:00 technomancy: pickles: the .read method on certain reader classes can read a char at a time, but the read function reads a single form.


21:00 hiredman_: pickles: read reads in a clojure form

21:00 ,(doc read)

21:00 clojurebot: "([] [stream] [stream eof-error? eof-value] [stream eof-error? eof-value recursive?]); Reads the next object from stream, which must be an instance of java.io.PushbackReader or some derivee. stream defaults to the current value of *in* ."

21:01 hiredman_: "Reads the next object from stream"

21:01 pickles: wonder where I got the impression it read a single character then...

21:01 i know the java streams do single chars but I thought i saw that on the clojure read method too

21:01 ah well

21:01 many thanks all

21:09 MiggyX: Has anyone managed to get congomongo to build?

21:11 amalloy: MiggyX: you really need to build it, not just use it?

21:29 ephcon: hey has anybody here messed around with scriptjure?

21:29 in particular, I'm trying to figure out a js for loop in scriptjure

21:29 https://github.com/arohner/scriptjure

21:42 test: clojurebot: (def x 5)

21:42 clojurebot: api examples is http://en.wikibooks.org/wiki/Clojure_Programming/Examples/API_Examples

21:42 MigZ: hmm, any obvious reason why when I set a namespace, clojure can't find any of the libraries (such as clojure-contrib) that it could see before?

21:43 amalloy: MigZ: from the information given, the only answer certain to be correct is "you did something wrong"

21:44 MigZ: amalloy: http://www.pastie.org/1761391 I didn't know if there was a common stupid thing to do wrong :)

21:45 test: sexpbot: (def x 5)

21:45 amalloy: MigZ: duck-streams and str-utils are part of clojure.contrib; your ns decl acts as if you wanted to include four independent libraries

21:46 you want (:use (c.c d-s s-u) (s.c)

21:46 test: sexpbot: (println "Hello World")

21:46 amalloy: &("hello world")

21:46 sexpbot: java.lang.ClassCastException: java.lang.String cannot be cast to clojure.lang.IFn

21:46 amalloy: oops

21:46 &"hello world"

21:46 sexpbot: ⟹ "hello world"

21:46 test: ahh thanks

21:47 &(defn foo [x] (inc x))

21:47 sexpbot: java.lang.SecurityException: You tripped the alarm! def is bad!

21:47 test: &(range 1)

21:47 sexpbot: ⟹ (0)

21:47 amalloy: MigZ: i know str-utils is extremely old, and i think duck-streams is similarly but i'm not sure. you probably want to use something newer as well

21:47 test: &(range)

21:47 sexpbot: java.lang.OutOfMemoryError: Java heap space

21:48 amalloy: clojure.string includes most of the features that ye olde str-utils did

21:49 MigZ: amalloy: Just took it from the clojure book. :) Will look into clojure.string

21:49 test: &(dorun (cycle '(1)))

21:49 sexpbot: Execution Timed Out!

21:49 MigZ: Well I've gotten rid of the use errors, now getting 'Unable to resolve symbol: mongo! in this context' - still getting closer ;)

21:50 amalloy: MigZ: errrr i included an error in my suggested ns decl

21:50 there should not be a paren before s.c

21:51 MigZ: amalloy awesome, that fixed it :)

21:51 amalloy: just keepin you on your toes :)

21:52 seriously though it took me a hellishly long time to fully absorb all clojure's namespace subtleties. it's surprisingly complicated

21:52 MigZ: amalloy: hopefully I'll pick it up at some point - I'm hoping to get to grips with clojure. How have you found it? I do a lot of work that needs to be paralelised :)

21:53 amalloy: MigZ: asking someone in #clojure what they think of clojure is liable to yield predictable results

21:54 MigZ: amalloy: well I wouldn't expect a hugely negative response - but perhaps a fair one of how it fits to their various workloads :)

21:54 amalloy: well, i'm still stuck with php for my day job

21:55 MigZ: amalloy: ah

21:55 amalloy: i find a lot of code i try to write is like "arrrrgh this should take two ##@%! lines in clojure"

21:55 sexpbot: java.lang.Exception: Unable to resolve symbol: %! in this context

21:55 amalloy: haha sorry sexpbot

21:55 MigZ: hah

21:59 amalloy: in fact here's a good example from today. i had, in php, something like Map<String, List<String>> (really just a bunch of arrays in php, but using java to indicate what the types were)

22:01 ataggart: amalloy: every day I was saying that. Then I just up and quit my job.

22:01 amalloy: i wanted to do something with each "pair" of adjacent items in each list. in clojure: ##(let [listmap {:a [4 7 8 9] :b [1 3 8]}] (for [[k v] listmap, [src dst] (partition 2 1 v)] [k src dst]))

22:01 sexpbot: ⟹ ([:a 4 7] [:a 7 8] [:a 8 9] [:b 1 3] [:b 3 8])

22:03 amalloy: ataggart: it's an idea with some appeal, for sure. could probably head just a little south and pal around with amitrathore and ztellman

22:04 ataggart: heh, I went the other way, north to Vancouver.

22:06 tomoj: amalloy: yes.

22:07 amalloy: tomoj: agreeing with anything in particular?

22:07 tomoj: my boss who also knows clojure is someone not driven to "arrrrgh" by php, but I can't help it

22:07 s/someone/somehow/

22:07 amalloy: tomoj: you can do a surprising number of functional things in php, they're just atrociously verbose

22:08 tomoj: it's a sickening pile of nasty to me

22:08 amalloy: it's made a little worse because our general manager slash software lead loves php and has a coding style nearly as eccentric as rhickey's

22:08 tomoj: "eccentric in a good

22:08 er. "eccentric" in a good way?

22:09 ..presumably not

22:09 amalloy: tomoj: *chuckle* good guess

22:10 if( isset($data[$key]) ) $data[$key]++; else $data[$key] = 1; // but with newlines

22:10 instead of just @$data[$key]++;

22:12 tomoj: I guess I'm not qualified to hate php

22:12 amalloy: eh?

22:12 tomoj: I don't know it very well

22:12 amalloy: we have an open door policy

22:12 anyone can hate with us

22:13 tomoj: that @ thing is just "ignore errors", right?

22:13 amalloy: yes

22:13 tomoj: the fact that that ends up setting the value for the key to 1 is somewhat baffling

22:13 amalloy: tomoj: $var, where nobody has defined var yet, evaluates to 0

22:14 along with issuing a warning

22:14 tomoj: ah

22:15 amalloy: ANYWAY. if you're in a language designed to let you be sloppy, why be sloppy *and* verbose

22:15 tomoj: :D

22:25 amalloy: tomoj: are you using 5.3? the new closure support is a big help, even if they are tedious to use

22:26 tomoj: yep

22:27 that's the function ($foo) use ($bar) {} stuff?

22:27 amalloy: yeah

22:28 MigZ: right, now to write this loop code in a functional way... should prove to be interesting ;)

22:28 yayitswei: what's the best way to get status updates from a long-running process? e.g. (doall (map #(process-keywords-from (days-ago %))) (range 0 30)))

22:28 tomoj: `array_filter($pub, function ($item) use ($tid) { return $item['tid'] == $tid; });`

22:28 `(filter (comp #{tid} :tid) pub)`

22:29 yayitswei: I put a println in the days-ago function, but it does'nt print until after the whole thing runs

22:29 tomoj: arrrrgh

22:30 amalloy: yayitswei: blurg. doall + map + anonymous function reeks. do you need the results of the map, or are you doing it strictly for side effects?

22:31 yayitswei: strictly for side effects

22:31 thakns for pointing it out btw, would love a better solution

22:31 amalloy: doseq

22:31 (doseq [d (range 30)] (process-keywords-from d))

22:32 yayitswei: and why is that better than doall?

22:32 amalloy: (a) doall forces the whole sequence to be realized all at once, taking up more memory

22:32 while doseq throws away intermediate results

22:32 yayitswei: oh! that's good to know

22:33 amalloy: (b) (map #(whatever %) coll) is just an ugly way of writing (for [x xs] (whatever x))

22:34 doseq uses the same binding style as for, and gives you the strict, side-effect behavior you want

22:34 (of course, when you just want to call a simple function, (map f coll) is nicer than (for [item coll] (f item)); but if you have to define the function on the fly, for is nicer

22:34 )

22:35 MigZ: if you have a hash key that has a space in it, how do you quote it?

22:36 amalloy: &(keyword "stupid key with a space")

22:36 sexpbot: ⟹ :stupid key with a space

22:37 MigZ: amalloy: working with some data from MongoDB - it has embedded documents as well as tag names that contain spaces

22:37 amalloy: yeah, i know

22:37 MigZ: amalloy, I meant my particular case :)

22:38 unfortunately when I did the mongodb book, I didn't learn how to use it with clojure lol

22:38 amalloy: MigZ: i don't understand

22:38 are you saying my suggestion doesn't work for you for some reason?

22:39 yayitswei: amalloy: seems to work. much faster, too. but, the println is still getting shown after the whole thing completes

22:39 MigZ: amalloy, I just get Unable to resolve & in this context

22:40 but that's probably something I'm doing elsewhere so checking that nwo...

22:40 amalloy: &(apply println '(& is my activation trigger))

22:40 sexpbot: ⟹ & is my activation trigger nil

22:40 amalloy: yayitswei: could be output buffering

22:41 MigZ: could try using (flush) but that might affect performance

22:41 yayitswei: should (flush) help?

22:41 just tried that, but it doesn't seem to have an effect

22:42 amalloy: i'm guessing process-keywords is itself lazy

22:46 yayitswei: amalloy: i changed process-keywords to use doseq -- is that lazy?

22:47 amalloy: it is not

22:53 MigZ: amalloy so if you had a hash called 'test' containing a key called 'Stupid Key', how would you print it? So far everything I've tried has blown up :)

22:54 amalloy: &(let [k (keyword "Stupid Key") test {k 10}] (k test))

22:54 sexpbot: ⟹ 10

22:55 MigZ: amalloy, hmm is it that hideous because of the stupid space?

22:57 amalloy: life sucks, and then you die

22:58 MigZ: amalloy yes but I'm hoping it might suck less lol

22:59 the current plan is to convince people here that clojure is nicer and faster than what we're currently using :)

23:04 trptcolin_: if i want to see if a given thing implementing IPersistentMap is a type / record vs. one of the clojure.lang maps (PersistentArrayMap, PersistentStructMap, PersistentHashMap, etc), am i going to have to go through and type-check?

23:05 got something i need to serialize where the reader might not have the deftype/defrecord classes imported...

23:08 brehaut: trptcolin_: im not quite sure i follow, but map? returns true for a record instance for me

23:08 trptcolin_: right, me too. i want something that distinguishes records/types from "regular" maps

23:09 so i can count on being able to deserialize a map-like thing without worrying about dependencies besides what's in clojure.core

23:09 brehaut: trptcolin_: ah right my bad

23:12 trptcolin_: my use case is actually such that i can do (into {} thing-thats-like-a-map) and be done with it either way (it's guaranteed to be small)

23:12 brehaut: trptcolin_: well a deftype will only be map? => true if it explicitly implements IPersistentMap

23:12 trptcolin_: i actually am not sure what this thing i have is (record vs. type), but it's definitely mappy

23:14 i'm just going to dump it into a hashmap, that'll work

23:14 brehaut: (type thing) will tell you for certain

23:14 trptcolin_: yep

23:14 well... it'll tell me the class. which may be a record or type :)

23:26 no_mind: what is the best way to return an error from a function. I have a function which returns a map after adding a key/value pair to map but if the key already exists it should return a warning/error indicating key exists.

23:28 brehaut: no_mind: 'best way' is hard to answer in a general sense.

23:29 ataggart: who consumes the warning/error? If it;s the caller of the add function, then just find out beforehand

23:29 (if-not (contains? m k) (assoc m k v))

Logging service provided by n01se.net