#clojure log - Oct 03 2008

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

0:35 johnwayner: Hopefully this is a FAQ: I've gotten the src and 'mvn install'd it. But when trying to start up the repl, it just hangs. No input is being read and no output printed on the screen. Java is 1.5.0. Platform is Windows 2003 server. TIA

0:36 arohner: how are you starting the repl?

0:36 johnwayner: java -cp target/clojure-lang-1.0-SNAPSHOT.jar clojure.lang.Repl

0:37 arohner: I've always used ant

0:37 though I would assume they both work

0:38 johnwayner: I didn't get any errors. And the jar is definitely there.

0:38 Strangely, I tried just throwing some debug println's in the Repl main(), and they aren't showing up either.

0:38 I may have other java issues, I suppose.

0:39 arohner: what terminal are you using?

0:39 johnwayner: I've tried the standard "Command Prompt" and M-x shell in emacs

0:39 ...which should be the same really

0:41 I'll play around some more. I am using a pre-boxed java set up that my company has put together. I'll try just using a stand JVM installation.

0:44 Hmmm... musta been something there. It's working on a 1.6 JRE I had lying around.

0:44 Thanks.

1:16 arohner: johnwayner: good

2:23 rk98x03: Morning gents, can somebody please stimulate my sense of (map (fn [])) ? :) I have a list of titles, and each title has subsequent subtitles. I need to map them out into an array, so that

2:23 title1-sub1-sub2-sub3

2:23 maps to "title1: sub1" "title1:sub2" "title1:sub3"

2:23 and so forth

2:27 Lau_of_DK: ok, simplified, if I want an infinite sequence of the word "hi", how do I make it?

2:28 So that (take 1 seq) = "Hi", take 2 = "Hi" "Hi"

2:31 k got it

2:31 thanks for listning

