#clojure logs

2010-09-08

00:14thunkI'm a little unclear on the distinction between toplevel variable bindings and function argument bindings.
00:14thunkAt the toplevel, a symbol refers to a variable which is bound to a value.
00:14thunkBut are function argument symbols bound directly to values, or do they also refer to variables (which may shadow variables referred to by toplevel symbols) that are bound to values?
00:14thunkIt's probably a mostly meaningless distinction, but I'd like to have it straight.
00:16thunkI guess what I'm asking is, what exactly *is* a variable object, and does it come into play in function argument bindings?
00:18wwmorganthunk: I think if you understand distinction between Symbol and Var then that will go a long way to clearing up your confusion
00:19wwmorganto partially answer your question, a Symbol in clojure is just a (possibly namespace-qualified) string. In an OO sense, the state of a Symbol contains no binding information
00:20thunkOk, so far so good.
00:21thunkThen each namespace probably has a table that maps symbols to variables?
00:22wwmorganthunk: yes. The Namespace object contains the bindings
00:22thunkAnd those variables may or may not be bound to actual values.
00:24wwmorgana Namespace maps Symbols to Vars (or java.lang.Class objects). See ns-resolve
00:25thunkAnd function arguments are also just symbols. But do argument values get lexically bound directly to those symbols, or is there also a variable intermediary?
00:26arohnerthunk: locals created by let, and fn arguments are bound directly to symbols. They're immutable
00:27thunkarohner: Ahh, I see.
00:28thunkI'm coming from a CL background, so this is new to me.
00:28wwmorganthunk: you can't get to the "underlying Var" of an argument to a function from within that function. If you needed something like that, you would pass the Var object into the function using #'
00:33thunkwwmorgan: Ok. That makes sense. So there's one there, but it's inaccessible to preserve immutability.
00:34thunkTutorials tend to omit these things, presumably to make things easier to understand. But they tend to confuse me instead.
00:34arohnerthunk: no, there's not a variable object there
00:34arohnerthe locals map is just a clojure map of symbols to values
00:35wwmorganthunk: I don't think that was the motivation for it.
00:36thunkOk. I must have misunderstood you. I've got it now, though.
00:36thunkThanks much.
01:14thunkSo then what is it that variables actually do?
01:14thunkIf symbols are mapped direcly to values in local let and defn forms, couldn't the same also be done in the namespace map?
01:15wwmorganthunk: I found this. There may be other reasons for it. http://clojure.org/vars
01:23thunkThanks wwmorgan.
01:24thunkThere's something I'm still not getting, but I should probably just let it go, and use clojure until it makes sense.
01:25wwmorganthunk: if you speak java then it's quite illuminating to read the source, or at least the interface definitions, of clojure.lang.Symbol, clojure.lang.Namespace, clojure.lang.Var, etc.
01:27thunkOk, will do.
02:01defnhello all
02:06replacagood evening defn
03:00LauJensenGood morning all
03:17javeid like a pointer to the src of a real world compojure app
03:17javeid like to find some hints on how to handle global state and such
03:18LauJensenjave: Would Moustache work, or does it have to be Compojure?
03:18javemoustache would be ok I think.
03:19javehavent done web dev in a while so I'm rusty on how to aproach where to store things like a global cache and so on
03:19LauJensenIn a couple of hours Im blogging about bestinclass.dk and how it's built using Enlive/Moustache. I said something about it in the past when I opensourced it: http://bestinclass.dk/index.clj/2010/05/refresh-your-cache--best-in-class-has-been-baked.html, http://bestinclass.dk/index.clj/2010/06/best-in-class--now-open-sourced.html
03:20LauJensenI haven't been able to convince any of my clients to OpenSource any actual web applications though
03:20javecoolness
03:20javeI just need some hints
03:20javein this particular instance I'm writing some glue code for sonar
03:21LauJensenThere are many hints in those posts. If you check out admin.clj and templates.clj in the Github repo you should be set for greatness
03:21javesplendiferous
03:21LauJensenprecisely
03:22javeclojure makes it actually fun to code again
03:23LauJensenYes it does. And after 3 years I had almost gotten used to it, but a few days of Java fixed me right up :)
03:24javeheh
04:35LauJensenjave: blogpost/screencast is up now, with a 7 minute explanation of the setup
04:37notsonerdysunnyis there something that would automatically generate a xml file which would detail the struct/class and its member variables or functions along with the argument types and return types...
04:39LauJensenNot that I know of
04:41notsonerdysunnyhttp://groups.google.com/group/clojure/browse_thread/thread/9f69e649c98a9617 .. is the reason I am asking
04:41notsonerdysunnybut is it straightforward to write one ?
04:42LauJensenSort of. But I think you'd want to look at clojure autodoc
04:42notsonerdysunnyLauJensen: if so .. would have a suggestion where I could start...
04:45notsonerdysunnywhat I am trying is much simpler .. what I would like is some way to get a list of all the defined classes/structs and interfaces (probably there is a function for this..) and run through its elements .. (I can do that right?) and create the html file ..
04:45notsonerdysunny*xml file
04:45notsonerdysunnyif these functions exist .. what would they be?
04:47hoecknotsonerdysunny: maybe look at http://en.wikibooks.org/wiki/Clojure_Programming/Tutorials_and_Tips#Invoking_Clojure_from_Java and then create an XML for the classes mentioned there, e.g. clojure.lang.RT
04:48hoecknotsonerdysunny: with reflection, you get everything but the parameter names of methods
04:48notsonerdysunnyactually that should be fine ..
04:49notsonerdysunnycan I access their types ?
04:49hoecksth. like (map (.getParameterTypes %) (.getMethods clojure.lang.RT))
04:51notsonerdysunnyoh that is neat ..
04:52notsonerdysunnyhoeck: did you visit the thread I had mentioned above?
04:53hoecknotsonerdysunny: yes
04:54notsonerdysunnyhoeck: do you think we can redefine defstruct to do the job .. would you have a suggestion?
04:55hoeckfrom what I can see, it should not be necessary to wrap defn, because you would use RT.var to look up and invoke fns
04:56hoeckeither you wrap the defstruct macro and create an xml, or you use java reflection to create it
04:56hoeckI'd rather use reflection
05:03notsonerdysunnyjust out of curiosity .. I heard clojure can actually infer types .. is it possible for us access this infered type?
05:05hoecknotsonerdysunny: i.e. http://gist.github.com/569861
05:07notsonerdysunny... hoek: thanks .. I guess this is waht I was looking for ..
05:07notsonerdysunny*what
05:27notsonerdysunnyleiningen always creates the same project file .. can I make it create a different default project.clj? like for instance always add swank-clojure to its dev-dependencies ...
05:32_na_ka_na_hey guys how do I extract the keys of defstruct?
05:34AWizzArd_na_ka_na_: when you have an instance, try (key your-struct)
05:34AWizzArdkeys (not key)
05:34_na_ka_na_suppose i have (defstruct e :a :b) . .want something like (struct-keys e) => (:a :b)
05:34_na_ka_na_from the definition, not an instance
05:36AWizzArd_na_ka_na_: with a nil-instance you can do: (keys (struct e))
05:38_na_ka_na_AWizzArd: nice idea, but doesn't this deserve a built in function?
05:38_na_ka_na_I'll be calling this a lot of times so I'll have to form a closure over the nil-instance
05:39AWizzArdI won't object. However, in my opinion this needs no built-in, as this is not very often called and runs very efficient.
05:39_na_ka_na_I can memoize it .. hmm
05:39AWizzArdYes. But then again: why would one want to call it multiple times?
05:40AWizzArdAnd (time (dotimes [i 1000000] (keys (struct e)))) was done for me within 110 msecs ==> 110 nanoseconds per call.
05:41_na_ka_na_I'm using a struct instance and persisting it to my table in database ... I blindly assume that the struct instance has exactly the same keys as columns of table ..
05:41_na_ka_na_that's why i need the keys
05:42AWizzArd(def get-struct-keys (comp keys struct))
05:43_na_ka_na_cant do that, what if the struct has more keys than the defstruct ?
05:43_na_ka_na_I want to restrict the struct to exactly the keys of defstruct
05:43_na_ka_na_struct is coming from an outside source
05:45AWizzArdget-struct-keys will create a fresh struct, with all struct values set to nil.
05:46AWizzArdSo you will get a seq of exactly the keys of defstruct, not of a specific instance.
05:46fliebelmorning
05:47_na_ka_na_oh ok got it now
05:48fliebelWhy do functions in Clojure/core often have multiple bodies, up to 3 arguments before they resort to using & args?
05:49LauJensenfliebel: Thinking about any function specifically?
05:49fliebelhttp://github.com/clojure/clojure/blob/b578c69d7480f621841ebcafdfa98e33fcb765f6/src/clj/clojure/core.clj#L1936
05:49fliebelcomp
05:50LauJensenI think for comp as well as a few others, its a performance consideration
05:50fliebelIt does this in a nested fashion, where it deals with one function with one arg, two funtcion siwht on arg, two functions with 2 rgs, etc...
05:51Chousukeit's a performance optimisation
05:51fliebelSo using a b c is faster than using & args?
05:52Chousukeyeah
05:53fliebelI feel guilty now, for planning to use comp in a non-speedy way :)
05:54LauJensen,(time (dotimes [_ 1e6] (+ (+ 1 2) (+ 3 4))))
05:54clojurebot"Elapsed time: 371.225 msecs"
05:54LauJensen,(time (dotimes [_ 1e6] (apply + [1 2 3 4])))
05:54clojurebot"Elapsed time: 1730.082 msecs"
05:54fliebel(what is 1e6?)
05:55Chousuke1 and 0 zeroes :)
05:55Chousukeer
05:55Chousuke6 zeroes
05:55fliebelI see
05:55fliebelBut why is the apply option so slow?
05:56Chousukefliebel: well in this case it's cheating a bit because + for two args gets inlined
05:56Chousukeso it's not that apply is slow, it's that + when inlined is fast :P
05:56Chousukeit basically compiles down to a simple method call.
05:56LauJensen+ online inlines when it has 2 args
05:57fliebelChousuke: So how is that related to comp?
05:57LauJensen,(time (dotimes [_ 1e6] (+ 1 2 3 4)))
05:57clojurebot"Elapsed time: 1160.466 msecs"
05:57Chousukebut apply still needs to break down the list of args so that it can call the rest arg version etc.
05:57Chousukeso it needs to do more work compared to a plain function call
05:58fliebelokay, but isn't that compensated by all the bodies to choose from?
05:59Chousukeand compared to fixed arity rest args are slower because a list of the args must be built at runtime.
06:00fliebelokay
06:00Chousukeso in terms of speed inline > fixed arity > rest args > apply
06:03LauJensen> ruby
06:05zmila,(type 1e6)
06:05clojurebotjava.lang.Double
06:05LauJensen,1e6
06:05clojurebot1000000.0
06:10fliebelLauJensen: So that's 7 zeroes then ;)
06:11LauJensen:)
06:13fliebelOkay… there is assoc, assoc-in, update-in, but where is update?
06:14LauJensenjust use update-in
06:15fliebelcould do that yea…
06:15LauJensen(defn update [m k f] (update-in m [k] f))
06:15LauJensenthere you go :)
06:16fliebelI expected to see the oposite in the source, update-in utilizing update.
06:24LauJensenman you're a hard guy to satisfy, gimme a sec I'll rewrite core...
06:24fliebelhaha, don't bother I'll use update-in :)
06:25LauJensen:)
06:25fliebelBut yea, there are times Clojure makes me want to rewrite core ;)
06:26LauJensenYea me too, Update it a little, rename the project to SLEDGE HAMMER! and release it as my own :)
06:28fliebelAdd OO back in… :P I mean, I don't miss the objects and inheritance to much, but in Python I can do the equivalent of (doc str) and see all the methods I can use to modify it.
06:29LauJensenOO? You mean that broken model for modeling real world entities, which only old farts still use?
06:29LauJensenGuess I could try to dig up some old irellevant papers on it :)
06:30fliebelLauJensen: Nah, I only mean the helpful propertie that I can lookup methods I can use to fumble with the object in question, rather than dig through the whole api to look for something that might be of use.
06:31LauJensenhttp://clojure.org/data_structures
06:31LauJensendid you read that fliebel ?
06:31fliebelLauJensen: Sure, a dozen times or so :)
06:31LauJensenThere are not many datastructures and the interfaces are very similar, it doesn't take too long to get familiar with
06:32fliebelI know… everything in Clojure makes sense in some way, but sometimes I just want to see all things I can de to a string, or a seq, or whatever.
06:33fliebelouch… forgot about that one… "Can't take value of a macro"
06:37fliebelAny better way to do this? (apply (apply comp list-of-fns) args))
06:38fliebelThat is… take a seq of fns and thread the seq of args through all of them.
06:39LauJensenits a little like
06:39LauJensen,(map (juxt inc dec) [1 2 3])
06:39clojurebot([2 0] [3 1] [4 2])
06:39LauJensenOr did I misunderstand your intention ?
06:42fliebelLauJensen: I think so… If you entered [+ inc] for the fns and [1 1] for the args, it should return 3
06:43LauJensenoh
06:43zmilalike apply-in :)
06:43fliebelzmila: Another new function for me :) I'll look it up
06:44zmilajust invented the name, no such function, i think
06:44fliebelnope :(
06:44LauJensenIf anybody liked this, feel free to upvote :) http://news.ycombinator.com/item?id=1671490
06:45fliebelzmila: It's more like apply->
06:47fliebel#clojure, the new vote-ring for everything Clojure :) *reads blogpost*
06:51fliebelLauJensen: Nice stuff :)
06:51LauJensenthanks
06:52fliebelLauJensen: I'm currently doing a lot of thinking and planning with defn to write our own :)
06:52LauJensenIf you could code at the speed of thought, you'd be done by now :)
06:52LauJensenI just learned that Planet Clojure is written in Python :(((((((( Awww the agony of defeat :(
06:53fliebelLauJensen: Yea, just like Apple retail stores running their administration on Windows(true story)
06:54LauJensenreally? That seems weird considering how Arch > Osx > A cardboardbox > Windows
06:55fliebelLauJensen: Replace the box with Wine for gaming :P
06:55LauJensengaming... hrmf :)
07:00fliebelMy new kick-ass plugin system: http://gist.github.com/569958
07:02LauJensen,(reduce (comp inc +) [1 1])
07:02clojurebot3
07:03fliebelLauJensen: Let me think about that one...
07:05fliebelLauJensen: Why do you use reduce instead of apply?
07:05LauJensen(defmacro comp-> [fns args] `(reduce (comp ~@fns) ~args))
07:05LauJensenits a little dirty, but it saves you a nested apply
07:05LauJensen(comp-> [inc +] [1 1]) => 3
07:07LauJensenfliebel: There was a discussion on reduce/apply a while back, where Christophe pursuaded me that you should always prefer reduce to apply, except when calling str or concat.
07:08fliebelLauJensen: Why?
07:10fliebelLauJensen: Also, they don't work the same way, for my solution (comp-> [+ inc] [1 1 1]) => 4 for yours it's 5
07:11fliebelThis is what mine comes down to (defmacro comp-> [fns args] `((comp ~@fns) ~@args))
07:11LauJensenah right
07:18fliebelLauJensen: Is the macro any better than using apply?
07:19LauJensenNo
07:20fliebelLauJensen: Would you mind explaining why reduce is better than apply in most cases?
07:21Chousukeis it? hm
07:21ChousukeI thought apply was better.
07:21LauJensenI'll try to relay what Christophe said. reduce makes more sense to the reader because the contract is so clear. (reduce f a) means that some kind of linear accumulation is going on, even if you don't know f.
07:22Chousukeat least, apply str ... is better than reduce str ... :)
07:22LauJensenconcat and str are the exceptions, because of their memory/stack use
07:23fliebelLauJensen: So I would do (reduce + [1 2 3 4 5]) rather than (apply + [1 2 3 4 5])?
07:23LauJensenyea
07:24fliebel… still don't get it… apply is one operation, while reduce will do 4.
07:24Chousukefliebel: that apply does reduce internally anyway
07:24Chousukeor + does
07:24LauJensen~source apply
07:25ChousukeI suppose reduce can be faster in this case because it can use chunks to work with the vector
07:25Chousukewhich might not be possible with apply. I don't know.
07:26LauJensen,(time (dotimes [_ 1e6] (apply + [1 2 3 4 5])))
07:26clojurebot"Elapsed time: 1891.233 msecs"
07:26LauJensen,(time (dotimes [_ 1e6] (reduce + [1 2 3 4 5])))
07:26clojurebot"Elapsed time: 1443.119 msecs"
07:26Chousukeand there is a new reduce protocol that allows reduce to have type-optimised implementations making it even faster.
07:26AWizzArdApply can not be written in the same level as Clojure code runs
07:26AWizzArdIt requires a higher level, for some "magic"
07:26Chousukebut that might've been disabled for 1.2?
07:33LauJensenChousuke: Doesn't look like it made it in
07:43mrBlissLauJensen: why were you using Windows in your screencast? I thought you were a serious Windows hater.
07:43LauJensenmrBliss: I wanted to try Camtasia
07:44mrBlissLauJensen: okay, nice screencast (audio quality dropped a bit towards the end)
07:45LauJensenyea it did - I couldn't figure out why so I decided to launch anyway. Should probably get a professional mic
07:45LauJensenand thanks
07:46AWizzArdDid Rich mention when the number branch will flow into Master?
07:46LauJensendidn't that happen already ?
07:46AWizzArd"number branch" as in: unboxed ints and doubles as default.
07:46AWizzArdI don't know :)
07:46LauJensenhe merged equiv a while ago, I think that included everything
07:49LauJensenhmmm
07:49LauJensenAudience snapshot: Based on internet averages, bestinclass.dk is visited more frequently by males who are in the age range 25-34, have no children, have no college education and browse this site from home.
07:52AWizzArdbtw, where can I find clojure-contrib.jar at http://build.clojure.org/ ?
07:53octecan i call the superclass from a proxy-class' method?
07:53mrBlisshttp://build.clojure.org/job/clojure-contrib/lastBuild/org.clojure.contrib$complete/
07:53AWizzArdocte: (doc proxy)
07:54octeNote that while method fns can be provided to override protected methods, they have no other access to protected members, nor to super, as these capabilities cannot be proxied.
07:54octethat means no?
07:54octeor only in the context of an overriden protected method?
07:54AWizzArdmrBliss: oh thanks. How did you get there? I mean, what is the click-path to that page?
07:54AWizzArdocte: "[...] args - a (possibly empty) vector of arguments to the superclass constructor [...]"
07:55AWizzArdThis is the only way I think.
07:55octeto the constructor ,yes
07:55mrBlissAWizzArd: clojure-contrib -> last build -> search for ...contrib:complete... -> voila
07:55AWizzArdmrBliss: oh okay, though I don't find this specifically erognomic to use.
07:56AWizzArdIt was very easy when I just had to click on clojure-contrib and found a direct link to the .jar
07:56mrBlissthis is because of the contrib overhaul (split into modules)
07:57AWizzArdSo that people can decide to include only more granular pieces of Contrib into their own .jar files?
07:58mrBlissI think so
08:00raekAWizzArd: http://build.clojure.org/releases/ or http://build.clojure.org/snapshots/
08:03AWizzArdraek: is there also a click path to go there, or is a direct link required?
08:03raekI haven't found any click path for those... :(
08:04AWizzArdk
08:12hoeckocte: proxy-super
08:15chouserbut beware, proxy-super is not thread-safe
08:16AWizzArdHow can one make a fn static?
08:18chouserrub it in your hair?
08:19LauJensenhaha
08:23AWizzArdRich mentioned something like :static to do this.
08:23AWizzArd(defn ^{:static} foo [arg] ...)
08:24AWizzArd(doc defn) doesn't tell
08:24clojurebot"([name doc-string? attr-map? [params*] body] [name doc-string? attr-map? ([params*] body) + attr-map?]); Same as (def name (fn [params* ] exprs*)) or (def name (fn ([params* ] exprs*)+)) with any doc-string or attrs added to the var metadata"
08:24raekI think the syntax is ^:static or ^{:static true}
08:24raekit's still experimental, I think
08:24raekAWizzArd: static, in what sense?
08:25LauJensenstatic in the case means primitive args and returns, cannot be redefined
08:25AWizzArdI want to type-hint args as primitives
08:27chouserAWizzArd: Either ^:static or ^{:static true}
08:30LauJensenAs I recall (defn ^:static myfn [^int x] (+ (int 5) x)) should be a static fn, taking an int and returning one as well
08:39chouser"Only long and double primitives are supported"
08:40chouserbut (defn ^:static myfn [^long x] (+ (int 5) x)) does seem to work.
08:40chousergives you a class with an invokeStatic method that takes a primitive.
08:48LauJensenok, well, long and double is enough
08:48dnolen_(member:defn ^:static myfn ^long [^long x] (+ 5) x)), takes long and returns long, no need to hint 5 in master branch of 1.3
08:48LauJensenI just vaguely recall seeing Rich do an example with ints
08:48LauJensenI might be wrong
08:48dnolen_erg, (defn not (member:defn
08:50LauJensencool
09:05AWizzArdLauJensen: long and double is enough: yes, as long one can still do (int my-long) to make it an int again.
09:26octei've written a clojure function to parse a line.. but it's very ugly: http://paste.lisp.org/display/114347 how would i write this in an idiomatic way?
09:31chouseran example of the kinds of lines it should parse would help me read the code you've got.
09:32octesure.
09:32octehttp://paste.lisp.org/display/114348
09:33rodgertqon the topic of parsing, and lazy sequences...
09:33fbru02hey guys , i was experimenting with this http://pastie.org/1145780 and i want the output that it is mentioned there, can anybody help??
09:34rodgertqI am running into some out of mem exceptions when parsing through a large file (~95MB)
09:34rodgertqthe file format is basically Clojure forms, 1 per line
09:34chouserocte: I think I'd recommend regex for something like this.
09:35rodgertqI use line-seq to read, read-string to parse each line, and then reduce by a map of specific IDs I'm looking for
09:35octechouser, ah, a list of regexps would work
09:35chouserocte: even just one or two should do it, I'd think
09:36rodgertqthere are 35 IDs in this case is, the whole thing should be lazy, and I would expect the vast majority of the large file's data to just be discarded and GC'd but this doesn't seem to be happening
09:41rodgertqsample of the parse function and the input are here http://gist.github.com/570138
09:44raekocte: are you making an IRC client/bot too?
09:45chouserocte: http://paste.lisp.org/display/114348#1
09:45chouserocte: not sure that's exactly right
09:45LauJensenrodgertq: If you slurp 95 MB of text into strings, you're at least putting 190Mb into memory, because of the way Java Strings are implemented.
09:46rodgertqbut shouldn't line-seq read that lazily?
09:46rodgertq(as opposed to slurp)
09:46raekocte: http://gist.github.com/570143
09:47raekI use the following regexen:
09:48raek(def message-regex #"^(?::([^ ]+) +)?([^ ]+)(?: +(.+))?$")
09:48raek(def param-regex #"(?:(?<!:)[^ :][^ ]*|(?<=:).*)")
09:49chouserfbru02: your input is confusing.
09:49chouser'("Clojure "ds " "Clojurism"")
09:49chouser,'("Clojure "ds " "Clojurism"")
09:49clojurebot("Clojure " ds " " Clojurism "")
09:49chouser,(count '("Clojure "ds " "Clojurism""))
09:49clojurebot5
09:49chouserfbru02: do you really mean to have a list of 5 things, including two symbols and an empty string?
09:50fbru02chouser: sorry i didn't mean that , I only meant "Clojure" "randomword" "Clojurism"
09:51LauJensenrodgertq: yea its lazy, but that does change much if you're holding the head
09:51raekocte: feel free to use whatever you like from it
09:51chouserfbru02: so a list of three strings?
09:51fbru02chouser: yes
09:52chouserfbru02: what you had seems to work.
09:52chouser,(map (comp first #(re-seq #"Cloju" %)) ["Clojure" "randomword" "Clojurism"])
09:52clojurebot("Cloju" nil "Cloju")
09:53fbru02ah let me check your slight modifications
09:53fbru02chouser: nice ! it is idiomatic to do it this way?
09:53clojurebotamespaces are (more or less, Chouser) java packages. they look like foo.bar; and corresponde to a directory foo/ containg a file bar.clj in your classpath. the namespace declaration in bar.clj would like like (ns foo.bar). Do not try to use single segment namespaces. a single segment namespace is a namespace without a period in it
09:53chouserfbru02: sure, nothing wrong with that.
09:53fbru02chouser: thanks ! :)
09:54rodgertqLauJensen: ok, could be an impedance mismatch in my understanding of how lazy sequences are implemented in clojure, vs. F# (which I'm more familiar with)
09:54chousercould also say (map #(first (re-seq #"Cloju" %)) ...)
09:54LauJensenrodgertq: I don't know much about F# except that nobody were able to implement my transient news reader successfully in F#
09:54chouserfbru02: or: (map #(re-find #"Cloju" %) ...)
09:55fbru02chouser: re-find sounds good (checking on clojuredocs.org) :)
09:56chouserrodgertq: what version of Clojure are you using?
09:57rodgertqchouser: 1.2
09:58chouserrodgertq: nothing in read-log jumps out at me as holding the seq head, but since it gets passed to to-forms, grok-items, and add-meta, any of those could accidentally retain the head as well
09:58rodgertqlet me update the gist to include those
10:00rodgertqactually I think it's to-forms that's doing it
10:01rodgertqhttp://gist.github.com/570138
10:01rodgertqto-forms is expecting a collection of lines, returning a collection of forms
10:02lenwLauJensen: I had a look through the bestinclass code and it has helped me a lot - just wondering if there is an easier way to decode incoming params from a web post ?
10:02LauJensenlenw: you mean than read-response?
10:03lenwLauJensen: was looking in the comments.clj at the receive-comment func
10:03LauJensensec
10:03lenwta
10:04LauJensenlenw: Well, easier or not I dont know, but thats a fairly naive way to do it and there's a lot of stuff that should be added to make it general purpose. What I would do if I were you was add a helper to read the body, and have that account for zero params, missing params, duplicate params etc and just re-use that
10:05LauJensenI don't use that version on any of my proprietary applications. And I think that there's actually already a helper in Ring which does the job, if you can find it, use it :)
10:05lenwLauJensen: thanks for the advice as always - off to look around
10:05LauJensennp :)
10:05rodgertqhmmm
10:06rodgertqnope
10:07chouserrodgertq: to-forms doesn't call eval, does it?
10:07rodgertqchouser: changed to-forms to take the reader directly and reduce it's result, get the same OOM exception, updated gist http://gist.github.com/570138
10:07rodgertqread-string
10:07rodgertqwhich likely does call eval
10:08chouserno, I think it doesn't.
10:08rodgertqok
10:08chouserwhich is good. eval is more than you need. creates classloader instances I think.
10:08rodgertqk
10:09chouserread-string should be safe as far as memory consumption is concerned, as should your various map and reduce calls.
10:10rodgertqso in the repl, calling all of this I have:
10:10rodgertq(def lc (indexed (read-log "latecancels.20100826.log")))
10:11rodgertqthis is the smaller list of things I want to pluck out related data in the larger logs from
10:11rodgertqthen for the larger file
10:11rodgertq(def o (read-log "orderstat.20100826.log" (filter-by-id lc)))
10:12rodgertqfilter-by-id just checks to see if the supplied collection contains the id from larger file and if so, conj's it to the result
10:13chouserrodgertq: you might try skipping some of the intermediate steps
10:14chouserrodgertq: try a simple filter (maybe with a regex) on the line-seq and conj that into your set -- make sure the set of strings at least fits in memory.
10:15rodgertqcould try that, though in a couple of cases I have more than one UUID in the input, so context matters
10:16chouseryeah, it'd just be a rough test
10:16rodgertqah, right, if it has it, parse it, then procee
10:16rodgertqd
10:17chouserwell, I was thinking just try to reduce the amount of code involved as much as possible and see if you're still running out of memory.
10:18chouserif that fixes it, then you know something in the code you removed is what's breaking things.
10:18lenwLauJensen: ring middleware wrap-params looks good
10:21octeraek, yes
10:22octechouser, thanks for your input :)
10:24LauJensenlenw: good to know
10:35anonymouse89any vimclojure users know how to easily put the last line entered on the repl onto the current line?
10:37LauJensenanonymouse89: IIRC its ':q! emacs M-x slime M-p'
10:43sleepynateLauJensen: huh.. i get -- zsh: command not found: emacs
10:44LauJensensleepynate: thats too bad man, thats cuz you a looser! :)
10:44anonymouse89LauJensen: right..
10:45sleepynateperhaps you meant to join ##flamewar instead of #clojure ? :)
10:47sleepynateanonymouse89: but to answer your question.. no, i can never get gorilla working right anyways :)
10:47sleepynateanonymouse89: i just tslime
10:47anonymouse89sleepynate: atm I'm starting a repl using ConqueTerm
10:48sleepynateanonymouse89: ahh, that works too
10:48anonymouse89and then just gorilla for stuff in files to eval
10:48sleepynatei keep a vim open in tmux and use ^B:split-window
10:49sleepynatethis way also i can have many things pipe to the same repl if i wish
10:50anonymouse89so if you're editing a file and want to eval a line how does that get piped to that repl?
10:50sleepynatevisual select, C-c C-c
10:51anonymouse89oh, then just switch over and paste
10:51sleepynatenah
10:51LauJensenhehe
10:51LauJensenok I wont say a word :)
10:51sleepynateanonymouse89: uno momento.. i show
10:58sleepynateanonymouse89: http://imgur.com/a/JQn8q/workflow_for_vimclj
10:58sleepynatefirst frame, i have repl open next to vim simple euler problem
10:59sleepynaterepl is running in tmux (and you see, there are other repls for python/php etc.. i use this technique in many languages
10:59sleepynateanyways, then V13j to select the 13 lines
11:00sleepynatethen hit C-c C-c to pipe out to repl
11:01sleepynateit's not as "nice" as nailgun et al, but it is simple and consistent :)
11:01Bronsasleepynate: what's that wm?
11:01sleepynateBronsa: xmonad
11:01Bronsablah
11:01Bronsahaskell
11:01sleepynateBronsa: ;)
11:01Bronsanever tried stumpwm?
11:01Bronsa100% pure common lisp tiled wm
11:02sleepynateyea, i have
11:02sleepynatei like xmonad :)
11:02Bronsai use stumpwm by 1 year
11:02Bronsanever tried xmonad
11:02chouserBronsa: does it have tabs in each tile frame?
11:03sleepynateall in all, they're not that vastly different.. but i came to clojure from haskell after a long-time-ago far-far-away scheme past :)
11:03Bronsawhat do you mean with "tabs"
11:03chousermy wm is going away in my distro, so I'm shopping for a replacement.
11:03anonymouse89chouser: going away?
11:03sleepynateBronsa: so i've been using haskell much longer than any CL variant :D
11:03anonymouse89sleepynate: thanks for letting me into you workflow btw
11:03chouserBronsa: multiple application windows in the same frame, with little tab buttons along the top top switch between them.
11:04Bronsachouser: nope
11:04alpheusHow can I add a doc string to a defrecord form?
11:04sleepynateanonymouse89: np. the most important part to me is not getting lost no matter which machine i'm on
11:04Bronsabut you can show/hide application in the same frame
11:04chouseranonymouse89: ion3. written by a mentally unstable person which has caused all manner of difficulties for distros. ubuntu's dropping it. can't blame 'em.
11:05anonymouse89chouser: I'm using wmii which has stacking. this is somewhat like what you're talking about with tabs
11:05Bronsahttp://img842.imageshack.us/img842/1092/screenshotnt.png
11:05anonymouse89chouser: you can divide into columns and then have stacks for each column
11:07ordnungswidrigBronsa: that are some colours!
11:07sleepynateBronsa: i suppose to big thing is... if you preen the same .conf for years... it's hard to switch over :D
11:07Chousukechouser: which is too bad, since ion3 is excellent
11:08Bronsaordnungswidrig: yeah
11:08Chousukechouser: but have you tried awesome? it's good too.
11:08sleepynateBronsa: this is actually new to me, having xmonad *inside* gnome. but i am required to use ubuntu if i'm going to use linux, and ubuntu doesn't like you to use a vanilla WM :/
11:09Bronsaso
11:09chouserChousuke: some friends tried awesome and came back to ion. ...though I forget why, now.
11:09Bronsayou actualy use xmonad as the gnome's default wm?
11:10LauJensenchouser: Why do you call Tuomo mentally unstable?
11:10opqdonution3 rocks
11:10opqdonutand tuomov has disappeared
11:11opqdonutthere are some people trying to pick up maintainership
11:11raekalpheus: since a defrecord from only implement methods of already existent protocols/interfaces, the docstrings usually go on the protocols/interfaces
11:11chouserLauJensen: seems self evident to me, based on his writings. I suppose others could reach different conclusions.
11:11LauJensenchouser: In my oppinion, I think you should be careful labeling people as such
11:12opqdonutI think he's merely opinionated
11:12chouserLauJensen: fair point. I'd like to amend my statement: ion3 was written by someone that's very difficult to work with.
11:13opqdonutand doesn't want to or can't communicate civilly
11:15sleepynateand paranoid
11:15sleepynatedon't forget that part :)
11:15raekalpheus: (defprotocol Source "A thing that produces items" (take! [source] "Removes one item from the source and returns it.")) (defrecord LineSource [buffered-reader] Source (take! [_] (.readLine buffered-reader)))
11:17alpheusraek: I'm still trying to get defprotocol. I think it's more object-oriented than I need (for my present purpose). I'm essentially using defrecord for something a map could do. The records are something to be returned from functions, or collected in sequences.
11:17sleepynatechouser: are you familiar with notion?
11:18chousersleepynate: aware of it.
11:18sleepynateit looks like it's both new and not very active
11:20raekalpheus: simple is good, so if ordinary maps would be sufficient, I'd recommend that
11:21raekif you need polymorphism based on the type of the first argument, use records
11:21raekor multimethods
11:22alpheusThat makes sense.
11:23raekmultimethods are great for doing dispatch based on one (or multiple) of the keys of a map
11:25alpheusLooking again at my copy of Practical Clojure, I see that I mis-read the guideline about preferring defrecord to defstruct. It didn't say anything about maps.
11:25raekif you find yourself adding a type key just to be able to do polymorhpism, maybe records are a better fit. if the thing to dispatch on is a part of the existing value, multimethods might be better
11:25raekstructs are one kind of maps
11:26raekthey just store some of the keys differently
11:26raekbut both structs and hash maps implement IPersistentMap (which records also do, btw)
11:27chouserthere's very little reason to use structs anymore
11:27raek...or if performance is an issue, go with records
11:29BahmanHi all!
11:33hugodIs there a way to establish a thread local value for a var? or do I need something like http://gist.github.com/570249
11:34opqdonutbinding
11:34opqdonutis thread-local
11:35hugodI need a thread local value that is an implementation detail - I don't want the caller to have to bind a value
11:40hugodand I don't want to create the binding on each invocation
11:40arohnerhugod: can't you bind inside the function definition?
11:42hugodarohner: I would rather not - potentially expensive initialisation
11:42arohnerhugod: I don't understand enough about the problem to help you
11:44hugodarohner: I'm probably worrying for nothing and should just bind inside the function.
11:44hugodthanks
11:46hugods/bind/construct/
12:15joshua-choiHey, everyone, can a macro capture at all what file and at what line it's called at, whenever it's called?
12:16danlarkinI think that is part of &env?
12:16slyrushey joshua-choi, anything new with fnparse?
12:16joshua-choiI've just started working on it for the first time in a long time now.
12:16slyrusdid you get my email re: contexts and/or check out my SMILES parsing code that makes heavy use of them?
12:16slyruscool
12:17slyrusA common-lisp port would be nice too :)
12:17joshua-choiYesterday I carefully rewrote the core so that rules are not functions with metadata anymore, since that's apparently subject to removal.
12:17joshua-choislyrus: Hmm, no I didn't—well, when did you send it?
12:17slyrusthe fnparse/clojure SMILES parser is MUCH nicer than my hand-did CL parser
12:18slyrusoh, a while back -- a github message, IIRC
12:18joshua-choiOh, I think I did reply to that
12:18slyrusthere wasn't too much there, I was just saying that I make heavy use of contexts after you suggested avoiding them
12:18joshua-choidanlarkin: Thanks. I'll check it out
12:18joshua-choislyrus: Ah, yes, I remember
12:18joshua-choiI still think you should probably use defmaker instead
12:18joshua-choiOh well
12:19joshua-choislyrus: (The thing is that I think that contexts can make problems harder to determine. defmaker forces you to isolate whatever contextual information you're passing, which is better I think.)
12:20slyrusok, I'll take another look
12:20slyrusthe code in questions is here: http://github.com/slyrus/chemiclj/blob/master/src/chemiclj/smiles/read.clj
12:21slyrusif you free up any time to take a look at what someone with too little knowledge of fnparse whips up at first glance :)
12:21joshua-choiI need to improve the examples
12:21joshua-choiIt's quite impressive, I think
12:21slyrusI see the only defmaker I use is something I ripped off from your examples :)
12:22slyrusfnparse? I agree!
12:22joshua-choiOh, no, your code
12:22slyrusheh. thanks!
12:22joshua-choiYeah, I do need to improve the examples, especially clojure.clj, to make use of defmaker
12:22joshua-choiUgh, I don't wanna write that YAML parser
12:22chousermacros can the the file and line number. they aren't in &env
12:23joshua-choichouser: Can't?
12:23chouserthey can. I've done it.
12:23chousergimme a sec
12:23joshua-choiOh good
12:23joshua-choiThis will make rules able to say what line they're at when they make an error.
12:24hiredmanyou can pull a line number off &form, yes?
12:24chouser(:line (meta &form)) should give you the line number
12:24chouserand *file* should be the filename
12:25slyrusjoshua-choi: I'd like blog about my fnparse experiences writing chemiclj. might contribute to the global tutorial on things to do (and to not do) to effectively use fnparse
12:26joshua-choihiredman and chouser: Wonderful
12:26chouserI've got a potential use case for fnparse coming up. Haven't looked at it before.
12:26joshua-choislyrus: That'd be great; I think the API is effectively frozen now
12:26slyruschouser: I highly recommend it!
12:27joshua-choichouser: Currently, tutorials are nonexistent, examples are poor, but doc strings are okay
12:27chouserI'm afraid I have to learn lein first.
12:27joshua-choiWhat may be confusing is that it is actually split in two, with differences
12:27joshua-choiYou don't need lein.
12:27joshua-choiActually, doc-strings are poor too. I'm about to revise them.
12:28joshua-choiFirst, though, I'm going to try to make rules able to say what line they're at.
12:28chouserI've a week or two out from digging into fnparse
12:28joshua-choiBefore I revise documentation
12:29joshua-choichouser: I'm about to push a new tagged version today; use that when you do
12:29chouserok, great.
12:29joshua-choiContact me if you run into problems or questions
12:29chouserthanks, I will!
12:32chouserI'm having trouble finding where in Compiler.java code is emitted to call static methods
12:32chouserought to be a generated call to the fn object's invokeStatic, right? But I'm not seeing it.
12:32joshua-choislyrus: I'm going to try to finish FnParse before I look at your example. :(
12:32joshua-choiBut contexts are fine
12:32joshua-choiIt's just that I prefer defmaker
12:32joshua-choiIf it weren't for you, though, I would have removed them
12:33@rhickeychouser: not sure I understand, not StaticMethodExpr?
12:33lpetitHello, does this look like a corrected bug or still a bug, for you : "The class name the JRE appears to be complaining about is "compile__stub/net/cgrand/parsley/lr-plus/TableState".  The "lr-plus" part seems wrong.  I don't think it's legal to have a hyphen in a class name."
12:33lpetitIt happens with IBM V6.0 JRE for a ccw user. Other users using sun jvms (including me) have no problem
12:35lpetitTableState is a protocol
12:36lpetitrhickey, chouser: ^^^ maybe you know, 'cause I don't have an IBM JRE for testing, and the test done by the user was with a late 1.2 RC, but not the final release
12:37slyrusjoshua-choi: like I said, if there's a better way, I'm all ears, but for the moment that was the only way I could make sense of tracking the global-ish state without doing it by hand w/ clojure's mutable data types
12:37slyrusI'm looking into defmaker right now
12:37joshua-choislyrus: That's precisely why it's not so good in my opinion: contexts make it global-ish.
12:39slyruswell, if you've got global-ish state in the thing you're trying to parse, what other options are there?
12:39chouserrhickey: sorry, I meant :static functions
12:39joshua-choislyrus: Passing them as arguments into user-defined rule-makers.
12:40joshua-choiMaybe there isn't much of a difference...? I'm not so sure now.
12:40joshua-choiHmm
12:40slyrusyeah, that's just what I was thinking :)
12:41slyrusperhaps rather than a global context a special variable that goes partway up the stack might be useful
12:41slyruss/goes/is bound/
12:41sexpbot<slyrus> perhaps rather than a global context a special variable that is bound partway up the stack might be useful
12:41lpetitmust leave now, will try solve my issue by other means :'-(
12:42@rhickeychouser: see InvokeExpr.parse, will generate a StaticInvokeExpr
12:42joshua-choislyrus: I'm not sure that I understand, but I'm suspicious of the idea anyway. :) In any case, contexts aren't *that* bad...at least it's part of the state argument, rather than being a mutable global variable.
12:43joshua-choiAh yes. defmaker forces you, however, to more explicitly express *where* you're using that contextual data.
12:43slyrusyes, and if it's part of the state argument, how is that so different from defmaker?
12:43slyrusoh, I see
12:43joshua-choiIt forces you to state everywhere it's needed
12:44joshua-choiThe bad thing about that is just that—it may be tedious, especially if you're adding something to an already written parser
12:44joshua-choiBut I think that it is better, net-wise
12:44joshua-choiThat way, where it's used is not so hidden, a disadvantage associated with big data structure arguments and imperative assignment.
12:45joshua-choiIt is a trade-off.
12:45slyrusthe idea of the special variables (to use the CL term, are the called the same thing here? it's whatever happens when you (bind [...]) things would be similar but you would avoid the tedium of passing the stuff as args
12:46slyrusI notice I have a bunch of defns that take context as the first arg. probably good candidates for defmaker
12:46joshua-choiPrecisely. I have bind, by the way.
12:46joshua-choiI mean, I hate bind.
12:47joshua-choiIt has given me bad trouble before. :(
12:47joshua-choiI have to go for a bit!
12:47slyrusok, nice talking to you!
12:49slyrusand in CL bind is just let, but with extra magic for special variables. it can certainly easily be overused.
13:00chouserrhickey: ah, perfect. thanks.
13:17joshua-choislyrus: Are you there? I want to ask a question.
13:27slyrusyes
13:27slyrusI sent you a github message re a simple defmaker example
13:28joshua-choiI got your message by the way. I don't think that's not a good place for a rule-maker.
13:28joshua-choiEither keep it as a regular function or change it to a rule. There is never any point to having a rule-maker with no arguments.
13:28slyruswell, yes, that's the next question :)
13:29joshua-choiBut I think I've already decided the answer to my own question. It's if I should convert every standard rule maker into a macro...so that they can determine at what line they were called in.
13:29joshua-choiI think the answer is no.
13:29joshua-choiIn order for a rule to be able to give an error that says at what line the rule was defined at, the rule maker that made that rule must be a macro...
13:30slyrusoh, right. ok, I'll keep plugging away at my defn-'s then
13:30joshua-choiBut there's that adage saying that macros are a pain and should be used if you really really need them
13:31joshua-choiI would like to say, though, that(h/defrule bond-symbol-order
13:31joshua-choi (h/hook #(get {\- 1 \= 2 \# 3 \$ 4} %)))
13:31joshua-choiis okay.
13:32slyrusI think I started with a bad example. That was deep down inside some defn-'s. I need to go back up to a function that I call directly from a rule and figure out how to replace that with a defmaker
13:33slyrusprocess-ring might be a good example if you're looking at my code
13:33slyrusright now I do (h/alter-context process-ring ring-num bond-symbol) ... and all sorts of stateful magic happens based on what's in the context
13:34slyrusat a minimum, I could remove the explicit passing/setting of the context by using a defmaker for that
13:34slyrusbut I guess I'm not quite sure when in a defmaker what the difference between the args and the subsequent args to, say, an enclosed h/hook are
13:37slyrusand I suppose my defmaker forms should look like (defmaker <foo> ....) to remind me that it's just a (special (well, not in _that_ sense)) rule?
13:42chouserjoshua-choi: could you examine the fn metadata to get a line number in cases where it wasn't created by a macro?
13:44joshua-choichouser: If I understand you correctly, then no, since what I want are the line numbers where the function was *called*, rather than where it itself was defined.
13:44joshua-choiI think only macros can do that, with (meta &form).
13:45joshua-choislyrus: Don't use angle brackets to delineate rule-maker symbols. I don't know if we should adopt some other sigil/etc...but I don't think angle brackets themselves are a good idea.
13:45joshua-choiUse 'em for rules, rather than rule-makers.
13:49joshua-choislyrus: A rule-maker is a function (or macro?) that returns a rule.
13:49joshua-choilit is a rule-maker. So is hook.
13:50slyrushow is a rule-maker different than a rule with a hook?
13:50slyrusI think I need to work through some examples to figure this stuff out
13:50joshua-choiI need to go! But a rule-maker is any function/macro that returns a rule, nothing more.
13:50slyrusok, ttyl
14:18AWizzArdrhickey: https://visualvm.dev.java.net/relnotes.html#changes
14:18AWizzArd“Recognizing Clojure, Groovy, JRuby, Jython and Scala runtimes”
14:19rainerschusteruh, nice
14:19headiuswhat on earth does that mean?
14:20rainerschusterprofiling?
14:20rainerschusterdetecting performance bottlenecks by running variant code path
14:20headiusseems unlikely; unless they've done a lot of work, profiling jruby with java tools would miss interpreter
14:21headiuspretty sure jruby's the only one in that list with an interpreter, though
14:21rainerschusterhuh? maybe they're into the ASTs ..
14:21headiusyeah, beats me
14:21headiusnobody contacted me about it though
14:21rainerschusterdon't know. is it possible to hook into the interpreters
14:22headiusthere's no standard API for hooking language-specific calls, and only a JRuby-specific API for capturing "call" and "return" events across interpreter and compiler
14:22headiusit's certainly possible they're using that, I guess
14:23rainerschusteri'm a .net guy, don't know how the JVM works
14:23AWizzArdI don’t know what exactly this means, but it sounds like they have improved this profiler for Clojure, at least to some extent.
14:23headiusperhaps they're unmangling some compiled names
14:24headiusall supposition!
14:24AWizzArdWe will see it soon. I guess in the next jdk they will include version 1.3+
14:24rainerschustermonitor of performance and memory consuptions is quite low level, nothing related to the interpreters
14:24headiuscould also just be support for writing visualvm plugins in those languages
14:24chouser"VisualVM now recognizes the Clojure, Groovy, JRuby, Jython and Scala runtimes, enabling these developers to easily find the appropriate processes."
14:25rainerschusterplugin architecture
14:25chouserhttp://profiler.netbeans.org/blog/images/visualvm_13_altjvmlang.png
14:25rainerschustermaybe one prof per int
14:25headiuschouser: ahh, so it's recognizing from command line that it's one of those lanuages
14:25headiusor via some other mechanism
14:25chouserI think it just can tell when a particular vm pid has clojure inside it.
14:26headiusseems simple enough
14:26chouseroh, or perhaps from the command-line, though that sounds a bit fragile
14:26chouserof course a vm can have jruby *and* clojure libs in it -- which icon to use then? :-)
14:26headiusjruby does register some mbeans, so they could use that...but who knows how they're doing it right now
14:26headiusyeah, exactly
14:27headiussome sort of lambdaruby icon
14:27chouserooh, lambdaruby!
14:27hugoddoesn't jvm have support for different "stratum"
14:28AWizzArdInteresting that they noticed Clojure.
14:28hugodjdwp that is
14:28chouserinteresting that they noticed anything at all besides java.
14:28AWizzArdbut not Scheme implementations or ABCL
14:29chouserhm
14:30cemerickchouser: hey, just toss a badge on the icon per-"runtime"! :-P
14:30headiuscemerick: with an alpha mask
14:30cemerickheadius: and little animated gif wiggles
14:30headiusooo
14:31rainerschustersome folks here from the clojure-clr branch?
14:31chouserwe know jruby is bigger and heavier, so should have a little clojure badge in the corner.
14:32headius:)
14:32cemericksha-ZAM! :-D
14:32headiusif it takes bigger and heavier to run on android unmodified...so be it
14:32chousernice
14:32headiusthough...that's kind of self-defeating too
14:33headiusI'm glad we've kept the interpreter, in any case
14:33chouserI just learned of team that ported a bunch of ruby code to C++ for performance.
14:33chouserI heard about it too late. jruby would have been perfect
14:33chouseror at least better than C++
14:38headiusthat's for sure
14:38headiusI'm working on some improvements in jruby 1.6 that should put it closer to java for general execution perf
14:39headiusboxed numbers are a hard problem, unfortunately (for clojure as well)
14:39danlarkinhiredman: ^
14:41dnolenheadius: have you look at the new static fns feature in 1.3, a reasonable work around given the situation.
14:42ninjuddcemerick: just read your hosted REPL proposal. good stuff.
14:43cemerickninjudd: Thanks; let me know if you have any ideas/feedback/whatever.
14:43ninjuddcemerick: i've been having thoughts of writing something similar to clean up the protocol used by cake to communicate with the persistent jvm
14:43cemerickI'm hoping to knock it out this week, at least in prototype fashion.
14:44ninjuddcemerick: it seems to me like what you're proposing is more than just a REPL protocol, right? you talk about it being for non-interactive use too
14:44cemerickninjudd: Nifty. By all means, make sure I'm making it so that you can use it.
14:44cemerickYeah, I'm going past the typical interactive usage model.
14:45cemerickNecessarily so, really. The requirements of tooling demand it IMO.
14:45headiusdnolen: static fns, no
14:45headiussounds like a dodge
14:45headiushow does it work?
14:46ninjuddcemerick: right, i need that too to be able to send cake commands to the jvm
14:47joshua-choiHas anyone looked into aliasing protocols? E.g. (clojure.contrib.def/defalias P another.ns/P)? Does it completely work?
14:50ninjuddcemerick: one thing i would need to be able to use it for cake would be a way for threads to report back incremental output as they run. for this reason, i was planning for each socket to represent a single thread and open multiple sockets or use clojure's concurrency constructs if i needed to do things asynchronously. do you think if would be too hard to do incremental output with a message based protocol?
14:51ninjuddcemerick: this is also something people expect with an interactive REPL.
14:51headiusdnolen: found a post on static fns
14:52headiusmy hands are somewhat tied as to what I can add to ruby, but I've considered extensions to allow optional static typing
14:52headiusI'm just happy I've gotten fully-boxed math (like in fib) to exceed clojure perf
14:54dnolenheadius: well with static fns, Clojure perf on fib is identical to Java.
14:55headiusbecause it's basically Java then :)
14:55headiusit's a little surprising how many "long" declarations are needed, looking at this example: http://clj-me.cgrand.net/2010/06/10/primitive-types-support-for-fns-coming-to-a-clojure-branch-near-you/
14:56cemerickninjudd: that's interesting. It's not quite what you want/get in an interactive setting, insofar as you still want the information coming back to be packaged as discrete messages (so you can track and associate them with client-side processes, etc).
14:56dnolenheadius: it's a bit more clever then that, static fns can still used higher order. things still need to be shaken out, but will cool when usable with vectors of primitives (map, reduce, filter)
14:56dnolenheadius: that level of type hinting is unnecessary now in the 1.3 branch
14:57dnolenheadius: well on literals anyway.
14:57headiusyeah, I'd assume literals wouldn't need hints
14:57headiusmost anything else I'd expect to need it though
14:58headiusclojure has a much simpler dispatch path as well, so even with static type hints in jruby we still need to dynamically bind most things
14:58ninjuddcemerick: would it simplify the protocol to just make it synchronous and use multiple connections if you need to send multiple commands in parallel?
14:58headiuswith no type hints at all I can get fib(38) down to around 3.5s, which I think is pretty good for fully-boxed
14:59cemerickninjudd: well, that would be the only way to do it given what I've sketched out so far. I'll have to think about what you've suggested though.
15:00headiusdnolen: I assume the collections support for primitives will mean shipping specialized versions of them
15:00headiusint vector, long vector, etc
15:01ninjuddcemerick: you could open one connection for the interactive repl, and one for the tooling (using future and such to run commands asynchronously)
15:01cemerickright
15:02cemerickbut it's possible that asynchronous, multiple reply messages will end up being a simple (optional) extension
15:02chouserheadius: the different primitive types for collections are generated via macros
15:02headiusbut the ultimate result is specialized collections
15:02chouseryes
15:03chouserno
15:04chouserthey're all clojure.core.Vec, but it uses different "ArrayManager" classes internally
15:04chouservalure are still boxed going in and out
15:04ninjuddcemerick: sure. this is kind of along the same lines of what Laurent was talking about with telnet...
15:04chouservalues
15:05headiuschouser: that's what I figured
15:06cemerickninjudd: not quite -- he was hoping to avoid any concrete protocol entirely in that scenario, which makes things pretty difficult. Multiple asynchronous returns is far, far simpler on first blush.
15:11ninjuddcemerick: right, there would still need to be some sort of protocol for the synchronous mode, so you know what is coming back over the socket (stdout, stderr, return value, exception) and so you can send interrupts and stdin out from the client
15:11cemerickI'm not certain that there *will* be a synchronous mode.
15:12cemerickA given client can make an async connection appear synchronous to the user at the keyboard.
15:13ninjuddthat's why i used the conditional "would"
15:13cemerickah, sure
15:14ninjuddnow that i think about it, once you implement the synchronous protocol, it isn't much of a jump to make it work asynchronously
15:15cemerickthe protocol itself has little to do with sync vs. async.
15:15cemerickInsofar as you can base the former on the latter from a client perspective, I'll be focusing on the async.
15:15chouserwise
15:16cemerickAssuming I can get the backend working nicely, the biggest challenge will be to get it to talk swank (or to get SLIME to talk whatever-this-REPL-thingy-will-be-called).
15:17chouseremacs is your first client target?
15:17cemerickoh, no
15:17cemerickccw, enclojure, hopefully vimclojure, and perhaps cake
15:17chouserok
15:18cemerickemacs is tied to swank for the foreseeable future, but I've no desire to be in the same position.
15:31ninjuddwhat is the accepted way to throw exceptions in clojure code? should I use gen-class to create a custom exception class, or just throw java.lang.Exception?
15:31hiredmanclojurebot: exceptions?
15:31clojurebothttp://paste.lisp.org/display/74305
15:31cemerickIllegalArgument, IllegalState, and IOException will bring you a long ways.
15:32hiredman^-- list of exceptions that already exist
15:32cemerickeh, most of those shouldn't exist to begin with
15:32chouserninjudd: also consider clojure.contrib.condition
15:33hiredmansun.jvm.hotspot.debugger.win32.coff.COFFException
15:33hiredmanno one ever expects that one
15:33cemerick(throw (COFFException. "blah")) ;; this actually means we can't connect to the server ;-)
15:34chouserheh
15:34technomancyes.com.sun.inquisitions.SpanishInquisition
15:34ninjuddhehe. never heard of c.c.condition. looks interesting
15:36raekit uses gen-class under the hood to make a special exception holding a map
15:37raekand exception handlers are selected by the result of a function applied to the map
15:37raekmuch like multimethods...
15:39ninjuddso does c.c.condition supersede c.c.except?
15:43cemerickchouser: do you have any interest in #clojure logs from before 2/1/08? I have just a few.
15:44cemerickheh, almost all joins and parteds though :-)
15:52raekninjudd: have you read this? (link from docs): http://groups.google.com/group/clojure/browse_frm/thread/da1285c538f22bb5
15:55arohnerwhat was the name of the clojure webapp channel?
15:56kencauseyarohner: #clojure-web?
15:56arohnerkencausey: thanks
15:57kencauseyarohner: You might want to read /msg alis help for future reference ;)
15:59ninjuddraek: just did.
16:00raekdon't think there is much more info on that manner than that... :)
16:19@rhickeyI'd like shorter names for unchecked-*, so optimized code isn't so ugly
16:20@rhickeya first cut would be inc! and dec! etc, where ! indicates danger
16:21@rhickeysomething similarly easy to append would be fine too
16:21sleepynatewhat about "uck"
16:21sleepynateyou know you wanna uck-dec
16:22lpetitHello all
16:22mrBlissAdd * to the end? Also replace multiply, add etc with * + /.
16:23lpetitI confirm there's a problem with the compilation (either live or AOT) of e.g. types, if the namespace containing the type definition cointains dashes.
16:24lpetitIt's quite easy to reproduce: create src/net/yournick/lr_plus.clj , and in this file, have just (ns net.yournick.lr-plus) (deftype Foo)
16:24lpetitAOT compile this , and shebang! in your classes/ directory you see the following folder structure: classes/net/yournick/lr-plus/
16:25lpetitlr-plus/ contains the Foo.class file
16:26lpetitthe problem is that while apparently with Oracle JVMs everything works fine while you don't try to AOT compile it, it does not work (even if not AOT'ed) with IBM JRE 6:
16:26lpetitCaused by: java.lang.ClassFormatError: JVMCFRE068 class name is invalid; class=compile__stub/net/cgrand/parsley/lr-plus/TableState, offset=0 (lr_plus.clj:8)
16:27lpetitThe net result is that all users of ccw which use an IBM JVM simply cannot use it :-/
16:28lpetitCould someone try to reproduce this on his machine ?
16:28lpetitOr do you think I can file an issue directly ?
16:30@rhickeylpetit: please file an issue, thanks
16:30lpetitok
16:34lpetitrhickey: do I leave all the defaults values ("Assigned to" blank, Milestone Backlog, Priority Normal, Component empty, Approval empty) ?
16:35@rhickeyyes
16:37lpetitok done, ticket #432
16:37@rhickeylpetit: thanks
16:37lpetitnp, going to bed now, cu
16:37@rhickeyhow about a global toggle for overflow checking?
16:38arohnerrhickey: I'd prefer something more local, like a function or binding
16:39cemerickrhickey: I know you've not wanted to go down this road in the past, but separate namespaces seem to make a lot of sense here.
16:41cemerickIt'd even be a perfect example of wholesome use usage ;-) (:use 'clojure.unchecked)
16:43chousercemerick: sure, might be fun.
16:44cemerickchouser: They're colloquy logs, which are XML :-P
16:44chousercemerick: re: old logs, that is. take the spotlight off my newbie questions a bit. just email whatever format you've got.
16:46chouserclojure-log site is already based on two different formats.
16:48cemerickninjudd: FYI, I've added your REPL question to the design notes, with a slight response.
16:49cemerickWould you like write privs so you can add more ideas/issues as you think of them?
16:49ninjuddcemerick: sure. thanks
16:50cemerickninjudd: just need your google docs email addy; /msg it if you like
17:59mvidis there a simple way to turn a sequence of strings into one large comma delimited string?
18:04slyrus,(apply str (interpose "," ["this" "is" "bogus"]))
18:04clojurebot"this,is,bogus"
18:05arohner,(clojure.string/join "," ["this" "is" "bogus"])
18:05clojurebot"this,is,bogus"
18:12rainerschustersomeone interessted in helping translate the contrib libs to .NET?
18:14slyrusI'm sure there's a java library that does just that accessible by maven. just add it to your project.clj, run lein deps, restart your jvm, call the StringConcatenatorGenerator, loop through the sequence calling addStringToBeConcatenated, download the InterposerGenerator framework, connect that to the concatenator and then ask the StringConcatenatorRenderer to do the hard work for you. These...
18:14slyrus...java frameworks are awesome!
18:15rainerschusterhuh?
18:15rainerschusteris that related to my question?
18:15slyrusno
18:15rainerschusterpuh
18:16rainerschuster:)
18:16slyrusstring concatenation (poor joke, I guess)
18:16rainerschustertranslation to .NET could be seen as string concatenation
18:16slyrusheh
18:29technomancydang; I was hoping they'd drop -master- from the version string in 1.3 =\
18:34alexykninjudd: ping
18:34drewrtechnomancy: inc
18:34alexyklancepantz: ping
18:35lancepantzsup alexyk?
18:35alexyklancepantz: so, finally with cake, how do I do a new proto, given I have a myclass.proto file in a proto/ subdirectory?
18:36lancepantzalexyk: few steps
18:36lancepantzadd protobuf as a dev dep
18:37lancepantzyou probably want it as a regular dep as well
18:37alexykwhy both?
18:38lancepantzit has to be a dev dep to be able to use the task in the cake jvm, but it won't be put in an uberjar then
18:38lancepantzyou may not need it if you're just using it to compile the java class
18:39lancepantzan then you'll also want to add :tasks [protobuf.tasks] to your project.clj
18:39lancepantzthen cake proto should work
18:43alpheusAs a lisp1, clojure doesn't need flet or labels? Do I just use let for a local function?
18:43tomojalso letfn
18:44alexyklancepantz: where will it take protobuf.tasks, and how will it know which subdir has .proto files?
18:44tomojI think there is some fancy stuff you can do with flet/labels that you can't with let/letfn though
18:45lancepantzalexyk: it's hard coded to look for protos in project_root/proto
18:45lancepantzi'm not sure what you meant by the first part of your q though
18:46alexyklancepantz: are the protobuf.tasks in a file in the distro?
18:46lancepantzit's a namespace in clojure-protobuf
18:47alexykwow
18:47alexyknice
18:47alexykso you cook jars with their own cake tasks!
18:48lancepantzninjudd's effort at plugins, i think its pretty damn clean
18:50AWizzArdtomoj: could you please explain what fancy stuff you were thinking about, in respect to flet/labels?
18:55AWizzArdalpheus: you can use let, or as mentioned by tomoj letfn.
18:58tomojAWizzArd: I don't remember exactly, I think maybe it had to do with mutual recursion?
18:59tomojthere was something about clobbering too
18:59AWizzArdtomoj: mutual recursion is the difference between CLs labels vs flet
19:00tomojI dunno CL so the whole discussion was somewhat mysterious to me
19:01AWizzArdhttp://www.lispworks.com/documentation/HyperSpec/Body/s_flet_.htm
19:16alexykAWizzArd: how's your in memory database project?
19:22zoldarhello, I'm having problems with utf-8 characters in slime, when I send string from emacs to repl (for example "jaźń") it hangs - after reconnect prompt is available again. however in clean repl everything is working fine. I'm using leinigen (lein repl, lein swank etc.). Here's my .emacs contents: http://paste.lisp.org/display/114366 .
19:22AWizzArdI did not have time in the past 16 days. But hopefully better times are ahead. Anyway, it is pretty close for going public.
19:30hiredmanzoldar: slime has an encoding setting and so does the jvm, you need to get everything to agree on utf-8
19:31zoldari ran "export JAVA_TOOL_OPTIONS="-Dfile.encoding=UTF8"" before running swank
19:34hiredmanhow are you starting swank?
19:34zoldarjust lein swank
19:34hiredmanyou may need to set -Dswank.encoding to match the swank encoding from emacs
19:34hiredmanor slime encoding
19:35hiredmanhttp://github.com/technomancy/swank-clojure/blob/master/src/swank/swank.clj#L66
19:36zoldarswank.ecoding worked, thanks
19:49tomojdoes sexpbot work in PM?
19:49tomojfor stuff other than clojure eval I mean
19:56wtetzneris there a reader macro for 'verbatim' string literals?
19:57wtetznerfor example, you could write "\n" instead of "\\n"?
19:58hiredmanno
19:59wtetznerare there any plans to add it, or was it discussed already and deemed a bad idea?
19:59phobbsHello everyone
20:00phobbsis there a macro for automatically memoizing recursive functions?
20:00chouserwtetzner: I'm supposed to be coming up with a proposal for that.
20:00wtetzneroh, cool
20:00phobbsif not, I wrote one
20:03hiredmanphobbs: why do you need a macro?
20:03phobbshiredman: how else would you do it?
20:03wtetznerdefn-memo
20:03phobbsThat didn't work for me
20:03phobbsit didn't memoize the recursive calls
20:04phobbsis it supposed to?
20:04hiredmanphobbs: it depends on how the function is recursively referenced
20:05wtetznerah
20:05wtetznerdefn-memo is implemented in an odd way
20:05wtetznerit just calls defn, and then calls alter-var-root
20:06hiredmanif the function is created via defn, and calls itsself by name, then (defn foo [...] ...) (def foo (memoize foo)) would be enough
20:06wtetznerstill seems odd that it wouldn't work
20:06hiredmanif you recurse using recur then that won't work
20:06phobbshiredman: that doesn't work
20:06hiredmanphobbs: prove it
20:07phobbsI just did
20:07phobbsmy laptop can barely do (fib 30) that way
20:07phobbsand chokes on (fib 50)
20:07phobbspathetic
20:07phobbsit's obviously not working
20:07phobbswith my macro I can do (fib 2000) in 37ms
20:08hiredmanphobbs: prove it to me
20:09phobbsdo you want me to give you code that calculates the Fibonacci function?
20:09phobbsreally?
20:10tomojof course it chokes on (fib 50)
20:10phobbsif it's memoizing correctly, it shouldn't
20:10wtetzner(def fib (lazy-cat [0 1] (map + fib (rest fib))))
20:10tomoj"calls itsself by name"
20:11phobbswtetzner: I know how to do that
20:11phobbssometimes that isn't convenient for larger functions
20:11tomojdoes the one that can do (fib 2000) with your macro call itself by name?
20:11hiredmanphobbs: how else will I know what kind of code we are talking about?
20:11phobbs(defn fib [n]
20:11phobbs (if (<= n 1) 1
20:11phobbs (+ (fib (dec n))
20:11phobbs (fib (- n 2)))) )
20:12phobbssorry, should have pastebinned
20:12phobbsbut you get the idea
20:12phobbsit would work if memoized
20:12tomojI guess so
20:12phobbsif not, it would choke
20:13phobbswith that code, (def fib (memoize fib)) doesn't help at all
20:13phobbsand neither does replacing defn with defn-memo
20:13octewhat's the idiomatic way of doing something like "while ((line = reader.readLine()) != null) { .... }" in clojure?
20:14phobbsocte: you could use a (loop [line (readline)] ...)
20:15phobbsocte: with a test that would quit once line is nil
20:15phobbsand recurring with (read-line)
20:15hiredmanits because (defn fib []) expands into something like (def fib (fn fib []))
20:15_atophobbs: fib 50 looks fine with for me, fib 2000 I'd need to increase the stack size: http://gist.github.com/571111
20:15hiredmanso you lose the indirection through the var
20:17phobbs_ato: oh, I was doing the memoizing after defining the function
20:18phobbs_ato: hmm... I get a stackoverflow error too, even with 1000. So maybe writing this macro wasn't a total waste of time
20:18wtetznerphobbs: how does the macro work?
20:19phobbswtetzner: I'll post the code
20:19wtetznerk
20:20phobbswtetzner: it basically searches for recursive calls (not recur, unfortunately...), and replaces those with memo-table checks
20:20phobbstraversing the tree with zip
20:24phobbshttp://gist.github.com/571117
20:24phobbsI couldn't figure out how to allow docstrings
20:24phobbsthat's not a huge deal right now though... I just wanted to use it for some exercises for school
20:25phobbsinstead of writing repetitive code
20:25phobbsbtw my clojure style is really horrible, I'm pretty new to the language
20:25hiredmanwhat about (defn foo [] (let [foo inc] (foo 1))) ?
20:26hiredmanor (defn foo [] [(foo) (foo)])
20:26phobbsit would break
20:26phobbsit's definitely not a finished product
20:26hiredmansymbol manipulation is tricky
20:32phobbswtetzner: it appears to use less than 1/10th the stack size
20:32phobbsso that's something
20:36wtetznerphobbs: cool
20:37wtetznerphobbs: one thing I've learned with doing clojure is that a lot of self-recursive functions can be rewritten as self-recursive lazy sequences
20:37wtetznerphobbs: for example, http://pastebin.com/QaEibGCw
20:37wtetznerphobbs: just something to keep in mind when writing clojure code
20:39phobbswhoa, condp is awesome
20:40wtetznerhaha, yeah
20:40wtetznerit's like a really powerful switch
20:40phobbs^_^
20:40phobbsthanks
20:41phobbsbtw, what does cons produce?
20:41phobbsa list?
20:41wtetzneralthough, now that i think about it, (or (#{0 1} n) (+ val1 val2)) might be better
20:41wtetznercons returns a sequence
20:42phobbsI know... but under the hood
20:42wtetznertry it
20:42wtetzner,(type (cons 'x '(1 2 3)))
20:42clojurebotclojure.lang.Cons
20:42phobbs,(class (cons 'a '(1 2 3 4 5 6 7 8)))
20:42clojurebotclojure.lang.Cons
20:42phobbsyeah
20:42phobbswhat is that?
20:42wtetzneri think it's just a class that implements seq
20:43hiredman,(ancestors (class (cons 'a '(1 2))))
20:43clojurebot#{java.util.List clojure.lang.Sequential clojure.lang.IMeta clojure.lang.Seqable java.io.Serializable java.util.Collection java.lang.Object clojure.lang.Obj clojure.lang.ISeq clojure.lang.IObj :clojure.contrib.generic/any clojure.lang.IPersistentCollection clojure.lang.ASeq java.lang.Iterable}
20:43phobbshiredman: thanks
20:44_atophobbs: http://en.wikipedia.org/wiki/Cons
20:45phobbsheh, yeah I know
20:45phobbsthought clojure might use something fancy like a vector
20:45phobbsanyway, gtg
20:45phobbsthanks everyone
20:49_atophobbs: nah, Cons is just a simple class with two fields, pretty similar to every other lisp except perhaps that the cdr can be any sequence not just more cons cells: http://github.com/richhickey/clojure/blob/master/src/jvm/clojure/lang/Cons.java
20:50hiredman_ato: in most lisps cons cells can contain any two things, not something and a sequence
20:51_atohiredman: ah yes, you
20:51_ato're right, my mistake
20:51_atodotted pairs etc
21:16alexyklancepantz: how do I tell cake proto to use existing google protobuf, installed?
21:16alexykninjudd: ^^
21:17ninjuddit should use it if protoc is in your path
21:17ninjuddbut it still needs to download the code to create the jar
21:22alexykninjudd: ah, I migrated the mac and protobuf was lost. It downloaded something, were building, asked for password, then died
21:22ninjuddshould pick up where it left off if you run again
21:23alexykninjudd: java.lang.Exception: unable to find proto/clojure/protobuf/collections.proto on classpath
21:23alexykthat's second time
21:23ninjuddrenamed to extensions
21:23alexykbut it comes from cake proto!
21:23ninjudds/collections/extensions/
21:23alexykah, I have it in my proto
21:24ninjuddyour proto file likely has collections in it
21:24alexykyep
21:24alexykninjudd: did you get to sorted map yet? :)
21:24alexykyay, proto works
21:25ninjuddno, but i'll accept a patch ;-)
21:25alexyka-mazin'
21:25alexykI need to finish that PhD first... cake proto rocks!
21:25ninjuddi did update sets though so you can do delete-on-append
21:26alexykdelete-on-append?
21:26alexykdeleting from a buffer?
21:27ninjuddnormally, there is no way to delete an element from a repeated field by appending to the protobuf
21:27ninjuddbut i changed the set implementation so that you can
21:28ninjuddyou can pass in a map of items to booleans and it will convert to a set, deleted the items that have false values
22:18tomojcemerick: excellent work
22:21quizme(map #(apply % '(3 5) ) '(+ -) ) <--- why doesn't this return (8 -2) ?
22:24quizmeoh...
22:24quizme^^; hehe
22:25quizme(map #(apply % '(3 5)) [+ -])
22:32tomojhaha
22:32tomojthat is confusing
22:33tomoj,((juxt + -) 3 5) ; relevant to your interests?
22:33clojurebot[8 -2]
22:40duncan_bayneHi all, quick newbie question: following the instructions on http://weavejester.github.com/compojure/docs/getting-started.html but I'm getting "Wrong number of arguments to repl task" when I try to run the app. Am I using outdated documentation?
22:44duncan_bayneOoh, that might do it: running Clojure 1.0.0, but project.clj asserts Clojure 1.2.0. I'll go fix that as a first step ...
22:49scottjoh wow I can't believe I didn't know v in slime debugger would highlight the relevant form