#clojure logs

2011-10-08

00:27no_mindI am getting this error on using compile "java.lang.ClassNotFoundException: clojure.contrib.json.Read_JSON_From" . Does compile has a dependancy on json ?
00:57amalloyno_mind: the code you're trying to compile does
01:00no_mindamalloy: but the code I am compiling desnt use json
01:02amalloyi think that you are wrong
01:04no_mindamalloy: my code is not using json, maybe some other lib is. But at the same time I have clojure.contrib.json installed
01:04no_mindI am using congomongo, maybe that is using json.;..
01:09no_mindamalloy: a grep on the source code directory shpws this "Binary file ./classes/clojure/contrib/json/Read_JSON_From.class matches". So Why the error ?
01:09amalloy*shrug*
01:10no_mindclojure community is turning un helpful day by day...
01:10amalloyperhaps you tried to add some new libraries to the classpath without restarting the jvm
01:11no_mindI fired a fresh repl to compile
01:11amalloyno_mind: this is a volunteer helpforce. nobody pays me to know what causes compile errors on your machine, and i simply don't know given the information "compile fails due to json"
01:13no_mindno one pays anyone all over IRC to help anyone...
01:14amalloyyes, indeed. so when nobody jumps out of the bushes with a solution to your problem, complaining that the community is becoming unhelpful is sickening
01:14no_mindwhat I trying to do is already open sourced and available on github.. No one is paying me to do this...
01:14no_mindI am asking this for couple of days now...
01:15amalloyunlucky. perhaps nobody knows the answer, or you're not giving any information
01:15amalloys/any/enough
01:15lazybot<amalloy> unlucky. perhaps nobody knows the answer, or you're not giving enough information
01:21no_mindI am using IRC for over a decade now, so I know how to supply enough information for sure
01:24rimmjobthe channel is just slow at this time
01:29rimmjobcould you post a link to the source?
01:37zodiakno_mind, do a grep -l for contrib.json across the whole project. I assume you have lein dep'd and also have your git clone/source in checkouts so everything related get's searched ;)
06:49PleajureSeeker_Hey, I'm a noob in Clojure and I'm having troubles with the basics of (gen-class) - can someone help me?
07:09eliOcs hi guys!
07:09eliOcsanyone active around?
07:10eliOcscan someone help me with the swank installation
07:10eliOcsI
07:11eliOcsI've been following the installation instructions:
07:11eliOcs#
07:12eliOcsInstall clojure-mode either from Marmalade or from git.
07:12eliOcslein plugin install swank-clojure 1.3.3
07:12eliOcsFrom inside a project, invoke M-x clojure-jack-in
07:14khaliGeliOcs, yup and
07:14eliOcsshould I be alble
07:14eliOcsto connect via de SLIME command
07:14eliOcsI dont get de REPL
07:14khaliGno the clojure-jack-in takes care of that
07:14khaliGwhat happens when you type it?
07:15eliOcscompiles a bunch of files
07:15eliOcsbut it doesn't take me to a new buffer
07:15eliOcsor anything
07:16khaliGyea it should split the screen and show a repl on the bottom
07:16eliOcswow
07:16eliOcsIt did it now
07:16khaliGnice :)
07:16eliOcsthe first time it only did the compile
07:16eliOcsok this is odd
07:16eliOcsthansk khaliG
07:16khaliGnp
07:16eliOcsfeel stupid now
07:16eliOcshahah
07:25eliOcswhen you finally get the emacs with lein to work it seems a great way to develop
07:28ziltieli0cs: Do you have elein installed?
07:32eliOcsyep
07:32eliOcsI've installed lein
07:36ziltiNo, elein is a script for emacs to use lein with emacs
07:37eliOcsoooh
07:38eliOcshavent installed that yet
07:38eliOcsI'll google it a give it a try
08:20eiro(hello "world")
08:22Arafangion(hello "eiro")
08:52daniel___whats the equivalent in clojure of x = (1 2 3) ?
08:52daniel___(define x 1 2 3)?
08:53daniel___something like that
08:53Bronsa(def x '(1 2 3))
08:53daniel___merci
08:54daniel___and what does the ' mean
08:54Bronsait's synax macro for quote
08:55Bronsaso that clojure doesnt treat (1 2 3) as a function call
08:55daniel___i see, but why would it?
08:55daniel___is 1 a function?
08:55Bronsaindeed it is not
08:56Bronsabut first elements of lists are always treated as if they were a function
08:56Bronsain all lisps
08:56daniel___ok
08:56Bronsaif you dont want to syntax quote you either need to construct the list with (list ...) or use a vector
08:57Bronsadaniel___: keep in mind that if you syntax quote, none of the fields of the list will get evalated
08:57daniel___ok, thats what i want i think
08:58Bronsathen (def x [1 2 3 whatever])
08:58daniel___(def ratings '(map rating args)) will give me an 'array' with the ratings of whats in my list
08:58Bronsano
08:58Bronsait will bind ratings to a list with three symbols
08:58Bronsamap rating and args
08:58daniel___ah shit, ofc
08:59Bronsaif you want it to be evaluated you need to remove the quote
08:59daniel___so in this case i want []
08:59Bronsano
08:59Bronsain this case you want (map rating args)
08:59daniel___ok right sorry
08:59daniel___[] is a vector
08:59Bronsaso taht x will be bind to the result of applying map to rating and args
08:59daniel___and it is equivalent to '() in this scenario?
08:59Bronsa*that
08:59Bronsawell no
08:59Bronsasyntax quoting can be done on vectors too
09:00Bronsaand it prevents every element to be evaluated
09:00Bronsaa vector is different from a list (apart from performance details) in wich it doesnt treat the first element of itself as a function call
09:01Bronsayou can see the difference here
09:01Bronsa,[map identity 1]
09:01clojurebot[#<core$map clojure.core$map@149e15b> #<core$identity clojure.core$identity@1c81de> 1]
09:01Bronsa,(map identity 1)
09:01clojurebot#<ExecutionException java.util.concurrent.ExecutionException: java.lang.IllegalArgumentException: Don't know how to create ISeq from: java.lang.Long>
09:01Bronsafuck
09:01Bronsa,(map identity [1])
09:01clojurebot(1)
09:01daniel___ok, thanks Bronsa
09:01Bronsanp
09:01daniel___wait, is there a repl in this channel?
09:02daniel___,(+ 1 2)
09:02clojurebot3
09:02daniel___:D
09:02Bronsayou can query clojurebot too
09:10mbaci watched stuart halloway's presentation on clojure and simplicity and now i'm confused
09:10mbacmaybe it's because i'm a clojure newb
09:12mbachere's what i understood. i have a rigorous definition of simple. clojure is simple. ???. clojure rocks!
09:12mbacdid i miss anything else?
09:21mbachttps://blip.tv/clojure/stuart-halloway-simplicity-ain-t-easy-4842694 <- this presentation
09:26cemerickmbac: What was confusing to you?
09:28mbacthe feeling that i missed something
09:29cemerickit's hard to respond to that
09:29mbacright. so, what if he had done s/clojure/lisp/g
09:29mbacit's still mostly the same talk. yes?
09:30mbacwith the exception of vector-bindings
09:30mbacthose are EVEN SIMPLER than what other lisps do
09:31cemerickNot really. Lisp doesn't address the same issues Clojure does re: concurrency, state, data structures, etc.
09:31cemerickLisp, broadly speaking, that is.
09:31mbacmaybe i'm having a problem because i'm a lisp newb
09:32cemerickLisp is good, but homoiconicity doesn't solve everything.
09:33mbacwhat's novel about clojure wrt. lisp?
09:33cemerickmbac: please read: http://clojure.org/rationale
09:34mbac"Defaults to immutability"
09:34mbacok that's exciting. i thought all lisps did that
09:34cemerickgoodness, no
09:35mbachow do people get off calling lisp a family of functional programming languages when immutability isn't default?
09:35cemerickIn very rough terms, all you need to be a lisp is homoiconicity and first-class functions.
09:35cemerick"functional" is a very, very nebulous term
09:36mbacto me it means no side-effects
09:36cemerickSome people would argue that only statically-typed ML-style languages are functional.
09:36mbacand mutability menas programming with side-effecs
09:36mbacstrong static typing is orthogonal to functional programming
09:36cemericksome would argue that immutability is orthogonal to FP
09:37gtrak``i thought functional meant functions
09:37cemerickRight, that's about the only common ground. :-)
09:37mbacpure functions
09:37fliebelI thought functional means "does concurrency well" ;)
09:37cemerickmbac: yeah, zero consensus on that.
09:37mbacpure functions and mutability can't co-exist?
09:38mbacwhat? really?
09:38gtrak``mbac, of course not
09:38gtrak``pure functions have no side effects
09:38mbacyes, i agree
09:38cemerickInsofar as most would want to say that scheme is functional, we have to admit that e.g. Javascript is as well on purely technical terms. A lot of it has to do with accepted idioms.
09:38mbacwe have consensus :)
09:38gtrak``the part that coexists isn't a pure function
09:39mbacIn computer science, functional programming is a programming paradigm that treats computation as the evaluation of mathematical functions and avoids state and mutable data.
09:39mbacno consensus? it's the first line in the wikipedia article!
09:40cemerickWikipedia being the end-all, be-all, of course. :-)
09:40mbacduh
09:41mbacthat's why i'm citing it :)
09:41cemerickmbac: If you look at the 'Type Systems' section in that article, it's clear the whole thing is constructed from an ML perspective.
09:43fliebelAre there any NXT owners here? I'm thinking about writing a compiler, so I wonder if there is any "market".
09:44mbacalright. so, if he had done s/clojure/scheme/g it's mostly the same talk, except again vector-bindings
09:45cemerickexcept scheme isn't immutable by default, has no unified data structure story, no state abstractions, etc.
09:45mbacOK! unified data structure story. i want that
09:59Leenihey guys, take a look at this: http://shootout.alioth.debian.org/u64q/performance.php?test=fannkuchredux
09:59Leeniwhy does clojure solution use only 75% of CPU?
10:02fliebelLeeni: No idea. Have you tried running it yourself?
10:06cemerickgfredericks: Not really a big point of comparison; I'd be surprised if such a hit existed.
10:06gfrederickscemerick: I'd think there'd be plenty of shallow interest though, scheme being one of the two major pre-clojure lisps
10:07cemerickWell, there's *lots* of schemes, which makes things more diffuse.
10:07gfredericksi.e., I think lots of people would google it, whether or not it'd make an existing article. I suppose googlers don't will articles into existence though.
10:07gfredericksoh I did not know that.
10:07cemerickyeah, there's dozens of 'em
10:07cemerickscheme is an idea
10:07gfredericksI guess now there are lots of clojures too huh :/
10:07gfrederickslots == 3
10:08cemericksorta
10:08gfrederickssorta
10:08cemerickThey all have the same objectives, as reasonable given their host platforms.
10:08gfredericksright
10:08cemerickWhich is not true for the various schemes.
10:09gfrederickss/existing/interesting
10:09gfredericksthe phrase "high-level typo" just popped into my head
10:13Leenifliebel: also what's the deal with slowness. It uses java arrays and runs on clojure 1.3 yet 4 times slower than java
10:14gfredericksLeeni: they're not accidentially including the clojure load time in the measurements are they?
10:15LeeniI don't think so, otherwise java would not get so close to C in terms of time
10:15gfredericksLeeni: I guess I could imagine them accounting for jvm startup time but not clojure
10:18bsod1gfredericks: what do you mean by `lots of clojures` ? sorry I'm new at clojure..
10:19gfredericksbsod1: I was just referring to the 3 platforms it has been implemented on: jvm, clr, and javascript
10:19ziltiDynamic languages always are slower than static ones. Especially if they aren't aot compiled.
10:19fliebelIt took me a couple of seconds to realize we have an CLR impl too.
10:20gfredericksas cemerick pointed out, they're really a lot more unified than is implied by calling them "lots of clojures", where the differences between them correspond to the differences between the platforms
10:20bsod1gfredericks: is javascript implementation ClojureScript?
10:20gfredericksbsod1: yes
10:20gfredericksfliebel: yeah I've never really heard of anybody using it :)
10:21cemerickzilti: s/always/often
10:22zilticemerick: I'd actually like to see a counter-example, never seen any.
10:23gfrederickszilti: well you could certainly construct one just for the sake of a counterexample
10:24fliebelzilti: Counter example to what?
10:24gfredericksfliebel: "dynamic always slower than static"
10:24cemerickzilti: Such comparisons are often flawed because of algorithmic differences enabled/required by the respective languages, and trivial comparisons almost always favor static compilation strategies because of the limited latitude for runtime optimization, etc.
10:24cemerickI've written Clojure that's faster than the corresponding java, tho.
10:25gfredericksI think those performance tests should include development time :)
10:30ziltiOf course, since Clojure can be compiled aot it can reach the speed of Java. As for Clojure speed faster than Java speed, I guess that has a lot to do with the involved libraries? Not that I want to say "dynamic is slower, dynamic sucks". It has its technical reasons, e.g. about having to calculate position and length of data in ram
10:31gfredericksonce the hardware people stop innovating we can all sit down and take a few decades to make our high-level stuff as fast as is theoretically possible.
10:33fliebelgfredericks: I'd like to hear the hardware people on that. "Once the software people stop mucking around, we can take a few decades to develop super fast hardware.
10:34gfrederickslol. I bet they get peeved that they have to support the same arbitrary instruction set indefinitely
10:35ziltix86 was considered to be outdated almost 20 years ago
10:37gfredericksI wonder what kind of speedup is possible with a fresh redesign
10:37gfredericksalso I wonder what the implications on consumer computing would be if FP was moved off-chip
10:40gfredericksI guess that would kick javascript in the gut
10:43Leenino man, I'm just asking where's the slowup since it's using java arrays and why does it only use 75% of cores. Not asking for instance why is it grotesquely memory inefficient because that's par for the course for clojure
10:52Leenior this: http://shootout.alioth.debian.org/u64q/benchmark.php?test=knucleotide&amp;lang=all
10:53Leeniclojure always has shitty cpu utilization
10:54ziltiLeeni: One could as well ask why Scala is 7 times slower in the benchmark.
10:54gfredericksas someone who's not an expert, I would think that "grotesquely memory inefficient" could lead to "shitty cpu utilization", since the former could reduce the effect of memory caching
10:55Leenizilti: because it uses only one core
10:55fliebelLeeni: The other run on multiple cores?
10:55Leeniif you are talking about the first benchmark
10:56Leenior are you talkng about the second one
10:56Leenilook at last column CPU load
10:56Leenishows cpu load for cores
10:56Leeniclojure is always around 75% load per core and I don't see why...
10:57ziltiSecond test is funny. g++ 3.86 sec, gcc almost 20 secs, clojure 9 minutes...
10:58Leeniclojure has 60 seconds I believe
10:58ziltiAnd, to be honest, I don't really trust these benchmarks. Look at the different Scala tries. First attempt 37 seconds, fourth attempt "failed". huh?
10:59Leenidifferent code
10:59ziltiLeeni: no, first attempt of closure in the second benchmark is indeed 9 minutes
10:59Leenithose are not attempts
10:59ziltiversions?
10:59Leenidifferent submitted solutions
11:00Leenigenerally the best clojure one is ugly as hell with loop-recur, array operations and typehints all over the place
11:00Leenistill takes twice as much RAM and four times as much time as Java in general
11:01Leeniidiomatic clojure code is 9 minutes yes...
11:01arohneremacs masters, what is the name of the feature where comments in your source code get executed by emacs? typically used for formatting and things?
11:05Arafangionarohner: #emacs is awesome. :)
11:06ArafangionI notice that Clojure actually has a respectable position in that benchmarks chart... Particularly #5.
11:06ArafangionAlthough it does have a lot of hints.
11:07pdkwhere's this benchmarks chart
11:07pdklanguage shootout?
11:07ArafangionYeah, that one.
11:08ArafangionIt would be interesting to see that shootout if the startup delay was factored out.
11:08ArafangionSuch that the routine itself was compared.
11:09Leenicompare it with java
11:09Leenisame startup
11:10ArafangionLeeni: Notice that the java code has fewer classes needed, it probably doesn't need to load any support used by Clojure or anything.
11:10Leeniand I don't think startup delay is factored in
11:10ArafangionNo, I doubt very much that it is.
11:11Leenior look at regex-dna test
11:12ArafangionClojure is much closer to Java there.
11:13ArafangionHmm, no, it's still roughly 10x slower.
11:13ArafangionBut that Java code there is horrible.
11:14ArafangionInteresing how C is consistently very high up.
11:16ArafangionHmm, "all shootouts" and "all languages" gives a /very/ interesting chart.
11:17ArafangionClojure is /always/ slower than C++.
11:17Leenino shit lol
11:17Leeniyou don't need a shootout to figure that one out
11:17ArafangionLeeni: Well, it's interesting because it's not always slower than C.
11:17ArafangionThe best clojure is faster thaan the worst C.
11:18gfredericksthe worst C has sleep calls in the inner loop
11:18LeeniI think the negative surprises are: how much slower it is than java, how ugly the code for fastest case is and how low the CPU utilization always is
11:19ArafangionThe low CPU utilization would be the only thing that concerns me there.
11:20ArafangionNote that I have yet to actually /use/ clojure.
11:20Leeni:)
11:21ArafangionUnlike the shootout folks, I actually know how to optimise.
11:21LeeniI think the big letdown is that in java I can write idiomatic code and I am pretty sure I am within 30% of speed of hand optimized code, in clojure with idiomatic code you can be pretty certain you are running code three times slower than optimized code
11:22ArafangionLeeni: That's a point, however, that said, my favorite langauge is python.
11:22ArafangionAnd I'm sure real-world clojure code is probably faster.
11:22Leeninot really
11:23Leenioperations on collections are expensive
11:23ArafangionUnfortunate. :(
11:23Leeniiterating though a sequence is expensive
11:23ArafangionIn python, doing a function call is expensive.
11:24Leenijust walking through a sequence and printing results will result in tons of memory allocations
11:24ArafangionThat's unfortunate - whose fault is that? Clojure, or the VM?
11:24Leeniclojure
11:25ArafangionWell, someone will just have to optimise clojure a bit more. :)
11:26Leenithis is impossible... you need to allocate an object for each member of a sequence otherwise you'll be breaking the abstraction
11:26ArafangionPerhaps you could reuse objects.
11:27Leenisequences must support ability to pass tails of sequences around
11:27Leenithus you need to allocate a sequence object for each element of sequence you realize
11:28ArafangionI'm sure they could still be reused. Perhaps have it copy the iterator on-demand, as well as reusing a shared pool of iterators.
11:28Leenithis is where clojure is very different from java loops or Iterable
11:28ArafangionWell, no, that makes sense.
11:28Leenibascially imagine a linked list
11:29ArafangionI can imagine it, but even so, I'm sure that there's going to be a typical use case that you can optimise for.
11:29Leeni(range 10) will produce 10 linked list(sequence) nodes
11:29ArafangionYou can't produce them lazily?
11:29Arafangion(Which is what I'm getting at)
11:29Leeniyes lazily
11:30ziltiThey are produced lazily
11:30Leenibut imagine you feed them into a function as a sequence of indexes
11:30Leenithey will all get realized inevitably
11:30ArafangionYou can't, say, pre-generate 100 linked lists and reuse them, lazily initialising more if you have the need?
11:30ziltiList = single-linked list, Vector = Java-Array
11:30ziltiSo why is Vector still so much slower?
11:30ziltiThat should be easy to optimize
11:31Leeniin any case where java would have iterable that returns 10 Integer objects, clojure has 10 sequence objects allocations
11:32Leeniin java ArrayList is faster at adding elements in the front than LinkedList up to I think 10000 or 100000 elements, even though it's O(n) for arraylist and O(1) for linked list. Simply because linked list add results in an allocation for each element added
11:32ArafangionSeems that the obvious solution is to reuse the sequence objects.
11:32ziltiI guess that's because all operations on collections are only realized using first and rest functions
11:33Leenizilti clojure vector is not array, it's a tree with 20 branching
11:33Leenihence it's really expensive to modify, because you have allocation of nodes again
11:33Leeni(among other things)
11:34ziltiHuh, that's strange cause in the screencast he says otherwise (Clojure for Java programmers)
11:35Leenii;m 100% it's a tree
11:35ArafangionJust looked at the source for sequence.
11:35ArafangionI notice that it's a clojure implementation, not Java.
11:36Arafangionhttps://github.com/clojure/clojure/blob/f5f827ac9fbb87e770d25007472504403ed3d7a6/src/clj/clojure/core.clj#L2350
11:36Leenijava doesn't have sequence, only Iterable interface
11:36dnolenLeeni: it's not *that* expensive to modify. plus you get all the safety benefits.
11:36dnolenLeeni: and it's not 20, it's 32
11:36ArafangionLeeni: That doesn't follow.
11:37ArafangionLeeni: Well, yes, Java doesn't have a sequence type, but that doesn't mean that it can't.
11:37ArafangionLeeni: I'm sure you'd be able to write one in Java? That was the observation I made, that it was Clojure.
11:37Leeniwouldn't change anything
11:37LeeniI mean if it was the same algorith
11:38ArafangionA Java implementation is *unlikely* to use the same algorithm!
11:38Leeniproblem is that sequences as they are conceptually produce a ton of allocations on first walkthrough
11:38Arafangionmap does even more allocations.
11:39Leenipoint being?
11:39dnolenfortunately the JVM is really good at allocations.
11:39Leenimap isn;t known for being fast
11:39Leenidnolen: still way way way worse than not doing allocations at all
11:40dnolenLeeni: in many applications the allocations hardly matter. Ever.
11:40Leeniit's why arraylist is way faster than linkedlist
11:40dnolenLeeni: it's easy to use a better data structure if the allocations matter.
11:40Arafangiondnolen: You have more or less the same cost for allocations in Java as you do in other environments.
11:41Arafangiondnolen: But deleting the objects is effectively free.
11:41Leeniallocations always matter
11:41Leenithey produce large slowdowns
11:41ArafangionNot if you pre-allocate.
11:42ArafangionPython, for instance, will pre-allocate and share integer objects.
11:42Arafangion(The first hundred or so, anyway)
11:42Leenijava has that too
11:42ArafangionLeeni: I'd be willing to bet it doesn't do that automatically for user-defined classes.
11:42Leeniyou are right it doesn't
11:43dnolenLeeni: in anycase "large" slowdowns doesn't really play out much in practice. If you need to write high perf low allocation code in Clojure it can be done w/o much effort.
11:44ArafangionThe JVM, can, at least, abstract most of the performance issues of using the native platform allocator.
11:44dnolenin any large code base you need to produce against mutability somewhere - so what are you going to do? deep copy an entire nested structure
11:44dnolenyuck
11:45dnolenexpect const to save you?
11:45dnolenyuck
11:45dnolenexpect that somebody would cast to a mutable type?
11:45dnolenyuck
11:45Arafangiondnolen: Arguably. The need to do so depends on your application design.
11:45ArafangionThere is still, however, a lot of copying going on. :(
11:46dnolenArafangion: well I'm no expert but I've rarely written code that doesn't need it after certain threshold.
11:47Leenihere's the dealio, if most basic operation (walking through a sequence) is slow then it's gonna affect all programs...
11:47Arafangiondnolen: I tend to restrict such large structures to the module it belongs to.
11:47Leenistill need to solve the mistery of low CPU utilization
11:47ArafangionLeeni: Walking through a sequence is slow in python, too, despite python not needing to pass tails.
11:48Leenithat's weird
11:48ArafangionLeeni: Mostly because function calls are slow.
11:48LeeniI've wrote a java function that returns and Iterable like clojure function range and was much faster
11:49Leenithen again, you couldn't pass it around
11:49LeeniI mean mid-iteration
11:51ArafangionLeeni: I should get to bed, otherwise I"m going to stay up thinking of a nice implementation that would allow you to do that, it doesn't seem to be that hard a problem.
11:51ArafangionAgain, speaking of someone who has never done clojure, perhaps there's something I'm missing entirely. :(
11:51dnolenArafangion: it's hard, you need to consider concurrency, locks, etc.
11:52Leenigotta figure out how to make the clojure 1.3 work with clojurebox or counterclockwise
11:52Arafangiondnolen: Oh, concurrency, forgot about that, but it'd still be doable, imho.
11:52dnolenArafangion: of course Clojure has already done the work for you :) and it's hard.
11:53Arafangiondnolen: From what I hear, you're optimising for the worst case, specifically, the assumption that a tail is always passed.
11:53dnolenArafangion: just working for an Iterable is not enough anyhow, you want array-like, set-like, etc.
11:53dnolenmap-like
11:53ArafangionMeh, that makes it a non-trivial amount of code!
11:54dnolenthus be lazy, use Clojure
11:54dnolenwork done
11:54ArafangionOn that note, G'night. :)
11:54Leeni:D
11:56Leenidnolen, do you know why on this benchmark http://shootout.alioth.debian.org/u64q/benchmark.php?test=fannkuchredux&amp;lang=all clojure's CPU utilization doesn't exceed 75% per core?
11:56Leenior any other benchmarks practically
11:56ArafangionPossibly locks.
11:57Leenithen C and java would have same problem too
11:57Leenithese algorythms seem easily paralelizable without locks
11:58dnolenLeeni: no I haven't looked at that code very closely, but that's code based off of 1.2.0, and I see some things that I wouldn't do.
11:59Leeniunder notes it says 1.3.0
11:59dnolenthe code itself is written for 1.2.0
11:59Leeniquite probable
11:59Leeniwhat wouldnt you do?
11:59dnolenLeeni: I know, I've been writing Clojure for 3 years :)
12:00Leeniwell I haven't and I can't find the screwup
12:01dnolenremove all the unnecessary casting, don't use range to allocate contents of array.
12:01LeeniI was thinking pmap was enough to get all the cores running at max
12:02Leenihehe I use range a lot
12:02Leenior (iterate inc 0)
12:02dnolenLeeni: as you should, unless you writing silly benchmarks.
12:02Leeniyeah I know range is much slower than a nice loop recur
12:27thorwili suspect that i have a case where i can't compile a file, because it refers to a class in a required file, in which it's the job of a macro to create that class
12:28thorwilactually, if i require a file, all the macros should get expanded, before anything else happens, or?
12:31thorwilit's appengine-magic's defentity, e.g.: (ds/defentity Article [title, body, created, updated])
12:31thorwilwhere i need to refer to Article in another .clj
12:36thorwildefentity expands to a defrecord: https://github.com/gcv/appengine-magic/blob/master/src/appengine_magic/services/datastore.clj#L380
12:42gfredericksthorwil: what sort of error are you getting?
12:43gfredericksand do you remember to import the class?
12:44thorwilUnable to resolve classname: Article
12:45thorwilgfredericks: i take this needs special handling then. import apparently ;)
12:45gfredericksthorwil: anytime you use a class created with defrecord or deftype you have to import it to refer to it directly
12:48thorwilgfredericks: ah, thanks. given the defrecord is in tlog.models.backing and called Article, what's the right import?
12:52thorwilnm, got things mixed up :)
12:56halarnold2000does stuart sierra have a nik on this channel?
12:57gfredericksthorwil: your hope looks right to me, which I presume you figured out on your own while I was not replying
12:58thorwilgfredericks: indeed
12:59thorwili was just juggling too many buffers ...
12:59gfredericksbuffer-juggling => buggling
13:01zerokarmaleftbuffuggling
13:02gfredericks(inc zerokarmaleft)
13:02lazybot⟹ 1
13:02gfredericksHA! Whaddayagonna call yourself now!
13:03thorwillol
13:11halarnold2000.
13:19zerokarmaleftgfredericks: i'm immutable :P
13:20gfrederickszerokarmaleft: does that ever change?
13:23zerokarmaleftgfredericks: probably when i get married and have kids
13:31mbacwhat's the way to represent an association list in clojure?
13:31mbacis a list of vectors appropriate?
13:32mbac([a b] [x y])
13:32duck1123mbac, there's a hash: {a b x y}
13:33duck1123do you want to be able to find b if you have a?
13:33meliponeI need to use the expt function from clojure.contrib.math but the abs function is conflicting with Incanter.core. How do I mix the two?
13:33Bronsamelipone: :as ?
13:34bsod1is there a better way to reload definitions other than calling (load-file ...) again?
13:34meliponeokay, that might work. I was trying (use 'incanter.core :exclude abs) but that didn't work
13:35Bronsamelipone: try with :exclude [abs]
13:35mbaci only want to iterate them. hashes seem overkill
13:35duck1123melipone: usually it's better to either require with a prefix (:as) or use only the vars you need (:only)
13:35meliponethanks!
13:36gfredericksmbac: hashes are probably more idiomatic. And they're easy to iterate over because they're seqable: ##(seq {:a 3 :b 489 :c 28})
13:36lazybot⇒ ([:a 3] [:b 489] [:c 28])
13:37gfredericksbut if you have some tiny piece of code where you feel like it's silly to use a hash, then I don't think anybody will jump out from behind a bush and yell at you
13:37mbachaha
13:38duck1123it all really depends on what you want to do with them. A seq of vectors might be more appropriate for you
13:38gfredericksmbac: hard to say anything else without more details
13:38mbacthat's about it.
13:41devnhow DARE YOU, sir!
13:42mbacwhat's the function that takes an f and a coll and returns the first x where f x is true
13:42mbac(coll means sequence-like thing right?)
13:42zerokarmaleftsome
13:44mbacclose, i want the x not the truthness
13:44Bronsambac: (comp first filter)
13:44eanxgeekping #clojure anyone here by chance familar with selenium? trying to lein compile some code java.io.FileNotFoundException: Could not locate selenium__init.class and I'm trying to figure out where that would come from.
13:44Bronsa,((comp first filter) odd? [0 2 4 1 2])
13:44duck1123,(some even? [1 2 3 4])
13:44clojurebottrue
13:44clojurebot1
13:45zerokarmaleftBronsa's then
13:45mbaci only want the first one :)
13:46duck1123Bronsa was right
13:46mbacand only want to compute all but the first
13:46mbacthat seems wordy
13:46Bronsawait, what
13:46mbacer, wait
13:46mbacand only want to compute the first
13:46duck1123,(->> [1 2 3 4] (filter odd?) first)
13:46clojurebot1
13:47zerokarmaleftyou have to compute on the things that come before it necessarily
13:47mbacsure
13:47Bronsambac: then being filter lazy, it will compute until one is true
13:47zerokarmaleftit's lazy though, it stops after the first
13:47Bronsaand returd that
13:47Bronsa*return
13:48Bronsasimply (def ffilter (comp first filter))
13:48Bronsaand have fun
13:50Bronsawhy?
13:50clojurebotwhy not?
13:50devnbecause i think it will slow down newcomers
13:51mbacwhoa, magic ->> thing
13:51Bronsambac: -> too
13:51devnMaybe I'm overstating it, but im working on a tutorial for a meetup group I run and I think the extra step of requiring clojure.repl in all of your projects in order to get (doc) and (source) is annoying
13:52duck1123those 2 forms are great for turning big complicated fns into simple lists
13:52Bronsadevn: personally i use doc and source only from a repl
13:52Bronsawhich is the usecase for them in some code?
13:52devnBronsa: coincidentally, i only develop when I'm using...a repl
13:53mbacare lists always lazy?
13:53devnBronsa: I see where you're coming from, but I miss the old days of not needing to (use 'clojure.repl) every single time I start a repl
13:54Bronsadevn: oh
13:54devnit's just extra garbage that new people to the language should not need to do.
13:54Bronsai always start my repl with lein repl
13:54Bronsaand it uses clojure.repl by default
13:54Bronsai tought it was the repl, not lein
13:54devnBronsa: so...that's one way out of how many to start a repl?
13:54Bronsadidn't mean to say that
13:54Bronsai tought that when starting the repl clojure.repl was automatically :used
13:55Bronsadidnt notice it was lein
13:55devn*nod* -- this is a change as of 1.3 I believe
13:55fliebelAre there any other binary libs for clojure other than Gloss?
13:56mbacoh filter does the lazy
13:57chewbrancais there a form of flatten that allows you to specify depth or type? I've got a list of lists of vectors, and I want to flatten that to be a single list of vectors
13:57Bronsambac: most of the core seq fns returns lazy seqs
13:57chewbrancaand flatten will flatten the vectors down as well
13:58Bronsas/ns/n/
13:58lazybot<Bronsa> mbac: most of the core seq fn return lazy seqs
13:58ibdknoxthe ones that can will do so :)
13:59gfredericksis there an example of a function that returns a seq that is not lazy?
13:59chewbrancagogo internet: http://stackoverflow.com/questions/5232350/clojure-semi-flattening-a-nested-sequence
13:59ibdknox,(doc reverse)
14:00clojurebot"([coll]); Returns a seq of the items in coll in reverse order. Not lazy."
14:00ibdknox:)
14:00gfredericksibdknox: that was certainly easy. :)
14:03duck1123,(doc doall)
14:03clojurebot"([coll] [n coll]); When lazy sequences are produced via functions that have side effects, any effects other than those needed to produce the first element in the seq do not occur until the seq is consumed. doall can be used to force any effects. Walks through the successive nexts of the seq, retains the head and returns it, thus causing the entire seq to reside in memory at one time."
14:04gfredericksobvious exception
14:04sritchieibdknox, do you have any examples of how to use sandbar for authentication with noir?
14:05sritchiespecifically, I'm not sure how to to use server/add-middleware to do something like this: https://github.com/brentonashworth/sandbar/blob/master/src/examples/auth/auth.clj#L130
14:06ibdknoxsritchie: I haven't used it, because it didn't seem to provide anything I needed, to do that, though you just need to add those two middleware separately
14:07ibdknoxsritchie: you won't need wrap-file :)
14:07ibdknoxsritchie: you could also comp them
14:07sritchiegot it, so just add (server/add-middleware with-security authorize) in there
14:07ibdknoxyep
14:08sritchienice, that tossed a few hours, but I'll figure it out from the sandbar side
14:08sritchies/hours/errors
14:08lazybot<sritchie> nice, that tossed a few errors, but I'll figure it out from the sandbar side
14:08sritchieKey must be integer, etc :)
14:08ibdknoxI think you'll need to include his session middleware too, which I'm not sure how way that'll play with mine
14:09ibdknoxin theory they shouldn't mess with eachother
14:09ibdknoxbut I've not tried it
14:10sritchieyeah, you're right, that worked out fine
14:12sritchieso, all I'm looking to do is restrict access to certain pages based on roles -- in noir, I could do the same thing by examining noir's session, right?
14:12mbaccan i have fold?
14:12mbacreduce isn't cutting it for me
14:14dnolenfoldl foldr considered slightly harmful, http://docs.google.com/viewer?url=http://research.sun.com/projects/plrg/Publications/ICFPAugust2009Steele.pdf&amp;pli=1
14:14ibdknoxsritchie: yeah, it's probably a bit simpler. You would use a pre-route, then check if the person has access, if not, redirect to login or whatever :)
14:15ibdknoxsritchie: for example: https://github.com/ibdknox/Noir-blog/blob/master/src/noir_blog/views/admin.clj#L50
14:15mbacdnolen, i know. i want it anyway.
14:15dnolenmbac: can't help you there :)
14:16sritchieibdknox: got it, that's great
14:16dnolenand if rhickey #strangeloop talk is any indicator, it's not going to happen. mayhaps as a contrib thing, but I don't hear many people asking for it.
14:18mbacwell, what's better then? i want to update state as i consume a list
14:20dnolenmbac: so why not reduce + an atom?
14:20mbachmm?
14:27mbacthere's seriously no fold function because it's not inherently parallelizable? this is better than having thousands of people try write their own buggy versions?
14:27mbacs/try write/try to write/
14:27lazybot<mbac> there's seriously no fold function because it's not inherently parallelizable? this is better than having thousands of people try to write their own buggy versions?
14:28dnolenmbac: thousands? if you feel so strongly about it bring it up on the mailing list, dev list.
14:28mbacthousands of crappy implementations, at least
14:29mbaci know mine will be
14:29dnolenmbac: I have yet see any implementations of it at all.
14:29dnolenmuch less thousands.
14:31mbaci'm projecting into the future a little
14:32dnolenpeople have been using Clojure for a while now, future hasn't arrived.
14:32dnolenbut honestly, sounds like something that could find a home in contrib.
14:34dnolenand other people that want it can benefit from a good implementation. same thing w/ pattern matching - rhickey doesn't like that either.
14:34dsantiagodnolen, has he said why he doesn't like pattern matching?
14:34dnolengotta run
14:35mbachttp://pastebin.com/yAS3Fjhe there, i fixed clojure :)
14:36gfredericksmbac: don't you gotta have a 2-arg version?
14:37mbacsee? i told you it'd be crappy
14:37fliebeldsantiago: From what I remember he just didn't like the current implementations.
14:37dsantiagoAh.
14:37gfredericksmbac: yeah, no motivation to prove your own point there :P
14:42Leeniisn't fold like reduce?
14:42mbacno
14:42mbaci mean, yes
14:43mbacbut if you use a language which discourages mutation, fold is what all of the kids who miss for loops will want
14:43mbacexcept they don't know they want it, yet
14:44gfredericksfoldl === reduce?
14:44fliebelbehold the treeduce https://gist.github.com/951553
14:45mbacit's not. part of the power of fold is the accumulator isn't necessarily the same type as the elements in the collection
14:46gfredericksmbac: well clojure.core/reduce certainly doesn't enforce that. I use it assymetrically all the time.
14:46fliebelmbac: Does reduce require that?
14:48mbacint total=0; for(int i=0;i<a.length;i++) total+=a[i].length; best functional programmingifies to (foldl (fn [acc x] (length x)) 0 a)
14:49gfredericks(reduce + (map count a))?
14:49gfredericksI don't even see where the + happens in your version
14:49mbacyeah, i forgot
14:49gfredericksah I see where it would go
14:49mbac(foldl (fn [acc x] (+ acc (length x))) 0 a)
14:50gfredericksso you're arguing that because something fits the imperative paradigm better, we ought to have it?
14:52mbacno, i'm arguing the loops that you use to get stuff done are strange
14:52mbacfold explicitly considers the start case
14:53mbacyour reduce would have a bug if 0-arity + didn't rescue you
14:54Leenireduce can take start value
14:54mbaci agree, you can not write bugs
14:54mbac;)
14:54Leeniit also enables you to accumulate different type than that is the collection
14:55gfredericksmbac: so you consider fold to be a function that requires a start value?
14:55Raynesreduce lets you do anything you want.
14:55gfredericks,(reduce conj [] #{7 8 4})
14:55clojurebot[4 7 8]
14:56gfredericks^ different accumulated type
14:57mbacgfredericks, sort of
14:58LeeniI never know when to use reduce and when to use something like apply vec
14:58mbacfold has a well known form. with reduce i have to look closer
14:58gfredericks,(doc vec)
14:58clojurebot"([coll]); Creates a new vector containing the contents of coll."
14:58gfredericksLeeni: apply vec sounds pretty useless; and apply vector is equivalent to vec
14:59Leeniyeah that
14:59LeeniI mean I can often do a lot of stuff just with map and reduce
14:59gfredericksLeeni: reduce is a lot more general
14:59Leenibut maybe using specialised function is better
14:59mbacyes, that's it! reduce is too general. it's terrible
14:59gfredericksif all you're doing is trying to make a vector out of something, then you should prefer vec/vector
14:59Leeniperhaps faster
14:59gfredericksmbac: I don't mean it's any more general than fold
15:00mbac:)
15:00gfredericksin fact part of what makes this discussion hazy is that there's not a clear line between the two
15:00mbacthere's a very clear line. fold has an explicit required start case
15:01mbacif you use it wrong the system stops you from having a bug
15:01gfredericksmbac: if we like the system to tell us when we have bugs we may as well use static types
15:01mbachahah
15:01mbaci guess i should stick to ocaml
15:02gfredericksclojure's got flexibility all over the place
15:02mbaci know, it's horrible
15:02gfredericksthen don't use clojure. apparently you don't like it.
15:02mbaci don't know how to do anything
15:03Leenihey, anyone got clojurebox or counterclockwise to run with clojure 1.3?
15:03gfredericksbtw, wikipedia doesn't agree with your strict definitions: http://en.wikipedia.org/wiki/Fold_(higher-order_function)
15:03gfredericksmbac: I think most of the people that use clojure appreciate the flexibility
15:04gfredericksI think that can be a personality thing though. Some people like it, some people don't.
15:04mbaci've noticed that
15:04toxmeisterleeni: CCW 0.4 works fine w/ 1.3
15:04gfredericksI have a friend who would be great with clojure except for that one point, so he uses scala
15:04mbacit's not inherently bad, it's simply thwarting my expectations
15:06gfredericksmbac: what other languages do you use/like?
15:09Leenitoxmeister: my CCW feezes my eclipse when I try to connect to 1.3 REPL
15:21mbacgfredericks, besides ocaml? i guess C
15:21mbacpython, when i'm doing project euler problems
15:23gfredericksdo you find clojure more flexible/surprising than python?
15:23mbacno, they're a lot alike
15:23mbacphilosophically, it seems
15:24mbacusing python in a large codebase with multiple people drives me nuts though
15:25gfredericksI think immutable data and preferring pure functions can help keep down the chaos
15:25mbacagreed
15:27gfredericksmbac: I sympathize with you some. the dynamic types and stuff are definitely the part of clojure I'm least sure about
15:27gfredericksmy personal approach is to use testing
15:28gfredericksmy hunch is that could be better than a static language, because you're forced to write lots of tests, which give you confidence not only that you got all the types right, but that the program also does what you want it to
15:28Leeniwhat's the difference between deftype and defrecord?
15:30gfredericksdefrecord gets you a map-compatible data structure. deftype is bare, and can even give you mutable fields if you need them
15:33mabesmbac: another version of foldl for you: https://github.com/amalloy/amalloy-utils/blob/master/src/amalloy/utils.clj#L72-74
15:33mabesin this case he aliased reduce to be foldl.. which wouldn't get the strict enforcement that you want
15:34gfrederickspretty easy to get it though: (def foldl #(reduce %1 %2 %3))
15:34mabesyeah
15:35gfredericksI wonder if reverse on vectors is fast
15:35mabes,(doc reverse)
15:36clojurebot"([coll]); Returns a seq of the items in coll in reverse order. Not lazy."
15:36mbacgfredericks, disciplined coding, almost universally, doesn't work
15:36gfredericksmbac: did I say otherwise?
15:36mbaci don't think so
15:36gfredericksmbac: what does work?
15:36mbaci'm paving the way for why i'd never write unit tests
15:36gfredericksoh I see
15:37mbacthe language should make it impossible to push a bad solution
15:37gfredericksoh golly.
15:37mabesmbac: do you use ocaml professionally?
15:37mbacyeah
15:38gfredericksmbac: if the language doesn't let you write incorrect code, I don't think it could be a programming language
15:38mbacno doubt
15:38gfredericksso I guess your statement hinges on what you mean by "bad solution"
15:38mbacthere's an interesting proof in there somewhere :)
15:38gfrederickseasy:
15:38gfredericksRequirements: push a bad solution
15:39mabesafter reading "Ocam for the Masses" and a few tutorials I must say that I am intrigued.. I've never used a language with a decent type system but the benefits sound nice
15:39mbacideally your developers write unit tests and check their mallocs and do proper mutex locking blah blah
15:39mabess/Ocam/Ocaml/
15:39lazybot<mabes> after reading "Ocaml for the Masses" and a few tutorials I must say that I am intrigued.. I've never used a language with a decent type system but the benefits sound nice
15:40mabes(here is the link to the mentioned article: http://queue.acm.org/detail.cfm?id=2038036)
15:40mbacbut if they're human beings they're going to forego all that shit if it means they get it out the door faster
15:40mabesmbac: what industry do you work in?
15:41mbacmabes, my boss wrote that article
15:41mabesmbac: awesome! I've been watching some of his presentations too :)
15:42mabesaside from HFT OCaml hasn't really seen much in roads in industry it would seem
15:45mabesmbac: what is your opinion on clojure's approach to concurrency and state?
15:46mbacwhat's clojure's approach?
15:46mabes:)
15:46mabeshttp://clojure.org/state
15:47gfrederickspiles and piles of mutexes
15:47mabeshttp://www.infoq.com/presentations/Are-We-There-Yet-Rich-Hickey
15:48mabesgfredericks: under the hood I suppose so, but the overall premise is to remove that complexity from the programmer, right?
15:48gfredericksmabes: yeah, I was kidding. it wasn't very funny.
15:48mabesgfredericks: lol.. okay
15:48gfrederickssometimes I forget whether jokes are supposed to be funny or not.
15:49Leenibtw about reduce
15:49Leeniit does have one weird behaviour
15:49mabesgfredericks: sarcasm can also be lost over IRC as well ;)
15:49Leeniif you hand it an empty sequence it will invoke the function with no arguments
15:49gfredericksmabes: I can get it lost face-to-face if I try hard enough.
15:50mbaceverything on irc is sarcastic, unless explicitly noted otherwise
15:50Leeniif you hand it a 2 or more elements it will do a reduce
15:50gfredericksLeeni: not much else for it to do, right?
15:50Leeniand if you hand it sequence of one element it will just return the element
15:50Leenithat's the weird one
15:50gfredericks:/
15:51Leeniin all other cases function gets called at least once
15:51mbac(defalias foldl reduce)
15:51mbaclulz
15:51Leeniexcept when sequence has 1 element
15:51Leenithen the function doesn't get called
15:52gfredericksLeeni: I think it makes sense, unless you phrase it specifically so as to make it sound like it doesn't make sense :P would you do it differently?
15:52Leeniperhaps invoke the function with one argument?
15:52gfredericksI think that's even weirder
15:53gfredericksreally the exceptional case is the 0-arg case
15:54gfredericksI think if you're going to call fold/reduce, you've got three options: 1), never call it on an empty list, 2) give an initial value that will be returned if you use an empty list, 3) barring the first two, give a reduce function that will accept 0 args
15:54gfrederickscase 3 is what you get for rejecting 1 and 2
15:54gfredericksI think the only other sane thing is to throw an error in case 3
15:54mabesmbac: have any book recommendations (or other resources) for learning ocaml? From what I've googled, "Introduction to Objective Caml" seems to be well liked: http://caml.inria.fr/cgi-bin/hump.en.cgi?contrib=347
15:56mbacthat's the best ocaml book available
15:56mbacwhich is to say it sucks the least
15:57mabesof course
16:03mbachave any book recommendations for learning clojure? :)
16:06zerokarmaleftmbac: i enjoyed JoC
16:06mabesmbac: given your background I think you would like Joy Of Clojure
16:08mbacsounds like the winner
16:09mabeswhich is to say you will hate the book the least
16:09mbachaha
16:13ghiuhi, i'm using intellij idea and leiningen. how can i access the jars imported in the /lib dir of the project from the build-in repl of my die? it seems to have a class path that is different from the one used by lein and the project. thanks
16:16ghiuoh, found it
16:16ghiui had to add the lib path to the "dependancies" modules in the project settings
16:21gfredericksis it possible to override the clojure reader?
16:26duck1123gfredericks: if you're asking like reader macros, no
16:34gfredericksduck1123: I was thinking like (binding [clojure.core/read my-silly-reader-fn] (require ...))
16:34gfredericksit's a stupid idea anyhow. Was just curious if that would work.
16:35mbacdoes this form (let [foo 1 foo (+ foo 1)] foo) particularly infuriate anyone?
16:36gfredericksmbac: it's a great way to imitate imperative programming! :)
16:37Bronsas/imperative/procedural/ right?
16:37mbaci don't want to risk re-using the old value by mistake
16:37mbacso... shadow it!
16:37gfredericksI think it certainly has the danger to screw up readability. Sometimes I can't resist using it for getting an argument into a canonical form though. I think clojure.core does that as well.
16:37gfredericksBronsa: dunno, what's the difference?
16:37mbacof course then you risk much more subtle scoping bugs
16:38gfredericksmbac: I wouldn't go out of your way to hide things like that. If you want isolation, create a separate function to call.
16:39Bronsagfredericks: as per wikipedia procedural can be used as a synonym for imperative
16:39Bronsaso i think i am wrong
16:39gfredericksBronsa: nah, you _were_ wrong. Now you're right!
16:39gfredericksprobably.
16:39Bronsagfredericks: lol right
17:04michaelr525hello!
17:06gfredericksmichaelr525: hello!
17:20bdb_I'm having some trouble getting swank-clojure to work with lein: I've installed the plugin & ~/.lein/bin/ is on my path, but `lein swank` still says "That's not a task."
17:21bdb_where should I look next to debug this?
17:21bdb_$ which swank-clojure
17:21bdb_$ lein swank
17:21bdb_That's not a task. Use "lein help" to list all tasks.
17:22bdb_hmm, that didn't render right in my irc client: `which` returns: /Users/brandon/.lein/bin/swank-clojure
17:27duck1123bdb_: is your lein up to date?
17:28bdb_yup: leiLeiningen 1.6.1.1 on Java 1.6.0_26 Java HotSpot(TM) 64-Bit Server VM
17:29ibdknoxbdb_: ls ~/.lein/plugins
17:29ibdknoxis swank actually in there?
17:29bsod1wow, I got NullPointerException in Clojure!
17:29bdb_yup
17:29gfredericksbsod1: ##(nil :foo)
17:29lazybotjava.lang.IllegalArgumentException: Can't call nil
17:29gfredericksdangit
17:29gfredericksI know there's an easy way to do it...
17:29bdb_aaaahh two versions were in there
17:30bdb_i ran uninstall on the older version
17:30ibdknox:)
17:30duck1123##(.getFoo nil)
17:30bdb_and `lein help` shows swank now!
17:30lazybotjava.lang.NullPointerException
17:30gfredericks(map nil [1])
17:30gfredericks,(map nil [1])
17:30clojurebot#<ExecutionException java.util.concurrent.ExecutionException: java.lang.NullPointerException>
17:30bsod1heh
17:31gfredericksbsod1: would you prefer clojure defined a NilPointerException? :)
17:31bdb_thanks idbknox
17:31ibdknoxbdb_: leave it to a VIM user to save the day ;)
17:31bdb_heh -- I'm a vim guy myself
17:32ibdknoxhaha
17:32bsod1,(* 1 nil)
17:32clojurebot#<NullPointerException java.lang.NullPointerException>
17:32bdb_been writing clojure in vim for a couple weeks and been using a little macro plus tmux to send forms to the repl
17:32bdb_and decided it was finally time to bite the bullet and learn some emacs
17:32ibdknoxvimclojure would make that much nicer for you
17:33bdb_yeah, was using that in offline mode
17:35Bronsa,()
17:35clojurebot()
17:35Bronsa,(nil)
17:35clojurebot#<CompilerException java.lang.IllegalArgumentException: Can't call nil, compiling:(NO_SOURCE_PATH:0)>
17:36gtrak``,(println "Clojure is awesome")
17:36clojurebotClojure is awesome
17:37gfredericks,(println "&(println \"clojurebot is awesome\")")
17:37clojurebot&(println "clojurebot is awesome")
17:37lazybot⇒ clojurebot is awesome nil
17:37Bronsalol
17:37bdb_so tempting to write an infinite bot loop :-P
17:38gfredericksbdb_: lazybot's arrow prevents it
17:38ibdknoxguarded against
17:38raekbdb_: this is why lazybot's output is prefixed with ⇒
17:38bdb_ah, nice
17:38gfrederickssomebody else say it too!
17:38gtrak``nerds :-)
17:38Bronsait's not nice
17:38Bronsait ruins fun
17:54sritchieyou'd just need one more bot that responds to the arrow, I think
18:14Leeniman I can't get swank to work with clojure 1.3
18:14Leeniit just crashes
18:18Raynestechnomancy: Ping.
18:20lnostdal_works fine here
18:23Leenichanged clojure jar version to 1.3 in lein.bat and now leinigen crashes
18:24duck1123Leeni: update lein, remove all older versions of swank and install an up to date version
18:24raekLeeni: change the version in your project.clj file, not in leiningen's internals
18:24Leeniraek I did that and it crashed on lein swank
18:25raekleiningen uses two processes: one for build tool stuff and one for your code
18:25raekwhich version of swank-clojure?
18:25Leeniyes but it ran swank with same version as build tool stuff
18:25Leeni1.3.3
18:25raekdo you have one as a dev-dependency? do you have one installed as a plugin?
18:25Leeniyes
18:25Leeniboth
18:25raekmake sure you don't have both
18:26raekif they are different versions, strange things happens
18:26Leenithey are both the same version
18:26raekprefer using it as a plugin
18:27LeeniI downloaded newest version of everything, put clojure 1.3 and swank 1.3.3 in project.clj, ran lein install plugin for swank 1.3.3
18:27Leenithen lein swank in project folder crashed
18:28raekstacktrace?
18:28LeeniCaused by: java.lang.RuntimeException: Unable to resolve symbol: print-doc in th is context
18:29Leenithen I changed .lein/bin/swank-clojure.bat so it pointed to 1.3 clojure instead 1.2 and nothing changed
18:29Leeninow I changed version used in lein.bat to 1.3 and I get a different error
18:30LeeniException in thread "main" java.lang.IllegalStateException: Can't dynamically bi nd non-dynamic var: leiningen.compile/*silently*
18:30duck1123I don't know what version other people are using, but I've been using 1.4.0-SNAPSHOT with no problems
18:30Leeniso apparently lein swank runs swank with whatever version of clojure it uses for itself
18:30Leeniwhich was 1.2, now I changed that to 1.3 and now lein doesn't work
18:30raekLeeni: leiningen uses clojure 1.2 for its own process, but that shouldn't interfere with you using clojure 1.3 in your project
18:31raekas I said, lein uses two processes
18:31Leeniwell apparently there's no way to tell it to run swank with 1.3
18:31raekswank runs in your project process
18:31duck1123and swank should use the project's version
18:31raekwhich uses the clojure version you choose
18:32LeeniI must be crazy then
18:32Leenichanged lein version back to 1.2
18:33raekLeeni: if you run "lein repl", you should get a 1.3 repl
18:33Leeniand I get this error when running lein swank
18:33Leenihttp://pastebin.com/YTQ8GxsX
18:33raekLeeni: when you get swank to work, it will run in that classpath
18:34Leeniwell that's the problem, it clearly doesn't
18:34raekLeeni: maybe clojure 1.3 isn't supported in the stable version of swank-clojure yes. have you tried 1.4.0-SNAPSHOT?
18:34raek*yet
18:35raekafter all, clojure 1.3 was released fairly recently
18:36duck1123raek: I'm pretty sure it worked in swank 1.3.0. The important thing is that he has only 1 version of swank
18:37duck1123Leeni: delete all your swank plugins, remove it as a dev dependency, delete lib/ and classes, then install 1.4.0-SNAPSHOT as a plugin
18:37bdb_Is there a naming convention for functions which return a mutated object? "set-foo" just doesn't seem right, since it's not actually changing it's argument… but I guess that would be "set-foo!" right? -- what's the convention?
18:37Leeniduck then how will I run swank with my project in classpath?
18:38duck1123lein swank, just as normal
18:38raekbdb_: the ! sign is for functions whose side-effects are not safe in transactions
18:38bdb_fair enough, so here's an example:
18:38raekfor example, if you 'swap!' an atom in a transaction, and that transaction is retried, the 'swap!' still happened and is not "rolled back"
18:39bdb_yup, gotcha
18:39bdb_let's say I have some immutable hash representing a person
18:39raekLeeni: do you have additional dependencies? sometime a dependency pulls in an old version of swank-clojure...
18:40bdb_with :first-name and :last-name keys
18:40bdb_and i want to provide set-name which splits on " " and returns a new person object w/ the first and last names set (yes, i know this is not a real example… you wouldn't every assume people have exactly one space and two names)
18:40bdb_what do you call that function?
18:40bdb_set-name ?
18:40bdb_with-name ?
18:40Leeniraek:seems to be the case
18:41bdb_name= ?
18:41raekI like with-name
18:42bdb_so i like that too and with-meta from the std lib seems to say that's a good idea… but i also see the with- prefix for functions which affect lexical bindings, like with-out-str, etc
18:42raekI think that's how Joda-time names their methods
18:42raekyeah, I see the conflict...
18:43raekwell, I don't know. names are always hard...
18:43Leenihm how do I figure out last release on github
18:43raekLeeni: is the dependency incanter?
18:43bdb_yeah, hence I'm asking for help :-) names are the hardest thing haha
18:44amalloybdb_: fwiw, with- is mostly for things that affect dynamic scope, not lexical scope. with-out-str is an example of that
18:44bdb_d'oh yeah, dynamic scope is what i meant
18:44raekLeeni: now you have experience the reason why you should use swank-clojure as a plugin and not as a dev-dep... :-)
18:44Leenitrying to figure out last Enlive version
18:45Leeniwell yeah but how do I run it as plugin and will it still let me use my project's classpath
18:45duck1123Leeni: Network view is always good to see which braches belong where
18:45LeeniI think other dev deps will always pull their versions
18:45Leeniso how to avoid that
18:45duck1123exclusions
18:46duck1123you can specify that a dependency should exclude other dependencies
18:46raekLeeni: if you have it as a plugin, it behaves like an invisible :dev-depenencies entry in your project.clj
18:47raekwell, in all your project.clj files
18:47duck1123You can also exclude globally. I recommend that people using 1.3 put a global exclusion on the older contrib libraries
18:47raekduck1123: oh, where do you set that global setting?
18:48duck1123:exclusions key (ex. https://github.com/duck1123/jiksnu/blob/master/project.clj#L44)
18:49FrankLwhat's the easiest way to call new clojure code from an existing java project in eclipse?
18:49FrankLi have ccw installed
18:50Leenithanks
18:50LeeniI got it to run
18:50Leenisuccessfuly connected from clojurebosx
18:50duck1123FrankL: If you use :gen-class in the clojure project, you can create a real Class that you can treat just like a Java class
18:51FrankLduck: yup, that's exactly what i want to do
18:51LeeniI'll have to look into exclusions if I wanna get my old projects to run
18:52FrankLbut the old project doesn't 'see' the class specified in clojure
18:52FrankLalthough i added the new project as a requirement
18:53duck1123I wonder if that has something to do with eclipse. So these are two separate projects?
18:54raekFrankL: https://gist.github.com/1273014
18:54duck1123Clojure has to be told to compile those namespaces into classes, I wonder if something about that isn't getting done when eclipse traces the dependencies
18:55raekFrankL: a pretty simple way is to skip gen-class and use clojure.lang.RT to access the clojure stuff
18:55raekmight not be the fastest way if you make a lot of java->clojure calls
18:55raekhrm, well, it shouldn't be that slow, actually
18:56raekFrankL: for this to work you need the clojure source and the clojure jars on the classpath
18:56FrankLthanks duck & raek, i'm looking at both options
18:57raekI think the simplest way is to make a new lein project, run lein deps and then add src/ and the jars in lib/* to your eclipse project classpath
18:58Leenistill can't get CCW to connect to repl though
18:58Leenieclipse just freezes
18:58raekif CCW has some lein integration, disregard my instructions for that part and follow the official docs :)
19:00Leeniwhen I click Connect to REPL in eclipse should I be connecting to the port "lein repl" gives or the swank server?
19:03duck1123 ccw uses repl, not swank
19:05winkafaik it does not work with "lein repl", it's another repl
19:06duck1123it works with nrepl
19:13FrankLyay, got it to work
19:13FrankLhad to compile the .clj file from the repl myself
19:13FrankLand then i could just use the class methods from a different project
19:13FrankLthanks again duck & raek
19:14duck1123congrats. Gen-class is good when you don't even want to think about the fact that it's clojure from the java side
19:15duck1123like when you're implementing some plugin interface
19:15FrankLexactly
19:36bdb_I'm sure this function is in core, but I can't find it: How do I get some value from a hash, apply a function to it, and return a new hash with that key/value pair replaced?
19:36amalloy&(doc update-in)
19:36lazybot⇒ "([m [k & ks] f & args]); 'Updates' a value in a nested associative structure, where ks is a sequence of keys and f is a function that will take the old value and any supplied args and return the new value, and returns a new nested structure. If any levels do not exist, hash-maps will be created."
19:36bdb_awesome. thanks!
19:37amalloybdb_: it probably wouldn't help in this case, but often if there's something you think is in core but don't know what to call it, lazybot can help
19:37amalloy$findfn {:a 1} :b 2 {:a 1 :b 2}
19:37lazybot[clojure.core/assoc]
19:37bdb_cmd+f in my browser only goes so far :-)
20:05duck1123there's also clojureatlas.com for when you have an idea what you want, but not what it's called
20:16bdb_duck: ok that's pretty damn cool :-)
20:17amalloyaw, no "pretty damn cool" for lazybot?
20:17gfredericksduck1123: let's be honest: are those fibonacci numbers?
20:18gfredericks(inc lazybot)
20:18lazybot⟹ -1
20:18bdb_heh, they are both pretty damn cool
20:18gfredericks(inc clojureatlas.com)
20:18lazybot⟹ 1
20:18duck1123gfredericks: yes they are
20:18amalloyhahahaha poor lazybot. gets dec'd when he makes a mistake, and so rarely inc'd
20:18amalloybut you don't mind, do you??
20:18lazybotamalloy: Uh, no. Why would you even ask?
20:19gfredericksamalloy: it's just too much fun to resist using lazybot to dec lazybot.
20:19bdb_(inc lazybot) ; just for you amalloy
20:19bdb_aw, no comment support :-P
20:19bdb_(inc lazybot)
20:19lazybot⟹ 0
20:19amalloyyeah, inc is dumb
20:19gfredericks(dec lazybot)
20:19lazybot⟹ -1
20:19bdb_haha
20:19gfredericks^ cause of no comment support
20:19gfrederickswanted to put that as a comment, but no...
20:19amalloynice. fair point
20:20gfredericks(* 3 lazybot)
20:20amalloyi guess it wouldn't be hard to add that, actually, but it hardly seems worth the bother
20:21gfredericksamalloy: I'm on it
20:25gfrederickswtf. I spent 2 minutes agonizing over that regex and github just discarded the change.
20:26gfredericks(dec github.com)
20:26lazybot⟹ -1
20:27gfredericksI think github got confused since I had forked sexpbot way back in the day and it's since been renamed and reowned.
20:31amalloyinteresting
20:31amalloywe do try to maximize your inconvenience
20:32gfredericksnow you know how badly I wanted to create that pull request.
20:33amalloyand instead you created it badly?
20:34gfredericksamalloy: the grammar?
20:34gfredericksor the code?
20:34amalloyno, just that you tried to send it and github failed you
20:35gfredericksoh I think this has been a wordplay.
20:36amalloy(inc gfredericks) ; thanks for pull request
20:36lazybot⟹ 2
20:36gfredericksnow my evening is complete
20:37bdb_Sweet! I'm going to give myself credit for supporting the clojure community w/ my awesome inadvertent feature request
20:38duck1123(inc bdb_) ; you've inadvertently helped us all
20:38lazybot⟹ 1
20:38gfredericksamalloy: I thought about converting it to use (read-string) instead of just the regexing
20:39gfredericksin other words I overthought it.
20:39amalloygfredericks: meh. the goal was for it to be fast, since it's checked every time he sees a message from anyone in any channel
20:40gfredericksah ha
20:40gfrederickswouldn't want to stress him out
20:40amalloynot that we're short on CPU time on the server, but just as a matter of good practice
20:40bdb_Oh hey, I've indirectly helped too: I'm brandonbloom -- thanks for pulling my fixes to the links in the lazybot read me
20:40gfredericksof course
20:40bdb_i mean directly*
20:41bdb_*sigh* i suck at typing/speaking/etc :-P
20:44gfredericksman now every time I say anything I'm going to imagine poor lazybot churning it through that regex...
20:45amalloygfredericks: #"^\(" is going to mean he short-circuits pretty fast :P
20:46gfredericksthe world is merciful after all
20:46gfredericks(sometimes)
21:17duck1123Does anyone know which namespace has a *debug* var? this dynamic warning is driving me nuts
21:19duck1123I really wish the dynamic warnings had shown the fully-qualified vars
21:22amalloyyuck. no qualified name, no filename, no compiler stacktrace? that's tough to fix
21:23gfredericksunzip lib/* and grep?
21:23duck1123just found it. Yay! one less warning
21:24amalloygfredericks: well, it could be compiled. you might have to search for _STAR_debug_STAR_
21:25amalloyduck1123: who was the offender?
21:26duck1123It was in lamina. I've been maintaining a branch with all the changes to work in 1.3, but I guess I missed one
21:26duck1123I'm updating all of the dependencies, trying to get rid of the last warnings
21:28duck1123does anyone know how long it will be before a build of algo.generic is up on the sonatype repo?
21:32icefoxShould Clojure documentation end in a period?
21:38icefoxPoking around in jira I didn't see anything, does Clojure have something like the Linux Janitor tasks?
22:28zakwilsonCongomongo converts string keys to keywords. I do not want this behavior in some cases. Can I turn it off?
22:37zakwilsonNever mind. Found it - coerce/*keywordize*
22:43amalloyzakwilson: oh really? i wish i had known that
22:43zakwilsonamalloy: well, documentation is a bit lacking, so I had to RTFS. Didn't take too long to find though.
22:44zakwilsonIt's kind of important too since I'm storing a bunch of maps with string keys and doing compute-intensive things with them. Keyword comparisons are much slower.
22:49amalloy&(let [x (keyword "test") y (keyword "test")] (time (dotimes [_ 1e7] (= x y))))
22:49lazybot⇒ "Elapsed time: 63.097127 msecs" nil
22:49amalloy&(let [x (str "te" "st") y (str "te" "st")] (time (dotimes [_ 1e7] (= x y))))
22:49lazybot⇒ "Elapsed time: 1080.501377 msecs" nil
22:49amalloyzakwilson: fast comparisons is practically the reason keywords exist
22:51zakwilsonamalloy: I don't think I still have my benchmark code around, but keyword lookups in maps were a lot slower under certain circumstances when I tested it last.
22:51amalloy&(let [x "test" y "test"] (time (dotimes [_ 1e7] (= x y))))
22:51lazybot⇒ "Elapsed time: 71.512589 msecs" nil
22:52amalloyin this case strings are about the same because they're interned class-constants
22:53amalloybut in general comparing keywords is extremely fast, and comparing strings *might* be extremely fast. if you were seeing bad performance it seems likely you were creating keywords on the fly or something
22:54amalloy(which congomongo does, of course, when it converts strings to keywords)
22:56zakwilson&(time (let [x :foo y (hash-map :foo 4 :bar 8 :qux 2)] (dotimes [_ 1e7] (y x))))
22:56lazybot⇒ "Elapsed time: 943.981712 msecs" nil
22:56zakwilson&(time (let [x :foo y (hash-map :foo 4 :bar 8 :qux 2)] (dotimes [_ 1e7] (y x))))
22:56lazybot⇒ "Elapsed time: 812.843381 msecs" nil
22:56zakwilson&(time (let [x "foo" y (hash-map "foo" 4 "bar" 8 "qux" 2)] (dotimes [_ 1e7] (y x))))
22:56lazybot⇒ "Elapsed time: 442.546335 msecs" nil
22:57zakwilsonThat code does not, as far as I understand it create keywords on the fly.
22:58ibdknoxhm
22:59ibdknoxit's nearly 2x on locally for me too
22:59ibdknox-on
22:59zakwilsonAnd it's more on big maps - IIRC something like 5x or 7x.
23:00ibdknoxhm
23:01amalloyinteresting. i guess i've got some source-reading to do
23:01ibdknoxthere seems to be a huge difference between using (hashmap...) and just using the literal
23:01amalloyibdknox: the literal is an array-map
23:01ibdknoxah
23:02ibdknoxfwiw
23:02ibdknoxin that scenario it's about a 3x diff
23:02ibdknoxbut the overall number is much lower
23:02ibdknox,(time (let [x "foo" y {"foo" 4}] (dotimes [_ 1e7] (y x))))
23:02clojurebot"Elapsed time: 603.974 msecs"
23:02ibdknox,(time (let [x "foo" y {"foo" 4}] (dotimes [_ 1e7] (y x))))
23:02clojurebot"Elapsed time: 1031.745 msecs"
23:03ibdknox&(time (let [x "foo" y {"foo" 4}] (dotimes [_ 1e7] (y x))))
23:03lazybot⇒ "Elapsed time: 234.443206 msecs" nil
23:03ibdknoxthere we go
23:04zakwilsonStrings are faster than numbers too.
23:04zakwilson&(time (let [x 1 y (hash-map 2 4 1 8 8 2)] (dotimes [_ 1e7] (y x))))
23:04lazybot⇒ "Elapsed time: 790.373633 msecs" nil
23:04ibdknoxnow that doesn't make sense to me at all
23:04zakwilsonNor to me.
23:04amalloyzakwilson: sure, that makes sense
23:04ibdknoxlol
23:04ibdknoxamalloy: how so?
23:05amalloybecause you're comparing interned string literals; they just do a pointer-equality check first, which succeeds
23:05hugodI wonder how long it takes jit to realise that the result of (y x) is not used and turn it into a nop
23:05amalloynumbers have to be checked for type, unboxed, and then compared
23:06ibdknoxmm
23:06zakwilson&(time (let [x (int 1) y (hash-map (int 2) (int 4) (int 1) (int 8) (int 8) (int 2))] (dotimes [_ 1e7] (y x))))
23:06lazybot⇒ "Elapsed time: 1155.865792 msecs" nil
23:06zakwilsonExplain that one?
23:07amalloyyou gave the compiler more boxing to do
23:07amalloyyou explicitly made x a primitive int, and then to look it up in y you have to box it every time
23:08amalloy&(time (let [x 1 y (hash-map (int 2) (int 4) (int 1) (int 8) (int 8) (int 2))] (dotimes [_ 1e7] (y x))))
23:08lazybot⇒ "Elapsed time: 876.695437 msecs" nil
23:08zakwilsonCan Clojure maps use a primative as a key?
23:08amalloythe other int calls are immaterial
23:08amalloyno
23:08ibdknoxah, that was the important bit I was missing
23:09amalloyibdknox: they're Map<Object, Object> and int isn't an Object
23:09zakwilsonRight.
23:09ibdknoxindeed not
23:09ibdknoxwouldn't string always be the fastest possible solution then?
23:10amalloyibdknox: only if all the strings are known at compile time, or interned later
23:10amalloywhich is exactly what keywords do, so i'm sorta puzzled as to why they're not fastest
23:10zakwilsonWhat would cause them to be interned later?
23:12amalloy&(let [x (str "a" "b") y (str "a" "b")] [(identical? x y) (apply identical? (map #(.intern %) [x y]))])
23:12lazybotjava.lang.SecurityException: You tripped the alarm! intern is bad!
23:12amalloywell, i guess that makes sense. but in a repl it works
23:12amalloythat is, returns [true false]
23:12amalloy[false true]. i'm a terrible repl
23:14zakwilsonSo you'd have to call intern? (read-string (slurp result-of-spitting-a-map-of-strings)) wouldn't do it?
23:16amalloyno
23:16amalloythat is, you would; it wouldn't
23:16zakwilsonStrings are still faster than keywords in that scenario.
23:18khaliGhm, trying to get started with clojurescript is dizzying
23:19ArafangionHmm, clojure depends on libasm-java?
23:19ArafangionWhat's the libasm for?
23:19amalloyfor er. assembling classfiles. the clojure compiler
23:20ArafangionAh, not asm in the normal sense, then.
23:20ArafangionHmm, looks like I just installed clojure 1.1, that's a tad out of date.
23:20amalloyi don't understand what "the normal sense" is, if it's not assembling stuff
23:20Arafangionamalloy: Converting assembly to machine code? :)
23:21sritchiehas anyone in here generated forms using Enlive?
23:21ArafangionHmm, yep, 1.1 is very out of date.
23:22amalloyArafangion: do yourself a favor, don't install any versions of clojure. just install lein and let it get you what you need
23:23ArafangionHmm, where would lein install it to? /opt/clojure?
23:23ArafangionI just installed 1.1
23:23dnolendamn Overtone #1 on Hacker News, whodathunk
23:24ibdknoxdnolen: Noir was #1 last week, Overtone #1 this week.... :D
23:24ArafangionClojure 1.1 seems to work very nicely.
23:24ArafangionIt manages to print "Hello", at least. :)
23:24dnolenibdknox: both deserved!
23:24ibdknoxArafangion: that is beyond out of date, don't use it
23:24Arafangionibdknox: Yeah, I found out after I installed it.
23:25ArafangionAre there newer debian packages, or should I backport it?
23:25ibdknoxdnolen: Clojure's getting more and more attention :)
23:25amalloyArafangion: do not install any versions at all, i'm telling you. clojure doesn't need to be installed
23:26amalloy$google clojure leiningen
23:26lazybot[Building Clojure Projects with Leiningen « I am Zef] http://zef.me/2470/building-clojure-projects-with-leiningen
23:26Arafangionamalloy: You underestimate how easy it is to install with the package manager.
23:26zakwilsonI have found cake preferable to leiningen, but they both do about the same thing.
23:27zakwilsonArafangion: the point isn't how easy it is to install. The point is that you're better off using the build tools than installing it.
23:27amalloyArafangion: you underestimate how irrelevant that is
23:27ibdknoxlol
23:27Arafangionamalloy: Yeah, I've just started to realise that clojure is typically used only as part of a regular java build script.
23:27amalloysudo apt-get install leiningen
23:27amalloyBAM. done
23:27Arafangionamalloy: Even better!
23:28ArafangionAh, it's not in stable.
23:28ArafangionWell, I'll check out the script. Not interested in using 1.1.
23:28ArafangionOne thing I noticed when using 1.1, just now...
23:28amalloyyeah, i'm not sure what versions of debian it's actually released for. my understanding is that phil did get it released for some version somewhere, at least
23:29ArafangionDefining a new function seems to require special syntax, why is the form (defn foo[bar] ...) used, why not: (defn (foo bar) ...)
23:29Arafangion?
23:29amalloybut downloading a shell script and asking it to install the package itself is not that hard
23:29Arafangionamalloy: Yeah, I'll be doing that.
23:29RaynesThat isn't a special syntax. That's consistent throughout Clojure.
23:29amalloyArafangion: uh, special syntax?
23:29RaynesIt's special compared to scheme, maybe.
23:29ArafangionRaynes: Yeah, compared to "other lisps".
23:29ibdknoxuh oh
23:30zakwilsonArafangion: the convention in Clojure is that parens are used for things that are evaluated and brackets are used for data.
23:30Arafangionzakwilson: Not a bad convention... But why the m-expr form?
23:30zakwilsonSo (defn foo [bar] ...), (let [foo bar] ...)
23:30zakwilsonArafangion: it's not m-expr form. It's the same form as Common Lisp (defun foo (bar) ...)
23:30mabesArafangion: the motivation is that Rich believes that overloading parens for function calls, and parameter lists adds complexity and thinks that complexity is one of the main reasons most people complain about parens in other lisps
23:31Arafangionzakwilson: s-expr form would be (defun (foo bar) ...), right?
23:31greghdon't think of clojure square brackets as m-exprs, since they aren't
23:31Arafangionmabes: Not sure I agree with that... But, making use of square brackets is a nice idea.
23:32Arafangiongregh: I mean, why do we do foo[bar], rather than [foo bar]?
23:32zakwilsonArafangion: both forms are sexps. There's no particular advantage to one form over the other. One is CL-style and the other is Scheme-style.
23:32greghArafangion: that's just what defn expects
23:32ArafangionIs there an implied space between '
23:33ibdknoxit's a visual distinction
23:33ArafangionIs there an implied space between 'foo' and '[bar]'?
23:33greghnot sure what that means, since a space there is optional and doesn't affect the meaning
23:33ibdknoxhm lol
23:33amalloyArafangion: no "implied" space is needed - put tokens wherever you want. but usually there is an "actual" space, stylistically, because that's how people write it
23:34Arafangionamalloy: Ah, now the world makes sense again. :)
23:34ArafangionWithout the space, it just looked like an m-expr.
23:34amalloyArafangion: try writing a few lines of clojure before asking why everything is different from...a language you've never actually used?
23:35RaynesThere was a stackoverflow thread about this, but damn if I can find it.
23:35Arafangionamalloy: Touche.
23:35zakwilsonYou could also write (defn foo,[bar] ...) if you wanted.
23:36amalloy(defn, ,foo, ,, ,,,,,[,bar],,, ...) is my preferred style
23:37dnolen,(,,,,,,,,,,,(fn [a ,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,, b] (+ a b)) ,,,,,,, 1 ,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,,, 1)
23:37clojurebot2
23:37amalloyhm. i bet i could write a little program to morse-code the commas and spaces in a clojure program
23:37amalloy"take my existing program and rewrite the spacing so that the commas and spaces, in morse code, spell out this shell script"
23:39dnolenArafangion: reading a lot of Lisp papers w/o using it? that's interesting
23:40Arafangion"Take the existing program and modify it subly so that the commas and spaces are a valid Brain**** program" <-- THAT would make me die inside.
23:42Arafangiondnolen: I had no opportunity to use it, i was struggling enough with crappy C/VB/C#/Java projects in microsoft-shop/uni.
23:42Arafangiondnolen: It's remarkable how lecturers can violate just about every rule and still somehow have a 'working' program.
23:42ibdknoxOne of my favorite non-functionally-related parts of clojure is that I never have to type commas
23:42ArafangionAt work, I use mostly C#, Python, Ruby, and C.
23:43ArafangionAnd I don't have opportunity to use anything radical there, either.
23:43dnolenArafangion: gotcha. Well if you're using Ruby/Python, you're not so far from Clojure.
23:43duck1123ruby was a good gateway to clojure for me
23:44dnolenClojure is built on the lessons of Ruby/Python/JavaScript.
23:45Arafangiondnolen: Ruby, perhaps, but python? No, I think it's quite different to clojure.
23:45dnolenArafangion: convenient syntax for data structures
23:45zakwilsonI really hate going to other languages where I have to type commas in collection literals. It's a trivial irritation, but I still find it really irritating.
23:45ibdknoxzakwilson: me too
23:46greghespecially when you have to omit the last one
23:46ibdknoxhah
23:46ibdknoxfuck IE
23:46ibdknoxthat is one of the single most annoying things in all of JS
23:47zakwilsonClojure has list comprehensions. I don't think Ruby does. Python does.
23:47ibdknoxYou guys might laugh at this, but C# can actually get quite close to Clojure too
23:47Arafangiondnolen: The commas do get in the way.
23:48Arafangionibdknox: Yeah, how so? (But yeah, C# is a remarkably good language)
23:48Arafangiongregh: What's especially annoying is when a langauge doesn't let you have a trailing comma. Eg, foo = [1, 2, 3,]
23:49dnolenArafangion: going back a little. I use Scheme/Racket and Clojure. Clojure's take on the number of required parens and syntax around vectors is a real win.
23:49ibdknoxArafangion: depending on which version of C# you're using, with LINQ, var, anonymous functions, and collection initializers you can write very clojure-esque code
23:50ibdknoxdnolen: Arafangion: it's a huge win from a cognitive load stand point
23:50ibdknoxyou can't underestimate the value of conceptual consistency
23:50dnolenibdknox: I believe that. I think that people focus on Clojure differences, rather than how much it draws in Good Ideas™ from many mainstream languages.
23:50Arafangionibdknox: Yes - I do use a LOT of C# 4.0
23:51Arafangiondnolen: Yes, I like the idea of providing convenient data structures via []'s.
23:51Arafangion(Or whatever the syntax is)
23:52dnolenClojure from one stand point is - Maintstream Good Idea Goldmine™
23:52ibdknoxdnolen: yeah, that makes me sad. I mean even if you just step back and look at it without trying to understand it, it's much easier to section of and group things usefully without even really knowing what it is.
23:52ibdknoxoff*
23:52zakwilsonWhen will we see atoms and agents in other languages?
23:56Arafangionzakwilson: By what definition?
23:57ibdknoxCompletely unrelated, but the fact that this can be written in so few lines of code should blow your mind: http://mbostock.github.com/d3/ex/voronoi.html
23:57zakwilsonArafangion: Clojure has constructs called atoms and agents. You can read about them on clojure.org - that explanation will be far better than any I could give.
23:57ibdknoxit cheats, but still
23:58ibdknoxzakwilson: I thought there was an attempt to do something like the in Scala, but I can't remember what it is called