3:06 avida: Lau_of_DK: (take 3 (iterate #(str % " " "hi") "hi"))

3:06 hrm, that only creates strings

3:07 this will return sequences: (take 3 (iterate #(conj % "hi") (list "hi")))

3:18 Lau_of_DK: avida , thanks, you can also (replicate 1000 "hi")

3:18 There are a few options

3:19 avida: ha, i totally misunderstood how take worked, thanks

3:21 you can use (cycle (list "hi")) too

3:24 Lau_of_DK: oh that was a good one :)

3:24 my first was (for [x (range 1000)] "hi")

3:39 jdz: Lau_of_DK: it looks like 1000 is infinity for you...

3:40 Lau_of_DK: hehe, its about 995 hits more than I expect to get at the most

3:40 Anyway, I'm having some trouble outputting the object[][] type to Java, how would I do that?

3:41 ex (to-array [(to-array [1 2]) (to-array[1 2]) ...]) would to be an array within an array, but it still fires a ctor argument error

3:49 jdz: Lau_of_DK: how about (to-array [[1 2][1 2]]) ? i admit i have started looking at clojur only yesterday

4:30 Lau_of_DK: same result im afraid

4:35 jdz: the form i mentioned works without errors for me...

4:35 Lau_of_DK: I see that Chouser has posted something like a bug-report on the issue

4:35 http://paste.lisp.org/display/61639/xml

4:36 remove the /xml from the url

5:14 achim_p: Lau_of_DK: question still open? try to-array-2d

5:14 reason is: to-array constructs an array of objects, without conveying information about the types inside. so an array of arrays looks like a 1D array of objects to java. see also (doc into-array)

5:44 Lau_of_DK: achim_p, still open, but thanks that was a good suggestion, I didnt find that procedure documented on the website, but I'll give it a go

5:53 achim_p, you got a sec?

5:55 I actually think it working now, it constructs like it should, but the JTable Im populating just hangs afterwards

5:56 Im getting some ArrayIndexOutofBounds, which is weird since I never assign a size

6:00 achim_p: mmh, hard to say. are the inner arrays all equal-sized? maybe a jtable doesn't like ragged 'matrices'. i don't know much about jtables, though

6:03 lisppaste8: Lau_of_DK pasted "2d array w. bad dimensions" at http://paste.lisp.org/display/67849

6:03 Lau_of_DK: achim_p, this routine digs into an xml structure thats like <problem> <title> bla </title> <solution> blub </solution> </problem>

6:03 And its supposed to return "title" "solution"

6:03 2d

6:04 jdz: Lau_of_DK: the code layout sucks to be honest.

6:04 Lau_of_DK: the layout?

6:05 H4ns: rather offensive usage of white space :)

6:05 jdz: Lau_of_DK: and you are still putting arbitrary constants in your code when you have been given a solution that does not involve doing so...

6:05 Lau_of_DK: okay, when you girls are done prettying up, could you look at the actual code?

6:05 H4ns: *g*

6:05 jdz: Lau_of_DK: the problem is we can't see the code...

6:06 H4ns: but really, get an editor that does the identation right so that it is easier to just read it.

6:06 as, say, an act of politeness.

6:07 Lau_of_DK: noted

6:07 achim_p: Lau_of_DK: what does (map (fn [x] (get-problem x)) titles) return?

6:08 Lau_of_DK: the function (get problem) is also pasted, its supposed to return a 1d array like ["title" "solution"]

6:08 Which then should be wrapped in another array

6:08 so its like [["title1" "sol1"] ["title2" "sol2"]]

6:09 H4ns: did you try it? does it do so?

6:09 achim_p: yes, i can see what it should do, but does it actually? ;)

6:09 Lau_of_DK: Positively maybe

6:09 achim_p: please try the map call in isolation, and print the result

6:09 Lau_of_DK: user=> (get-problem "Bad Cable")

6:09 (["Bad Cable" "Try with another cable"] ["Bad Cable" "Try wifi"] ["Bad Cable" "I

6:09 nform hotel of broken cable in room."])

6:11 H4ns: just as it would be easier to read: (fn [x] (foo x)) is equivalent to just foo, no?

6:12 Lau_of_DK: yea, im using map to cycle all the xml hits

6:14 H4ns: so, what does (xml-> w-xml :problem :title text) actually return?

6:14 isnt that a sequence of sequences?

6:14 Lau_of_DK: The return the text from all xml nodes in /problem/title/

6:15 user=> (xml-> xml :problem :title text)

6:15 ("--- INFO ---" "3.rd MAC" "Bad Cable"

6:15 ...

6:16 H4ns: looks proper. i'd freely insert some print statements at this point :)

6:17 Lau_of_DK: huh?

6:17 achim_p: and you made sure that get-problem returns a 2-tuple for each of these?

6:18 Lau_of_DK: No im not 100% sure - how can I be +

6:19 achim_p: i think you'll have to make sure. i think either the first row of the matrix or the maximum of row sizes serves as an implicit size declaration for jtable.

6:20 (that's wild guessing)

6:20 H4ns: Lau_of_DK: it does not look as if there is a way for get-problem to return anything but an array of seqs

6:20 no, a seq of arrays really

6:20 Lau_of_DK: print statements as in "make the program print what it is doing to trace the problem"

6:21 Lau_of_DK: with common lisp, i'd trace get-problem, but clojure does not have trace on the repl yet, or does it?

6:22 Lau_of_DK: no it doesnt

6:22 Ok, I'll have to hit this again on monday, thanks for the input guys

6:22 H4ns: Lau_of_DK: one last thought:

6:23 Lau_of_DK: shoot

6:23 H4ns: Lau_of_DK: what happens if get-problem returns nil?

6:23 could solutions be nil at any time?

6:23 Lau_of_DK: I suppose I get an array of nils

6:23 H4ns: ah, no. :)

6:24 well, without the input data set, proper formatting and some more clojure experience it is just guesswork. :)

8:21 prunedtree: how small can a deployable and standalone "hello world" in closure ? (including all the JVM machinery)

8:34 H4ns: depends on much time you want to invest stripping down the jre

8:35 clojure itself is below 500k, but the jre as distributed uses around 54 mb on-disk

8:35 prunedtree: ok

8:36 I'm extremely unfamiliar with Java (the platform)

8:37 how does it perform as a desktop deployement ? Is it common to deploy application along with their own java runtime ?

8:37 H4ns: yes. shrink-wrapped applications come with their own jre.

8:38 prunedtree: Is there any issue distributing commercial apps this way ? (regarding sun's licencing on the jre for instance)

8:39 H4ns: any issue, well. there is a license agreement, but you can distribute the jre at no cost if you follow sun's guidelines.

8:40 prunedtree: ok, so it's viable for commerical desktop applications

8:41 H4ns: certainly

8:41 rhickey: prunedtree: sure, look at IntelliJ for instance

8:41 prunedtree: with all the web madness, some language seem to think it's 'all okay' not to be distributable because they run on servers anyway

8:42 as I said, I'm scarily ignorant about Java (the platform/the language)

8:42 I know how sun's JVM internals works very well, but that's because I know the roots of it (not java)

8:43 rhickey: prunedtree: there's Java Web Start too

8:43 prunedtree: how fast does the JVM boot these days ? haven't tried for years

8:43 rhickey : oh great, you are on IRC :)

8:43 the web is very scarce on implementation details of closure

8:44 rhickey: well, there is the source

8:44 prunedtree: I've tried to read everything I could find on clojure. I've watched the 'clojure for lisp programmers' screencast. looked very good

8:45 I don't come from a Lisp background, but from smalltalk. so Java always looked like a regression to me. but the way clojure does polymorphism looks nice

8:46 * H4ns had a very pleasant experience with the xsocket asynchronous communications library this morning. it is impressive how well clojure interacts with java, and i'm looking forward to writing more applications, less infrastructure in the future. :)

8:46 prunedtree: I have no idea how to setup a Java environnement and so on... I wonder how many clojure newbies have no idea how to do Java at all

8:46 rhickey: H4ns: great! it's been fun watching you dive in

8:47 H4ns: prunedtree: i have used java a little, but only a little. it is a relatively friendly environment to work in, and most stuff is usually described from a professional or enterprise perspective.

8:48 prunedtree: that's great. actually, I've always been tempted to use the JVM given the great compiler/GC/threading technology

8:48 but in my memories it could take dozens of seconds to boot... and I'd really like my applications to boot under 2 seconds

8:49 H4ns: rhickey: i want member, at least. find would be nice, too, but given that the standard library is rather minimal, (first (member ..)) would do

8:50 prunedtree: I've looked into what can be done with JNI, and I've seen that there have been many many changes over the years

8:50 It used to be ungodly slow

8:50 H4ns: prunedtree: all the java programmers i know avoid the jni at all cost.

8:50 rhickey: H4ns: you've seen: http://groups.google.com/group/clojure/msg/ff8777fc5f5d0157 ?

8:51 prunedtree: H4ns : my idea is quite simple. I have a single JNI method to implement

8:51 with { return getBufferAddress(...)() } in the body

8:51 H4ns: rhickey: yes, that is what i am referring to.

8:52 prunedtree: (ie, a native call on a bytebuffer)

8:52 plus a hack to get the base address of nio direct buffers

8:52 with that, you can do anything

8:52 rhickey: It's been an experiment of mine to see how long people can go without them - the answer is, pretty long!

8:53 A nice thing about not having them is it discourages slow code, people use the associative structures more rather than using lists when inappropriate

8:54 but I understand their utility for small things

8:54 prunedtree: re JNI. the thing is, I want to write very high performance apps, and clojure will not be fast enough

8:54 it's not because of clojure. even java isn't fast enough... and C isn't either

8:55 I have absolutely no issue writing compilers that produce machine code myself, and clojure should be up to the task

8:56 blackdog: rhickey: did you see charlie nutter's post about Xbootclasspath speeding up jruby boottime significantly? i'm not sure if it would make a difference for clojur or not

8:57 drewr: blackdog: I've been using it in my clojure run script and it only gives me about 0.1s improvement.

8:57 blackdog: ok, there it is :)

8:57 prunedtree: how long is your boot time overall ?

8:57 drewr: About 1.4s. :-(

8:57 blackdog: jruby probably has a lot more overhead in base classes than clojure

8:58 prunedtree: 1.4 sec... well that's much better than it used to be. still huge but I (my users) could live with that I think

8:58 H4ns: rhickey: find/member are the cl programmer's set membership operations, and it is often useful to consider a vector or list to be a set. if clojure has other techniques for achiving that, what are they?

8:58 rhickey: H4ns: use sets

9:00 drewr: prunedtree: Yeah, it's not ideal, but I don't use Clojure for fast, shell-style things. If I'm doing reports from a db, however, I don't care about adding another second on a multi-second process.

9:00 rhickey: that was my point before, without sets in the language, you use lists/vectors and it doesn't scale, with sets in the language, you should use them

9:00 prunedtree: might be okay for shell things if you keep an instance open I guess

9:00 drewr: I also use -Xverify:none, which saves another 0.1s.

9:01 prunedtree: then simply pipe some shell arguments to the running instance, which will spawn a worker thread for it

9:01 there might be some way to achieve that using xargs/netcat... or simply write a trivial C app that does it

9:02 rhickey: blackdog: with AOT compilation of Clojure we could precompile boot.clj. That + Xbootclasspath would probably make a difference

9:02 H4ns: rhickey: so please do not include member or find in the standard library. i'll actually print the pdf today and read it on my flight home, so i'll know how i determine set membership on the weekend :)

9:02 prunedtree: rhickey : btw, I was surprised by one element of the syntax while viewing your presentation

9:02 blackdog: rhickey: ok, nice

9:05 prunedtree: why are maps {:keyA x, :keyB y } but destructuring them {x :keyA, y :keyB} ?

9:05 this seems very confusing

9:08 rhickey: prunedtree: you are using x and y there for 2 different purposes, in the first case they are the values, in the second the let-bound names

9:08 drewr: prunedtree: They aren't. He just happened to used keywords as values in the destructuring slide.

9:08 (I'm assuming you're talking about the recent talk.)

9:08 rhickey: in destructuring, you are really making a mapping from a let-bound name to a key

9:09 prunedtree: rhickey : bound to values, right ?

9:09 rhickey: yes

9:09 prunedtree: so they should be to the same place as values (imho)

9:10 it looks as if you're bouding names to keys with :a being the value (inverse mapping)

9:10 to my untrained eyes

9:10 rhickey: I disagree, when you say let [x 42] the value comes second, here, the value isn't supplied directly, rather its key is, also second

9:11 prunedtree: binds x to the index of the vector that has value 42 ?

9:11 weird

9:11 rhickey: no, I'm comparing to normal let

9:12 prunedtree: ah, (x 42) in lisp...

9:12 rhickey: let [name value]

9:12 prunedtree: yeah, must be my lack of familiarity with Lisp speaking. but the lack of symetry is disturbing

9:12 rhickey: (let [ {name value-key} value-map]

9:12 prunedtree: If it's idiomatic I'll get used to it hopefully

9:13 where value-map could be a former binding, right ?

9:13 rhickey: I don't disagree that one could see it differently, but this is how it is, and, as I said, this way is necessary in order to support :as and :or

9:14 prunedtree: okay

9:15 drewr: prunedtree: I see what you mean now. I haven't destructured maps very much.

9:15 rhickey: :and :or :keys etc are very powerful

9:17 prunedtree: also there's a weird difference between ident and :ident.. aren't both symbols ? what is the rationale behind that ?

9:17 (especially when uou have strange forms like :or / :as .. which are obviously not keys)

9:17 rhickey: no, keywords are not symbols in Clojure

9:18 (symbol? :key) -> false

9:19 prunedtree: so the difference is in the resolution ?

9:20 rhickey: they are read as different types of objects

9:20 prunedtree: why aren't :or/:as keywords ? old lisp convention ?

9:21 rhickey: they are keywords, not in the 'reserved words' sense

9:22 a keyword is just a datatype with the useful property that it always evaluates to itself

9:22 prunedtree: whereas symbols are resolved ?

9:25 rhickey: prunedtree: yes, see: http://clojure.org/reader and http://clojure.org/evaluation

9:26 prunedtree: yeah, I've read that. I guess the sourcecode provides the most information

9:26 rhickey: that's in those docs, no need to read the source to Clojure in order to use it

9:27 prunedtree: well the docs seem very barebones. I've read it and it feels more than a teaser than real documentation. no offsence meant :)

9:29 rhickey: http://clojure.org/evaluation : "Strings, numbers, characters, nil and keywords evaluate to themselves."

9:31 prunedtree: ah yes, keywords aren't symbols. I'm not used to that denomination, sorry

9:37 jdz: Clojure: what would it [Lisp] be like if you had been given a second chance.

10:13 drewr: So I fired up a JVM with the requisite jswat flags, and I'm running the jswat application.

10:13 And I've attached to the socket.

10:13 How do I get an exception in the REPL to appear in jswat?

10:17 leafw: uncatched exceptions will appear in the plugged debugger

10:18 drewr: I just ran:

10:18 user=> (throw (Exception. "foo"))

10:18 java.lang.Exception: foo (NO_SOURCE_FILE:0)

10:18 But jswat doesn't seem to care.

10:18 leafw: because the reader is catching it. I don't know how one can stop the reader from doing so.

10:19 rhickey: drewr: usually there is some break-on-exception setting

10:19 drewr: leafw: Ah, that makes sense.

10:20 rhickey: Looking...

10:21 rhickey: because there are so many exceptions-as-flow-control uses, they make you say which ones to break on

10:21 prunedtree: in java or in clojure ?

10:21 rhickey: no exceptions as flow control in Clojure

10:22 except in the transaction system

10:22 drewr: There's a Breakpoints window, with "Uncaught exceptions" checked. Perhaps leafw is right that since the REPL is catching the exception to show it to me, the debugger doesn't know about it.

10:24 That seems counterintuitive though, since the point of the attached debugger is to monitor a running JVM.

10:24 leafw: drewr: jswat is just a wrapper for jdb

10:24 drewr: jdb only shows uncatched exceptions

10:26 rhickey: new breakpoint|breakpoint type|exception pick exception type etc

10:27 drewr: rhickey: Yeah, just trying that...

10:27 leafw: ha, so it can be configured :)

10:27 drewr: ...and getting somewhere now.

10:29 I think it would be worth adding a sentence in the "Getting Started" section that says something to the effect of, "Make sure you set up a breakpoint for something other than the default uncaught exceptions rule..."

10:31 prunedtree: what is the prefered environnement for clojure under win32 ? eclipse ?

10:31 Chouser: drewr: you could add details here: http://en.wikibooks.org/wiki/Clojure_Programming#Getting_Started

10:31 drewr: prunedtree: For me? Emacs.

10:32 H4ns: prunedtree: emacs-23 and slime work for me.

10:32 Chouser: prunedtree: gvim and a command prompt, just like everywhere else. :-)

10:35 prunedtree: on windows, sure....

10:35 I guess that would be somewhat doable, but why not use the candy

10:36 aren't there good Java IDEs with decent integration of clojure ?

10:36 baetis-fly: i thought someone was working on a netbeans plugin, but i agree, emacs + slime.

10:36 dudleyf: prunedtree: enclojure is a plugin for Netbeans

10:36 H4ns: there is enclojure which integrates into netbeans, but that seemingly does not run on windows.

10:37 prunedtree: ohh

10:37 Chouser: candy rots teeth. Or maybe I'm already too old-fashioned. I understand gvim and command prompts, so I use them.

10:37 prunedtree: so emacs it is on windows then... ironic :)

10:37 Chouser: H4ns: oh, I'm sure that must be a temporary failure. I'm pretty sure enclojure is meant to work on Windows.

10:37 cemerick: enclojure certainly is supposed to run on windows; I don't have any experience, but I've seen reports of success on the google group

10:38 prunedtree: I'll give it a try then

10:38 H4ns: oops - i am alone, then.

10:39 so i stand corrected. enclojure does not work for me on vista/x64 right now but i'll try the next version.

10:39 drewr: Hm, this doesn't seem very productive. I have to reattach the session after every exception.

10:39 rhickey: cemerick: I haven't heard you chime in on the potential maps as java.util.Maps change - iirc you were one of the few to stand up for keeping them Collections

10:39 prunedtree: it looks like it's made for OSX not windows

10:39 quoting the site: At the moment enclojure has only been tested on Mac OSX. If you are testing on Windows/Linux, please post any issues you find in the enclojure group.

10:40 cemerick: rhickey: I've been very distracted by other stuff...

10:40 prunedtree: well, can't be much worse than emacs in windows

10:40 * cemerick goes to check his overflowing clojure-group inbox

10:41 rhickey: cemerick: short story is I'm thinking about making the change

10:42 Chouser: relevent thread: http://groups.google.com/group/clojure/browse_thread/thread/e83e3de776fd8143/26c4a2995fbc959c

10:42 ^ cemerick

10:42 cemerick: Chouser: thx, reading now

10:46 wwmorgan: do you have any opinion on this maps as j.u.Map change?

10:49 wwmorgan: it's easy enough to go from a j.u.Map to an IPersistentMap, because you can use (into {} m)

10:50 cemerick: wwmorgan: I think the general concern is pushing clojure maps out into java libs that require j.u.Maps; or, implementing java interfaces that require a j.u.Map

10:54 wwmorgan: cemerick: I see. Up to now you would need a function like this http://paste.lisp.org/display/67857

10:54 abrooks: This shows how little Java background I have. Can't a class implement multiple interfaces? Why can't Clojure maps implement both j.u.Map and yadda.yadda.collection ?

10:55 cemerick: abrooks: j.u.Map and j.u.Collection have a conflict (with the remove method returning different types -- void in one and an Object in another, I think)

10:55 abrooks: Ah! Okay. Now I see.

10:55 wwmorgan: abrooks: I think the main concern is how you handle mutability

10:57 cemerick: That's a good point. Making cmaps implement j.u.Map gets you one step closer to java compatibility, but given that so many java libs assume that Maps are mutable, would we simply be setting ourselves up to fail further down the call stack?

10:57 wwmorgan: it would be pretty disastrous if users started .put-ing their clojure maps because they can

10:58 instead of using assoc, I mean

10:59 rhickey: cemerick: there's a well defined subset of read-only methods, all of the others are optional

11:00 cemerick: rhickey: Sure. It's unfortunate that there isn't a separate MutableMap interface; however, the optionality of those methods is entirely defined by API contract and nothing else. There's a *lot* of java code out there that simply assumes mutability of Maps.

11:01 I'd suggest that that's not the case for j.u.Collection, which was long just a stand-in before Iterable was available.

11:02 rhickey: cemerick: then a common use case might be just calling a java.util.XXXMap ctor passing a Clojure map, which you can't do right now

11:03 cemerick: rhickey: calling that ctor from clojure, you mean?

11:04 rhickey: cemerick: from Java, for interop

11:05 cemerick: I agree about optional being a lame contract, but doesn't reduce the utility of read-only

11:07 cemerick: rhickey: no, the utility isn't diminished at all -- I'm just trying to think of the gestalt of java Map usage I've seen/written. Assuming mutability is pretty common. I might be wrong about that, of course.

11:08 prunedtree: maybe you could have in/out args for java interop

11:08 cemerick: I think this is a choice between six of one and a half-dozen of another. There's pitfalls on either side.

11:08 wwmorgan: If clojure maps implement java.util.Map, then getting a mutable map is as easy as calling the HashMap constructor and passing in a clojure map. Although it might be confusing for new users

11:08 prunedtree: let java mutable your structure and give you the mutated one back as if the changes where atomic

11:09 rhickey: cemerick: enough people are asking for Clojure maps as Maps, indicating the read-only limitation of that is not prohibitive

11:10 cemerick: rhickey: True -- at least for the current Clojure-using population.

11:11 rhickey: is Stuart right in assuming/hoping that seq on a map would continue to emit key-value pairs after this change?

11:12 rhickey: absolutely

11:16 dudleyf: Immutability is such a stand-out feature of Clojure that most users are not going to be too surprised by a read-only limitation on Clojure Maps

11:17 cemerick: dudleyf: I think the surprise will be more in the neighborhood of passing clojure maps to libraries or returning clojure maps from gen-class impl functions where the recipient assumes mutability

11:18 I guess I'm essentially neutral on the change. I certainly see some upside, but losing the single base for all clojure collections is unfortunate, IMO.

11:18 dudleyf: cemerick: Sure, but I found it much more surprising that clojure maps weren't Maps

11:19 Maybe we should just start a JSR to make the Collection and Map interfaces compatible

11:19 ;-)

11:19 Chouser: can't we just submit a patch to fix j.u.Collections remove method?

11:20 cemerick: dudleyf: for sure, it falls outside of one's expectations. I think there's solid reasons behind Rich's choice there, though. The rising tide of Java<-->Clojure intermingling seems to be nudging the needle, tho.

11:21 dudleyf: cemerick: Yeah, it makes sense once you understand the reasoning behind it

11:21 cemerick: Ach, Map doesn't extend Iterable (or, Iterable<Entry<K,V>>, I suppose)! That's really unfortunate. I was hoping that I could fall back to expecting that all clojure collections were Iterable.

11:24 rhickey: cemerick: Clojure maps will still be Iterable

11:24 cemerick: rhickey: actually, could you make clojure maps Iterable? That would be helpful.

11:24 rhickey: and IFn and all of their other goodness

11:26 cemerick: rhickey: OK, I'm +0 on it as a whole. ;-)

11:27 rhickey: +0 - that gives me all the points I need! :)

11:28 cemerick: I always knew you were a low maintenance benevolent dictator.

11:28 The mutability issue may be more important than our particular circle appreciates, though. I wouldn't be super surprised if the common idiom becomes (HashMap. clojure-map) in a year's time.

11:29 Chouser: rhickey: did you see my new patch for clojurescript? I don't need any response except that you're aware of it or not.

11:29 rhickey: Chouser: sorry, saw your message, yes, haven't looked at the patch

11:29 dudleyf: cemerick: But isn't that the idea?

11:30 Chouser: rhickey: ok, thanks.

11:31 cemerick: dudleyf: I wouldn't think so; if that's expected to be the norm, then a simple helper function to remap a map to a j.u.HashMap is a simpler, easier choice.

11:32 rhickey: cemerick: are you suggesting a copy-free mapper class that implemented mutability?

11:34 cemerick: rhickey: I thought a patch for such an approach was put forth over the summer -- perhaps in the same discussion around making vectors implement j.u.List?

11:34 Chouser: I think prunedtree suggested that -- could be a little thing wrapping a ref and a persistent map

11:36 cemerick: hrm, I think I missed that, but that approach sounds very pleasant. There are many Java methods that take a map, fiddle with it, and return void.

11:39 Chouser: would that be better than just copying a PersistentMap into a j.u.Map, passing it in, and creating a new PersistentMap afterward?

11:41 cemerick: Chouser: I'd think so, especially in those cases where you need to capture changes being made to a j.u.Map in a method without a return value.

11:42 But that's sort of orthogonal to what I've understood the demand to be: that is, that clojure maps should directly implement j.u.Map.

11:46 Chouser: orthogonal, yes.

11:47 but while we're still talking about it, rhickey is nearly done implementing it. Next words from him will be "IPersistentMap now implements j.u.Map"

11:47 cemerick: I mean, that approach would be generally more useful IMO, but then I can't really give voice to the view that implementing j.u.Map is really important.

11:47 heh, yeah, that's a safe bet.

12:09 prunedtree: wow. expected it to be kinda slow, but not that much (microbenchmarking :s)

12:42 is naive fibonnaci an isolated case or are function calls really expensive in clojure ?

12:43 Chouser: a clojure function call should cost the same as a java function call

12:44 cemerick: prunedtree: you can paste your microbenchmark if you like. I'll bet a type hint will bring the clojure into parity with Java.

12:44 prunedtree: (defn fib [n]

12:44 (if (< n 2)

12:44 n

12:44 (+ (fib (- n 1))

12:44 (fib (- n 2)))))

12:44 note, I tested on two other very very dynamic systems that do not need any type hint to produce ridiculously superior performance

12:45 in fact, even an interpreter performs faster...

12:45 maybe it's the JVM I have which sucks ?

12:46 Java: 1.6.0_07; Java HotSpot(TM) Client VM 10.0-b23

12:48 cemerick: prunedtree: you'll likely be happier with (defn fib [#^Integer n] ...

12:49 fwiw, you'd be better off using loop/recur, which won't blow stack

12:53 prunedtree: as I said, I tested on other systems that do not have types

12:53 and I have the same difference (an order of magnitude) if a feed a ratio as input (to avoid fixnum arith)

12:53 ozzilee: prunedtree: What kind of times are you seeing?

12:54 prunedtree: (fib 36) takes 17 sec

12:54 blackdog: does that include jvm starup time?

12:54 Chouser: (fib 36) is 1.8 seconds here.

12:55 walters: prunedtree: what hardware architecture?

12:55 Chouser: user=> (time (fib 36))

12:55 "Elapsed time: 1814.196797 msecs"

12:55 ozzilee: (fib 25) is 11.8 seconds on a 700mhz PPC :-)

12:56 prunedtree: core2duo ulw

12:56 1 ghz

12:56 Chouser: prunedtree: that's faster than my machine. there must being something "wrong" with your environment.

12:56 walters: prunedtree: oh, client VM...hm. you might use -server

12:57 i think in the latest openjdk beta there is no -client and -server anymore which will be nice

12:57 cemerick: client/server shouldn't impact things that much...

12:57 dudleyf: unless it does include jvm startup time

12:57 prunedtree: and i'm getting under 5 sec in interpreted smalltalk

12:58 Chouser: yeah, even without -server I'm at about the same speed

12:58 prunedtree: <dudleyf> unless it does include jvm startup time << doesn't, it's inside a program

12:59 dudleyf: Then client/server won't make much of a difference until you run the same benchmark 10,000 times or so

12:59 prunedtree: <Chouser> "Elapsed time: 1814.196797 msecs"

12:59 what is your hardware ? that's closer to what i'd expect to see...

13:00 Chouser: prunedtree: core 2 duo, 800 MHz

13:00 prunedtree: and anything specific jvm-wise ?

13:03 Chouser: java version "1.6.0_06" Java HotSpot(TM) Server VM (build 10.0-b22, mixed mode)

13:03 prunedtree: maybe the client VM is at fault

13:03 how do you get the server thing ? j2ee ?

13:04 lisppaste8: abrooks pasted "lazy fib performance" at http://paste.lisp.org/display/67863

13:04 Chouser: I doubt that's the issue, but I guess maybe ... I just have a pretty stock ubuntu install. Not sure how I got server instead of client.

13:04 abrooks: Lazy fib 36 (i.e. 35) takes 0.242755 msecs

13:05 prunedtree's fib on the same system takes 2549.496222 msecs

13:05 That's crazy.

13:05 1000X slowdown.

13:06 I think prunedtree has spotted a real performance issue.

13:06 Chouser: With OpenJDK Server VM (build 1.6.0_0-b11, mixed mode), I'm still getting (fib 36) in 1.5 seconds

13:07 abrooks: your algorithm is different -- you're caching values instead of recomputing.

13:07 abrooks: Chouser: I know.

13:07 Chouser: I assume prunedtree is using an algorithm that is intentionally beating on function calls.

13:07 prunedtree: yes

13:07 dudleyf: prunedtree: just pass -server to the java command

13:08 prunedtree: doesn't work. I have j2se

13:08 Chouser: But for some reason his is taking 10x longer than mine. I think that's an environment issue, somehow.

13:08 prunedtree: maybe there's something wrong with the client VM

13:10 dudleyf: prunedtree: I think you're right

13:10 prunedtree: humm 2 mb... good that sun has good proxies here...

13:11 100 mb, not 2

13:11 dudleyf: user=> (time (fib 36))

13:11 "Elapsed time: 13347.682 msecs"

13:11 with -client

13:11 cemerick: prunedtree: I just tried your function on -client and -server, no timing difference.

13:11 prunedtree: client still doesn't use the c2 compiler ? urgh... thought they fixed that years ago

13:12 I hope the server performance is more reproducible than the client one ;)

13:12 dudleyf: user=> (time (fib 36))

13:12 "Elapsed time: 2936.406 msecs"

13:12 with -server

13:12 prunedtree: that creates a huge incentive to bundle the VM with any app you distribute

13:12 danlarkin: (time (fib 36))

13:12 "Elapsed time: 8332.648 msecs"

13:13 that's with prunedtree's fib function

13:13 prunedtree: wouldn't want my clients using the client version and getting horrible performance

13:14 walters: prunedtree: ah...i think both VMs are shipped with the J2SDK or whatever it's called, they created a -client because they thought it would make a large startup time impact as I understand it

13:15 dudleyf: It does cut down startup time significantly, but I've never seen that kind of performance gap on simple benchmarks

13:15 leafw: walters: :if that's the reason, makes no sense anymore: here a jdk takes one or 2 seconds to launch (T60 laptop)

13:15 walters: leafw: in a cold cache?

13:16 leafw: walters: in cold, it may take 5 or 6 secs

13:16 granted.

13:16 with -server flag, we are talking.

13:19 prunedtree: bah

13:19 the sun website sucks

13:20 I have no idea how to get the server VM....

13:20 Chouser: prunedtree: what happens when you use -server -- error? no change?

13:21 prunedtree: error

13:21 tells me I don't have the right dll

13:21 (ie I don't have the server VM)

13:23 dudleyf: prunedtree: http://tinyurl.com/5ptq6n

13:24 From there you should be able to pick your platform and download the jdk

13:24 Or wait, are you on a Mac?

13:24 prunedtree: windows

13:25 and I tried the jre 1.6u7

13:25 dudleyf: Then you should be able to download it from there ^^^

13:25 prunedtree: and also the jdk

13:25 dudleyf: You want the jdk

13:26 prunedtree: and they don't give me the server thing :/

13:26 maybe I should remove the jre and put the jdk ?

13:26 dudleyf: Maybe

13:27 I haven't installed a JRE without the JDK in a long time

13:28 prunedtree: uninstalling both. the jdk you linked to was the one I had btw

13:29 achim_p: Chouser: just read your post to the list regarding shell calls. since that's on my todo list anyway, i could as well do it as a seperate library

13:29 for now my needs are simple, sth like ruby's/python's popen* would do (in conjunction with expect), but i'm not settled on it. you don't seem to like it - care to elaborate on where you see the shortcomings?

13:30 walters: Chouser: btw if you do take influence from something, python's subprocess is very good and the only one i've used that isn't broken or very limited

13:31 abrooks: walters: Subprocess is better than the others but is still horribly awkward. Launching programs sucks in Python.

13:31 walters: the hard part about implementing it is you can't do it on top of the JDK ProcessBuilder class since it won't let you do prefork functions

13:31 abrooks: it sucks everywhere as far as i know

13:31 it's like remoting

13:32 they'll just never be as nice as local library call

13:33 abrooks: I have a Python library partially constructed that allows for much better process control.

13:33 print pl("ls", "/dev")("grep", "-i", "tty")().stdout

13:34 There's also IFS parsing available if you don't want each argument as a separate string.

13:35 walters: yeah, i have a shell (http://hotwire-shell.org) which implements a trivial language specifically for this, but i don't think it necessarily makes sense in the core subprocess invocation library

13:37 Chouser: walters: that looks nifty

13:37 abrooks: I don't know if belongs in the core library but I want something better as part of the distribution. Your project looks very interesting.

13:40 Chouser: I guess my objections to python's popen* revolve around the combinatorially named functions and that the mechanisms for when you want to capture none of the output, just stdout, or stdout and stderr each feel rather different.

13:40 I don't think I've ever used subprocess.

13:40 walters: yeah, popen* is broken

13:40 Chouser: so as long as we don't do that, I'm golden. ;-)

13:41 prunedtree: reinstalled everything, rebooted.... and still no server

13:41 Chouser: I find it unlikely that implementing something akin to abrooks' api would be that much harder.

13:41 prunedtree: :-(

13:42 hm, looking at my Windows VM, I see I also have the Client VM

13:44 abrooks: Can't you just switch the VM with the -client/-server flags or is that only with the VM provided with the Sun JDK?

13:45 Chouser: So on my 800MHz laptop, in a VMPlayer running XP, using the Sun Java Client VM, (fib 36) takes 7.6 seconds.

13:46 prunedtree: how come it's so much faster than me ?

13:46 Chouser: abrooks: apparently the VM package for windows understands the switch, but doesn't include the actual server VM.

13:46 Error: no `server' JVM at `C:\opt\java\bin\server\jvm.dll'.

13:46 prunedtree: <abrooks> Can't you just switch the VM with the -client/-server flags or is that only with the VM provided with the Sun JDK? << I installed the jdk... which installs the jre

13:47 Chouser: I think I have only the JRE

13:47 abrooks: Okay. I'm only half paying attention. Sorry.

13:49 prunedtree: man I sure hope there's a way to avoid all this mess when I deliver application, or that platform is simply not usable (how do they manage to have something immature after more than a decade ? it takes some serious skills....)

13:49 you think it's legal to build the VM from the source and distribute it in a commercial package ?

13:49 without all the sun clutter

13:50 walters: the icedtea project has removed all proprietary plugs, but it's targeting Free operating systems and not Windows, but i doubt it would be hard to get it to build for Windows

13:51 achim_p: how about

13:51 (popen "ls" ...) -> [in out err]

13:51 walters: i believe the goal is to get upstream openjdk to this point as well, but they are more concerned about complete compatibility

13:51 achim_p: (with-popen ["ssh" ...] in out err

13:51 (expect in "^[uU]sername: " (fn [match] ...)

13:51 ... ))

13:51 walters: e.g. icedtea just doesn't implement SNMP

13:52 cemerick: prunedtree: there's a *lot* of people using Java very successfully in a lot of different scenarios. It's certainly not unusable.

13:52 abrooks: achim_p: I like the context manager ("with") style much better -- much more lispy.

13:52 You'd want both, I'd suppose.

13:53 achim_p: abrooks: yes, both

13:54 prunedtree: I'm one very unlucky people

13:54 the only positive side is that I am an incredible beta-tester ^^;

13:59 Chouser: wouldn't the with- version be equiv to (let [[in out err] (popen "ssh" ...)] (expect in...))

14:01 abrooks: Chouser: Often context managers will automatically close/dealloc/cleanup the managed item on exit of the block.

14:01 Chouser: abrooks: ah, good point.

14:09 achim_p: perhaps a third version would be nice, one that slurps out+err and returns a string

14:12 and timeouts for expect - has anybody come up with a simple way to perform blocking calls with a timeout?

14:13 lisppaste8: achim_p pasted "with-timeout" at http://paste.lisp.org/display/67868

14:13 walters: achim_p: you can call Thread.interrupt() on the blocking thread, not sure how that appears in clojure

14:17 achim_p: walters: thanks, i'll have to look into java threading. right now i'm abusing agents for that

14:20 prunedtree: 4.5 seconds

14:20 i'm still very far from 1.5 sec...

14:20 still much better than the client VM

14:22 Chouser : you use a 64 bit system ?

14:27 Lau_of_DK: Has anybody here got a clojure example of a successful initialization of a JTable using the object[][] object[] constructor?

14:27 Chouser: prunedtree: 32 bit

14:28 Lau_of_DK: I saw you were poking at that. I dug out my example, and found I bailed on that constructor. ...so no, I do not.

14:28 prunedtree: c2duo ?

14:28 Chouser: prunedtree: core 2 duo, 800MHz

14:28 prunedtree: are you sure you tested the same function ? no integer hint or such

14:29 Chouser: no integer hint (which wouldn't help anyway since these are not calls to java methods)

14:29 Lau_of_DK: Chouser the all-seeing - Okay. Its a little weird, I managed to get it initialized, so it was accepted as an object[][] (the data), but when rendering it fails and throws some outofbounds errors....

14:30 prunedtree: so how come we have different performance results ?

14:30 I have a 1ghz c2duo

14:31 Chouser: prunedtree: that's an excellent question, and I'm afraid I don't really know.

14:31 Maybe there's some Java forum where they would know such things? I knowledge of Java is pretty shallow.

14:32 prunedtree: I'd say that it's speedstep messing up your measurements (giving you something that's not realtime)

14:33 can you try something that takes a dozen seconds to check it's true real time ?

14:33 and not time scaled on some virtual high frequency clock

14:33 fib 40 should do (if that doesn't take too long)

14:34 Chouser: (fib 37) in my VMPlayer, Windows XP, etc. just took 13 seconds, counting manually

14:36 prunedtree: other than -server, what parameters do you use ?

14:37 Chouser: no -server in my Windows install. C:\>java -cp h:\build\clojure\clojure.jar clojure.lang.Repl

14:38 then I pasted your fib fn at the prompt, and ran (time (fib 36))

14:38 prunedtree: "Elapsed time: 6308.444789 msecs"

14:38 24157817

14:38 Chouser: I can see one of CPU meter peg at 50% for 7 or 8 seconds.

14:38 prunedtree: for fib 37

14:39 Chouser: oh! that's better, isn't it?

14:39 prunedtree: didn't feel like realtime

14:39 ah, it is

14:40 the VM takes a few seconds too boot, too

14:40 4 sec to boot

14:40 Chouser: but still, in linux (no vmplayer) with -server, (fib 37) takes 2.8 seconds (not counting java boot)

14:42 prunedtree: Exception in thread "main" java.lang.NoClassDefFoundError: clojure/lang/Repl

14:42 Caused by: java.lang.ClassNotFoundException: clojure.lang.Repl

14:42 strange, I can't do what you did

14:43 ah no, wrong path

14:44 Chouser : and it's not a 64-bit linux ?

14:44 I guess you must have some hidden VM parameters, as you didn't have to add -server

14:45 (which gives me the client version here...) (or maybe -server is the default on linux... discrimination !)

14:46 I have consistent timings ...

14:46 user=> (time (fib 36))

14:46 "Elapsed time: 3704.085855 msecs"

14:46 14930352

14:57 Chouser: On linux (32 bit) without -server I get 2836 msecs and with -server I get 2818

14:58 ah, but -client gives me 13403 msecs

14:59 so it does appear to be client vs. server setting -- you got -server to work on Windows now?

14:59 prunedtree: yes

14:59 otherwise I get 18 sec

14:59 it looks like the speeddown for client is consistent

14:59 I wonder if it's not a timing error from windows/linux

15:00 (well, I do measure 4 seconds of real time myself)

15:00 you are sure that the numbers you get are accurate on linux ?

15:01 Chouser: I'm not including java boot time

15:02 rhickey: even with -server you may need to run it a bunch of times to get the server to optimize it

15:03 achim_p: whoa, shockingly slow on a power pc (1ghz). 40 secs for (fib 36)

15:03 dudleyf: rhickey: But is it expected for -client to run the simple fib 8-9x slower than -server?

15:04 Chouser: (fib 38) in linux with -server is definitely taking no more than 5 realtime seconds.

15:04 rhickey: this kind of benchmarking is a huge time-suck

15:04 dudleyf: No kidding ;-)

15:04 Chouser: prunedtree: at least you're beating your smalltalk numbers now

15:04 prunedtree: no I'm not :)

15:05 but it's closer to something acceptable

15:05 Chouser: hmph.

15:05 danlarkin: which version of fib are you all using now?

15:06 prunedtree: 4.5 sec on my system is the time for /interpreted/ smalltalk

15:07 <rhickey> even with -server you may need to run it a bunch of times to get the server to optimize it << actually it doesn't make any difference to me

15:07 OSR works well

15:07 Chouser: danlarkin: http://clojure-log.n01se.net/date/2008-10-03.html#12:44a

15:08 danlarkin: Chouser: thanks

15:08 Chouser: note that's not a good fib implementation, but it's a pretty punishing way to test function call speed.

15:09 rhickey: except all of your numbers are not bound at all by function call speed, but by arithmetic boxing!

15:10 danlarkin: Chouser: haha agreed, but I want to try it with -server and -client on my machine

15:10 rhickey: this test is dominated by boxing

15:10 prunedtree: yeah, I think so

15:11 I wonder if the linux VM has some different internal compiler tweaks

15:11 ozzilee: achim_p: What PPC? G4?

15:13 achim_p: ozzilee: yes, inside an aging powerbook

15:14 danlarkin: so I get about 8.1 seconds with -client, 5.3 seconds with -server, -client being the default on my Leopard macbook pro

15:15 prunedtree: I get ~5x difference between client/server. but I'd like to have Chouser's numbers ;p

15:18 anyway, that's decent enough. as long as you are within 10-5x of the C time I'd say it's acceptable for most stuff

15:19 danlarkin: I don't see any speed improvement by hinting n to an Integer

15:19 unless I'm doing it wrong, which is totally possible

15:19 (defn fib [#^Integer n] ...

15:21 ozzilee: ozzilee: My 700mhz G3 is still cranking away... 8 minutes so far...

15:23 prunedtree: let's try a much more interressing benchmark...

15:23 dudleyf: danlarkin: That only affects Java method calls where Clojure might otherwise need to use reflection

15:23 If I'm not mistaken

15:23 * ozzilee is talking to himself, apparently

15:23 ozzilee: achim_p: I meant to reply to you :-)

15:24 Chouser: dudleyf: right

15:25 lisppaste8: rhickey pasted "hinted fib" at http://paste.lisp.org/display/67873

15:25 prunedtree: humm. how do I get an interval ? call java ? code it myself ?

15:26 rhickey: dudleyf: no, hinting can impact arithmetic too. The main problem here is that the recursive calls take and return Objects, but inside the fn we can optimize a bit, see paste

15:27 prunedtree: well, to make it interressing I tested (fib 301/10) also

15:28 other polymorphic systems would still win by a huge margin. hard to tell if it's the way you do polymorphism or number unboxing

15:29 anyways, ints are so common in code that it's likely to impact everything. hopefully the next generation of VMs will unbox stuff. it's actually trivial compared to more exotic stuff they do with locks and so on

15:29 danlarkin: hinted fib clocks in at 1.2 seconds with -server, 3.5 with -client... down from 5.3 and 8.1 respectively

15:29 rhickey: all Lisp and Smalltalk system that have tagged numbers will beat all JVM langs that box on this benchmark, until the JVM supports tagged numbers or optimizes the escape analysis across calls

15:30 achim_p: ozzilee: wow, 8 minutes :) i wonder why (un)boxing is so much more expensive on the jvm for ppc.

15:31 rhickey: danlarkin: not too shabby

15:31 ozzilee: achim_p: Oh it's still going. 15 minutes or so now.

15:32 Chouser: cljs performs poorly for this test.

15:32 abrooks: Chouser: heh. Really? </ironic>

15:33 Chouser: (fib 30) costs 4 seconds in Rhino

15:34 * ozzilee hopes his laptop hasn't started anything on fire at home...

15:38 abrooks: Chouser: That's really impressive, actually. I assume that's the hinted fib?

15:38 achim_p: alright, enough of this for me - signore fibonnaci would likely turn around in his grave if he knew what the kids were doing with his sequence nowadays ;)

15:38 abrooks: Oh, it's also fib 30.

15:40 Chouser: no, hinting doesn't work in cljs yet.

15:53 ozzilee: achim_p: 39.31 minutes. I win.

15:54 danlarkin: ouch

17:24 lisppaste8: prunedtree pasted "stack overflow without recursion" at http://paste.lisp.org/display/67882

17:25 prunedtree: wrote a bytearray implementation because immutability sucks to do sieves

17:25 stack overflow at 10k iterations is a problem for something that should iterate over 10 million elements...

18:37 Chouser: prunedtree: http://paste.lisp.org/display/67882 is pretty interesting.

19:08 (dorun (for [i (range 10000) j nil] nil)) --> java.lang.StackOverflowError

19:24 It's all lazy-cat's fault.

19:56 got it.

20:01 prunedtree: I think this patch to boot.clj fixes the problem you found: http://clojure.googlegroups.com/attach/1a9afd4aed95c26c/for-overflow.patch

20:25 Pupeno: Hello.

20:25 Chouser: Pupeno: hi

20:25 Pupeno: How does this thing of adding a dot at the end of a name work? like JFrame.

20:26 I mean, what is it supposed to do? I couldn't get anything but errors.

20:26 Chouser: (Foo. x y) is the same as (new Foo x y)

20:26 which is like "new Foo(x, y)" in Java

20:26 Pupeno: oh, ok.

20:27 Thanks.

20:27 Chouser: np

20:35 Pupeno: Can you ship a Clojure program in a jar?

20:44 Chouser: yep

20:45 Pupeno: Nice. Thank you.

20:45 Chouser: Many of the clojure lib functions will find .clj files in the classpath, including in .jars

20:46 danlarkin: so is the (Foo. x y) a reader special-case? It has to be, right? Because Foo. is not in the namespace so it can't be called like a normal function or macro

20:48 rhickey: danlarkin: It's actually special macroexpansion: (macroexpand '(Foo. x y)) -> (new Foo x y)

20:49 Chouser: danlarkin: it's not in the reader, technically, since "Foo." is a valid symbol and is read that way. The docs say Foo. turns into "new Foo" at "macro expansion time"

20:49 achim_p: hi! it's probably really easy, but it won't cross my mind right now: how to obtain a lazy seq of ((1) (1 2) (1 2 3) ...) from (1 2 3 4) in one pass? i'd like to produce a lazy seq of "growing" reads, given a reader ("h" "he" "hey")

20:51 danlarkin: rhickey: Okay, so macroexpand-1 knows how to deal with the (Foo. x y) form, but how does clojure know to try to macroexpand it? For instance, (Foo x y) won't be passed to macroexpand.. or will it?

20:53 Chouser: achim_p: (map (fn [a b] (take a s)) (iterate inc 1) s)

20:54 That's one way -- I'm sure there's something better.

20:54 rhickey: danlarkin: in looking to see if a form is a macro form, the compiler looks for leading or trailing dots, which are reserved for this purpose, then knows it gets special expansion, otherwise looks to see if was a defmacro var etc

20:55 Chouser: rhickey: you saw the stack overflow in "for"/

20:55 ?

20:56 achim_p: Chouser: thanks! that's quadratic-time though, but it should do for now

20:57 rhickey: Chouser: yes, thanks for chasing that. Your fix works ok for that case, but I think there may be a deeper problem

20:57 Chouser: rhickey: ok.

20:58 danlarkin: rhickey: excellent, thank you for the explaination

20:58 Chouser: achim_p: what? it's a lazy seq of lazy seqs -- each level of seq produces the next item in constant time

20:59 danlarkin: sorry if I'm asking a bunch of arcane annoying questions of y'all, but it helps me learn a lot about the language

21:00 Chouser: danlarkin: tell you what, nothing helps learn arcane and annoying details of a language like writing a new back end -- know anything about JavaScript?

21:00 :-)

21:00 danlarkin: Chouser: oh jeez, more than I'd like to

21:01 Chouser: hm... looked at clojure-contrib/clojurescript at all?

21:01 achim_p: Chouser: of course you're right, i misread. i should get some sleep :) thanks again!

21:01 Chouser: achim_p: np

21:01 danlarkin: Chouser: I'm scared of it!

21:02 Chouser: yeah, me too :-( well, just so long as you know it's there...

21:03 danlarkin: TBH I haven't looked at it. Saw it was there but moved on

21:03 although now I'm looking

21:04 rhickey: achim_p: no, you are right, the takes, when consumed grow with N

21:04 achim_p: Chouser: erm, but take takes longer for growing a, doesn't it?

21:05 ah, ok

21:05 lisppaste8: rhickey pasted "taking" at http://paste.lisp.org/display/67889

21:05 rhickey: try that

21:05 Chouser: ah, I see.

21:07 if you touch each item produced, though, aren't they the same?

21:08 "taking" is a win if you're doing something sparse on each vector, like using nth.

21:08 rhickey: no, because each take starts at the beginning, while each step of mine just adds one item to the vector

21:09 achim_p: rhickey: perfect, thank you!

22:18 danlarkin: ((fn [a b c d] b) 1 2 3 4) => 2

22:18 ((fn [a b c d :as lst] b) 1 2 3 4) => java.lang.Exception: Unsupported binding form: :as (NO_SOURCE_FILE:57)

22:18 :-(

22:19 ohhh

22:19 wait!

22:20 no.. still don't get it

22:22 oh.. must I do it like this, ((fn [[a b c d :as lst]] b) [1 2 3 4])?

22:23 rhickey: danlarkin: yes

22:25 danlarkin: I see -- so it's not quite like "def fun(*args)" if you're familiar with Python. I was assuming it worked that way, but come to think of it I shouldn't have, based on the let example of destructuring

22:26 lisppaste8: baetis-fly pasted "Faster nsieve vs. prunedtree" at http://paste.lisp.org/display/67899

22:43 danlarkin pasted "metadata" at http://paste.lisp.org/display/67900

22:45 danlarkin: so my question about that is why does one way of defining a function get an :arglists key in its metadata, but the other way doesn't

22:47 Chouser: danlarkin: the :arglists metadata is added by the defn macro itself

22:47 boot.clj, line 207

22:47 danlarkin: d'oh!

22:47 good reason

Logging service provided by n01se.net