2010-10-24
| 01:03 | defn | oh my god. so much email to catch up on post-conj |
| 02:01 | wooby | defn: sup! |
| 04:51 | _ulises | morning |
| 05:50 | _ulises | how can I reset an ns so that I don't get illegal bindings? |
| 06:54 | raek | _ulises: either (in-ns 'some-other-ns) (remove-ns 'the-ns) or (ns-unmap 'the-ns 'conflicting-var) |
| 07:54 | _ulises | raek: thanks |
| 08:10 | ulises | why am I getting 'unmatched delimiter )' here: http://paste.lisp.org/display/115855 |
| 08:10 | ulises | :( |
| 08:14 | MayDaniel | ulises: The metadata needs to come before the namespace. |
| 09:07 | raek | _ulises: also, it is possible to do it like this: lastfm-clj.core |
| 09:07 | raek | eh |
| 09:07 | raek | (ns lastfm-clj.core "Core functions for lastfm-clj" {:author "Ulises Cervino Beresi"} ...) |
| 09:41 | bytesource | Hi all! I am currently reading the chapter on HBase of 'Clojure in Action'. I downloaded HBase but have no idea of how to install it on Linux. I couldn't find a simple manual either on the web. Does anybody know how to do the install? I am using Leiningen and Emacs. |
| 09:46 | kumarshantanu | ubuntu has apt-get for HBase/Hadoop? |
| 09:48 | tomoj | no |
| 10:02 | ulises | MayDaniel: thanks |
| 10:32 | Sweetshark | How do I access the static "class" member of a class object, i.e. what I write "Object.class" in Java returning the type? |
| 10:33 | _ulises- | I believe it's class |
| 10:33 | _ulises- | ,(class "foo") |
| 10:33 | clojurebot | java.lang.String |
| 10:33 | tomoj | ,String |
| 10:33 | clojurebot | java.lang.String |
| 10:33 | _ulises- | oh, wait |
| 10:33 | _ulises- | (,String/class) |
| 10:33 | _ulises- | ,(String/class) |
| 10:33 | clojurebot | java.lang.NoSuchFieldException: class |
| 10:34 | _ulises- | ,String/class |
| 10:34 | clojurebot | java.lang.Exception: Unable to find static field: class in class java.lang.String |
| 10:34 | _ulises- | hrm |
| 10:34 | tomoj | ,(class String) |
| 10:34 | clojurebot | java.lang.Class |
| 10:34 | kumarshantanu | ,(String/getClass) |
| 10:34 | clojurebot | java.lang.NoSuchFieldException: getClass |
| 10:35 | tomoj | Sweetshark: (just write "Object") |
| 10:35 | kumarshantanu | ,(.getClass "Whatever") |
| 10:35 | clojurebot | java.lang.String |
| 10:37 | Sweetshark | tomoj: actually (class String) looks like what I want ... |
| 10:41 | Sweetshark | meh, not quite ... but (Class/forName "java.lang.String") should do for now ... |
| 10:43 | _ulises- | Sweetshark: what are you trying to do anyway? |
| 10:44 | Sweetshark | _ulises-: http://api.openoffice.org/docs/java/ref/com/sun/star/uno/UnoRuntime.html#queryInterface%28java.lang.Class,%20java.lang.Object%29 |
| 10:44 | tomoj | Sweetshark: what? |
| 10:44 | tomoj | ,(= (Class/forName "java.lang.String") String) |
| 10:44 | clojurebot | true |
| 10:44 | tomoj | just write "String"... |
| 10:45 | _ulises- | right |
| 10:48 | rdeshpande | anyone else having issues getting labrepl to 'lein deps'? |
| 10:50 | Sweetshark | tomoj _ulises-: well it parses of the repl, thanks so far ... |
| 10:52 | _ulises- | rdeshpande: I've cloned a fresh labrepl and doing lein deps as we speak |
| 10:52 | _ulises- | so far, no issues |
| 10:57 | _ulises- | rdeshpande: right, lein deps has finished without issues, what issues are you encoutering? what arch? which version of labrepl? etc. |
| 11:03 | defn | hey all |
| 11:06 | _ulises- | hey defn |
| 11:08 | rdeshpande | _ulises-: im seeing this http://pastie.org/1245060 - but where is 1.2.0beta1 coming from? i dont' see 'beta1' anywhere grepped in the repo. shouldn't it just be getting 1.2? |
| 11:09 | raek | http://build.clojure.org/releases/org/clojure/clojure/ it exists here |
| 11:09 | _ulises- | this is what I have on my project.clj: http://pastie.org/1245065 |
| 11:09 | _ulises- | see if there's anything different with yours? |
| 11:10 | maravillas | perhaps it's a transitive dependency |
| 11:12 | rdeshpande | _ulises-: nope, same exact ting |
| 11:12 | maravillas | is your labrepl up to date? |
| 11:12 | rdeshpande | yep |
| 11:12 | rdeshpande | just cloned |
| 11:12 | _ulises- | rdeshpande: tried pulling from ... oh |
| 11:13 | _ulises- | I can also see you're on OS X, like me :/ |
| 11:13 | maravillas | hm, i just grabbed its deps and got 1.2, not beta1 |
| 11:13 | maravillas | oh, nevermind |
| 11:13 | _ulises- | same for me |
| 11:13 | maravillas | it's a dev-dep |
| 11:13 | rdeshpande | could it be something in my home dir? |
| 11:13 | maravillas | either autodoc or swank-clojure must depend on it |
| 11:14 | maravillas | regardless, though, i was able to grab it |
| 11:14 | rdeshpande | hmm |
| 11:14 | rdeshpande | very odd |
| 11:15 | maravillas | hm, nope |
| 11:15 | maravillas | well, that's beside the point anyway |
| 11:15 | maravillas | actually, i bet i had mine cached locally |
| 11:18 | _ulises- | rdeshpande: I suppose that telling you to start afresh is pointless? |
| 11:19 | rdeshpande | not sure how much fresh it could be :/ |
| 11:19 | rdeshpande | *how much more |
| 11:19 | _ulises- | did you *just* do a clone? |
| 11:19 | _ulises- | I did mine when you asked the question actually |
| 11:20 | defn | Can someone refresh my memory on :use in the (ns) macro |
| 11:20 | defn | specifically how to use :as with :use |
| 11:20 | maravillas | _ulises-: the latest isn't working for me either, after i deleted the cached copy in ~/.m2 |
| 11:21 | defn | (:use clojure.contrib [io :as foo]) |
| 11:21 | _ulises- | maravillas: oh :( |
| 11:22 | _ulises- | what about leiningen? do you have the latest version? |
| 11:22 | maravillas | i don't understand why, unfortunately, since beta1 is still available on the build site |
| 11:27 | maravillas | rdeshpande: as a workaround, you could try downloading clojure-1.2.0-beta1.jar, .jar.sha1, .pom, and .sha1 from http://build.clojure.org/releases/org/clojure/clojure/1.2.0-beta1 and putting them in ~/.m2/repository/org/clojure/clojure/1.2.0-beta1 |
| 11:27 | maravillas | it's not the right answer...someone else might have more insight |
| 11:32 | wooby | defn: http://gist.github.com/284277 |
| 11:32 | KLll | guys |
| 11:33 | KLll | I have a vector |
| 11:33 | KLll | (def some-vec [1 2 3]) |
| 11:33 | KLll | what's the best way to modify it |
| 11:33 | defn | wooby: !! |
| 11:33 | _ulises | KLll: you don't? |
| 11:33 | KLll | (def some-vec (assoc some-vec 2 3)) |
| 11:33 | KLll | or what? |
| 11:33 | defn | wooby: you sir, are a saint |
| 11:34 | _ulises | why do you need to modify it? |
| 11:34 | KLll | I want to add to it |
| 11:34 | KLll | or change it |
| 11:34 | KLll | for instance I have a vector of maps or listeneres to events |
| 11:35 | _ulises | assoc is possibly what you want |
| 11:35 | wooby | KLll: in clojure the modification of things by re-deffing them is discouraged, there are special types for handing variables that can change over time. atom is probably the one you should check out |
| 11:35 | KLll | adding a listener requires changing a map, then associng that map into the vector, then I have to rebind the vector |
| 11:35 | _ulises | keep in mind that if you do (assoc [] 1 1) you'll get out of bounds exceptions |
| 11:35 | _ulises | also what wooby said |
| 11:35 | wooby | (def my-vec (atom [1 2 3])) |
| 11:36 | wooby | KLll: http://clojure.org/atoms |
| 11:37 | wooby | i now giggle every time i see fib used as an example anywhere |
| 11:38 | maravillas | it's now possible to reference fib ironically |
| 11:39 | KLll | the thing is |
| 11:39 | kumarshantanu | is it possible to access clojure.repl/source in code? (instead of REPL) |
| 11:39 | KLll | in nearly every program I have some state |
| 11:39 | kumarshantanu | ,(source source) |
| 11:39 | clojurebot | java.lang.Exception: Unable to resolve symbol: source in this context |
| 11:39 | KLll | that changes |
| 11:39 | KLll | so the atoms are the way to do it? |
| 11:39 | kumarshantanu | ,(clojure.repl/source source) |
| 11:40 | clojurebot | Source not found |
| 11:40 | raek | keyword args question: if I do a (foo :a 1 :b 2) call, I want to get 'options' bound to {:a 1, :b 2}. is (defn foo [& {:as options}] ...) the correct way to do that? |
| 11:40 | wooby | kumarshantanu: (use 'clojure.contrib.repl-utils) (source atom) |
| 11:41 | raek | or, I guess my question is "when does function arguments automagically become maps=" |
| 11:41 | wooby | KLll: not always - there are also refs and agents |
| 11:41 | KLll | how do you decide between using an atom and using a ref |
| 11:42 | raek | KLll: refs are for when you might need to coordinade changes of multiple refs |
| 11:42 | raek | with atoms, you can't do that |
| 11:42 | KLll | I see that |
| 11:43 | raek | so, if you have something internally that only you use, (like a counter or something) you could use an atom |
| 11:43 | raek | but when others need to use it too, it might be better to use refs to be on the safe side |
| 11:44 | wooby | good screencasts that cover the use cases for refs/atoms/agents: http://www.pluralsight-training.net/microsoft/olt/course/toc.aspx?n=clojure-concurrency-tutorial |
| 11:44 | bmh | does clojure have a function like Haskell's zip or zipWith? (map over two collections simultaneously) |
| 11:45 | opqdonut | ,(map + [1 2 3] [4 5 6]) |
| 11:45 | clojurebot | (5 7 9) |
| 11:45 | bmh | oh. That's convenient. |
| 11:45 | opqdonut | ,(map vector [1 2 3] [4 5 6]) |
| 11:45 | clojurebot | ([1 4] [2 5] [3 6]) |
| 11:46 | wooby | bmh: there's also zipmap |
| 11:46 | opqdonut | which is mostly unrelated |
| 11:46 | wooby | does the haskell thingy not return a map? |
| 11:46 | bmh | it doesn't |
| 11:47 | wooby | ah |
| 11:47 | raek | zip returns tuples |
| 11:47 | bmh | The type of zip is: [a] -> [b] -> [(a,b)] |
| 11:47 | wooby | ignore me :) |
| 11:47 | opqdonut | haskell's zip does what map vector does |
| 11:47 | opqdonut | zipWith does what clojure's map does |
| 11:48 | bmh | sometimes I think programming in clojure would be easier if I didn't know scheme/haskell |
| 11:48 | bmh | I'd have read the manual. |
| 11:54 | KLll | hi |
| 11:56 | KLll | sup |
| 11:56 | TheAnimal4 | Yo yo yo KLll |
| 12:01 | defn | wooby: fib is important to programming |
| 12:01 | defn | factorial is also really important to what we do everyday. |
| 12:02 | defn | thinking out loud: im not sure what i'd do if i didnt have factorial, probably just code hello world over and over |
| 12:03 | rdeshpande | bmh: what is your impression so far coming from haskell? |
| 12:04 | bmh | rdeshpande: from scheme might be a little more fair. I really dig the loop-recur construct |
| 12:04 | bmh | multimethods are wonderful |
| 12:07 | defn | i like functions :D |
| 12:07 | _ulises | I recently found a use for protocols ... go figure :D |
| 12:07 | defn | im making a conscious effort post-conj to use some more protocols in my code |
| 12:07 | _ulises | well, more like I just came across a case where I thought "thank god for protocols" |
| 12:08 | defn | chouser's finger tree code makes some nice use of protocols |
| 12:09 | jarpiain | Ok, my port of the clojure compiler into clojure seems now capable of compiling itself. Time to release :) |
| 12:09 | jarpiain | http://github.com/jarpiain/cljc |
| 12:09 | bmh | rdeshpande: I think the interop is my favorite feature. At the absolute worst, it makes clojure as good as java. |
| 12:09 | bmh | Praise be to Technomancy for giving us Lein. |
| 12:09 | defn | don't forget the cake :) |
| 12:10 | gfrlog | clojure is not as good as java at worst |
| 12:11 | gfrlog | it lacks most of the static benefits |
| 12:11 | defn | if i wanted to use statics i wouldnt be using clojure in the first place |
| 12:11 | opqdonut | why not |
| 12:12 | defn | i want a dynamic language. |
| 12:12 | gfrlog | my point was that if I'm going to resort to using clojure by just calling java, I'll get a lot more benefit out of using java as java |
| 12:12 | opqdonut | clojure could be a great dynamic language with optional static features |
| 12:12 | opqdonut | common lisp is quite good at being both static and dynamic |
| 12:12 | defn | gfrlog: it depends. |
| 12:12 | bmh | I want a type system ;-) |
| 12:13 | gfrlog | defn: what do you mean? |
| 12:13 | bmh | It's absurd that the jvm doesn't support tco |
| 12:13 | gfrlog | bmh: it makes sense to me, assuming they designed it for java |
| 12:13 | defn | gfrlog: it depends on what you care about. if you're only concerned with the benefits of statics then okay, but who the heck cares about just one thing? |
| 12:14 | defn | i want an expressive language. i want maintainable code. |
| 12:14 | bmh | gfrlog: Not in the slightest. Java is an OO language. You program in an OO language by calling methods. |
| 12:14 | gfrlog | defn: nobody of course, but static benefits are huge |
| 12:14 | gfrlog | defn: I'm assuming a hypothetic world (i.e., "at worst") where the best use you can make of clojure is to pretend it's java using the interop |
| 12:14 | bmh | gfrlog: If you don't have tail-calls, eventually your method calls smash the stack. Therefore, you can't write OO java! |
| 12:14 | KLll | I find my code less maintainable in clojure |
| 12:15 | defn | gfrlog: yeah, in the real world things are a bit different ;) |
| 12:15 | gfrlog | bmh: clearly you can -- you use for loops instead of recursive algs |
| 12:15 | gfrlog | defn: they are. I spend too much time on theory sometimes. |
| 12:15 | KLll | any recursion can be changed into iteration |
| 12:15 | somnium | bmh: have you read GVR's manifesto against tail calls and fp in general? |
| 12:15 | kumarshantanu | any CCW user here? |
| 12:16 | bmh | somnium: I did. I don't think much of him. |
| 12:16 | bmh | somnium: Have you read Xavier Leroy's rants about kernel threads in Ocaml? |
| 12:16 | defn | who is GVR |
| 12:16 | defn | oh... nvm |
| 12:16 | bmh | Guido |
| 12:16 | defn | guido |
| 12:16 | defn | if you have a link ill entertain it :) |
| 12:16 | somnium | bmh: I have not. I just wanted to mention my amazement that a language designer would be openly hostile to such fundamentally useful features |
| 12:17 | bmh | somnium: I think Guido is a turd. |
| 12:17 | defn | somnium: the human condition sucks |
| 12:17 | defn | you make a decision so you have to hate all other decisions or something |
| 12:17 | defn | it's ludicrous |
| 12:18 | gfrlog | sunk cost fallacy |
| 12:18 | gfrlog | or something similar |
| 12:18 | _ulises | perhaps larry wall is the king of inflammatory remarks |
| 12:18 | bmh | Xavier is a bit of a different story. Fire up your favorite GNU/Linux distro and type 'man pthread' |
| 12:18 | defn | perhaps larry wall is the worst speaker i've ever seen |
| 12:18 | bmh | "linuxthreads-0.10 by Xavier Leroy", it makes his opposition to kernel threads seem slightly less insane |
| 12:18 | gfrlog | $ man pthread |
| 12:18 | bmh | defn: I agree entirely. |
| 12:18 | gfrlog | No manual entry for pthread |
| 12:18 | bmh | pthreads, sorry |
| 12:18 | defn | bmh, did we meet yesterday? |
| 12:19 | gfrlog | much better |
| 12:19 | bmh | defn: We didn't. |
| 12:19 | defn | heh sorry -- im trying to do post-conj association |
| 12:19 | defn | so many twitter handles and nicks and names in my head atm |
| 12:19 | bmh | I last saw Larry Wall speak in... 2007? |
| 12:19 | gfrlog | I was that guy sitting in one of the chairs |
| 12:19 | defn | gfrlog: omg. same. |
| 12:20 | gfrlog | defn: damn, we should've talked |
| 12:20 | defn | i know. next time you're at a conference talk to the guy in the chair, that'll be me. |
| 12:20 | gfrlog | okay |
| 12:20 | defn | unless he's not, in which case: keep trying. |
| 12:20 | gfrlog | two or three tries max I'm sure |
| 12:21 | defn | the sarcasm is palpable |
| 12:21 | gfrlog | and sticky |
| 12:21 | defn | indeed. *investigates the palp closely* |
| 12:22 | defn | as in palpus |
| 12:22 | bmh | Does clojure have a function like "conj-with" for shoving things into a map? (i.e. If a key already exists, then use some function to combine the values) |
| 12:22 | _ulises | bmh: merge-with |
| 12:22 | _ulises | ,(doc merge-with) |
| 12:22 | clojurebot | "([f & maps]); Returns a map that consists of the rest of the maps conj-ed onto the first. If a key occurs in more than one map, the mapping(s) from the latter (left-to-right) will be combined with t... |
| 12:23 | defn | will be combined with the mapping in the result by calling (f val-in-result val-in-latter). |
| 12:24 | KLll | Hi |
| 12:24 | TheAnimal4 | Greetings KLll |
| 12:24 | KLll | my greeter bot :P |
| 12:24 | defn | epic. |
| 12:24 | defn | Hi |
| 12:24 | TheAnimal4 | Greetings defn |
| 12:24 | KLll | :P |
| 12:24 | gfrlog | clojurebot: hey |
| 12:24 | clojurebot | hey is for horses |
| 12:25 | bmh | _ulises: sure, but merge with noms a pile of maps, oh, I guess it'll work |
| 12:25 | KLll | hello |
| 12:25 | TheAnimal4 | Greetings KLll |
| 12:25 | KLll | sup |
| 12:25 | TheAnimal4 | Yo yo yo KLll |
| 12:25 | _ulises | bmh: you can always use {} as one of the maps |
| 12:25 | _ulises | bmh: I suppose you could also use reduce? |
| 12:26 | defn | heh -- any new language, if it wants to be successful, needs to have a separate channel for the inevitable irc bot experimentation that will occur |
| 12:26 | _ulises | I'm not familiar with conj-with unfortunately |
| 12:26 | KLll | next up: let's plug it into Warhammer item database so it will quote stats into the channel :P |
| 12:26 | bmh | KLll: why don't you write a bot that finds arbitrage opportunities in Warhammer? ;-) |
| 12:26 | KLll | maybe I should look into some textual analysis |
| 12:27 | defn | linkparser maybe? |
| 12:27 | KLll | so it picks out buzzwords out of random chat |
| 12:27 | KLll | then repeats statements about that buzzword from weeks ago |
| 12:27 | defn | "web 2.0", "agile", etc. |
| 12:27 | KLll | that would troll many people |
| 12:28 | defn | set up some future/promise or agent type thing that, when someone responds, tells them in no uncertain terms they have been trolled |
| 12:28 | KLll | hahahah |
| 12:29 | defn | there's this hillarious library for clojure that generates business BS, like "synergizing business ROI with gold futures" |
| 12:29 | defn | err for ruby, it's called "faker" |
| 12:30 | KLll | something like that |
| 12:30 | KLll | I recall a channel where they had a bot named |
| 12:30 | KLll | gothgirl19 |
| 12:30 | KLll | or something like that |
| 12:31 | KLll | it regurtiated back statements converted into questions |
| 12:31 | defn | heh yes ive seen that trolling mechanism in action -- i used to know someone who did a similar thing with a bot named "cutie5484" |
| 12:31 | KLll | when they looks at chat logs there were a surprising amount of people trying to pick up the bot and talking to the bot for hours |
| 12:32 | kumarshantanu | is it possible to get the name of a function as string? map? --> "map?" |
| 12:32 | defn | sure |
| 12:33 | gfrlog | um |
| 12:33 | gfrlog | really? |
| 12:33 | kumarshantanu | defn: how? |
| 12:33 | gfrlog | is it in the metadata? |
| 12:33 | somnium | kumarshantanu: from the runtime representation? |
| 12:33 | defn | there are a few ways |
| 12:33 | defn | ,(str (:name (meta #'and))) |
| 12:33 | clojurebot | "and" |
| 12:34 | kumarshantanu | ,(str (:name (meta map?))) |
| 12:34 | clojurebot | "" |
| 12:34 | KLll | why the #'? |
| 12:34 | defn | interesting... |
| 12:34 | KLll | isn't ' enough?? |
| 12:35 | gfrlog | '(let [my-fun vector?] (str (:name (meta #'my-fun)))) |
| 12:35 | KLll | ,(str (:name (meta 'map?))) |
| 12:35 | clojurebot | "" |
| 12:35 | gfrlog | ,(let [my-fun vector?] (str (:name (meta #'my-fun)))) |
| 12:35 | clojurebot | java.lang.Exception: Unable to resolve var: my-fun in this context |
| 12:35 | gfrlog | I suck at commas |
| 12:35 | defn | ,(meta 'map?) |
| 12:35 | clojurebot | nil |
| 12:35 | defn | ,(meta #'map) |
| 12:35 | clojurebot | {:ns #<Namespace clojure.core>, :name map, :file "clojure/core.clj", :line 2079, :arglists ([f coll] [f c1 c2] [f c1 c2 c3] [f c1 c2 c3 & colls]), :added "1.0", :doc "Returns a lazy sequence consisti... |
| 12:35 | gfrlog | ,(let [my-fun vector?] (str (:name (meta my-fun)))) |
| 12:35 | KLll | ,(str (:name (meta #'map?))) |
| 12:35 | clojurebot | "" |
| 12:35 | clojurebot | "map?" |
| 12:35 | defn | there ya go :) |
| 12:35 | KLll | ,(meta 'map) |
| 12:35 | clojurebot | nil |
| 12:35 | defn | there's another way too but im failing to remember it |
| 12:36 | KLll | seriously, what's the difference between ' and #' |
| 12:36 | raek | ,(class 'conj) |
| 12:36 | clojurebot | clojure.lang.Symbol |
| 12:36 | raek | ,(class #'conj) |
| 12:36 | defn | quote, var quote |
| 12:36 | clojurebot | clojure.lang.Var |
| 12:37 | kumarshantanu | how do I #" inside a macro? |
| 12:37 | defn | KLll: #' is var quote, ' is quote |
| 12:37 | somnium | ah, map? is defined with `def', not `defn', so I guess the metadata doesn't get attached to the function object? |
| 12:37 | raek | the metadata usually go on the var object rather than the fn object |
| 12:37 | KLll | could be |
| 12:38 | raek | but since 1.2, fns can have metadata too |
| 12:38 | defn | ,(meta #'map?) |
| 12:38 | clojurebot | {:ns #<Namespace clojure.core>, :name map?, :file "clojure/core.clj", :line 149, :arglists ([x]), :doc "Return true if x implements IPersistentMap", :added "1.0"} |
| 12:38 | somnium | I think defn commutes the metadata now |
| 12:38 | somnium | ,(meta map?) |
| 12:38 | clojurebot | {:line 153} |
| 12:38 | defn | gotta var quote |
| 12:38 | kumarshantanu | defn: how can i var-quote inside a macro? |
| 12:39 | defn | kumarshantanu: i have code somewhere, one sec |
| 12:39 | kumarshantanu | #'~fn-name |
| 12:39 | wooby | jarpiain: re: compiler, neat! |
| 12:39 | somnium | defn: if you don't know the name it's hard to var-quote :P |
| 12:39 | KLll | does clojure have date stuff, or do I have to use java.util.Date? |
| 12:39 | defn | ;) |
| 12:39 | raek | kumarshantanu: it is not known at macro expansion time what var the symbol fn-name will refer to |
| 12:39 | defn | somnium: oh right |
| 12:40 | raek | KLll: clj-time is a neat lib (a wrapper for Joda time) |
| 12:40 | raek | javas date classes are a mess |
| 12:40 | defn | no doubt |
| 12:41 | KLll | not really once you use GregorianCalendar :P |
| 12:41 | raek | joda time makes the dates immutable, so they work pretty well with clojure |
| 12:41 | KLll | I really like the mutators on GregorianCalendar |
| 12:41 | KLll | they are really neat |
| 12:42 | defn | im outta here, folks |
| 12:42 | raek | kumarshantanu: if you have the symbol foo and want "foo", you can simply use the function 'name' |
| 12:42 | raek | ,(name 'foo) |
| 12:42 | clojurebot | "foo" |
| 12:43 | kumarshantanu | raek: I am passing a function to a macro, and want to find out the name inside that macro |
| 12:44 | defn | kumarshantanu: where does the function come from |
| 12:44 | defn | what if you get an anonymous function? |
| 12:44 | raek | kumarshantanu: the fn object itself does not know wich names are bound to it |
| 12:44 | kumarshantanu | actually I am trying to diagnose some defects -- so the macro asserts few values and then (should) tell which function failed -- so I need the name |
| 12:45 | raek | a macro could of course look at the unevaluated argument and if it is a symbol, treat that as the name for it |
| 12:45 | somnium | ,(meta (resolve 'map?)) |
| 12:45 | clojurebot | {:ns #<Namespace clojure.core>, :name map?, :file "clojure/core.clj", :line 149, :arglists ([x]), :doc "Return true if x implements IPersistentMap", :added "1.0"} |
| 12:45 | KLll | (re-find #"time" "don't have time") |
| 12:45 | KLll | ,(re-find #"time" "don't have time") |
| 12:45 | clojurebot | "time" |
| 12:46 | raek | kumarshantanu: you could store the unevaluated argument. in that case, you get the code for the expression that failed |
| 12:46 | somnium | ,(let [fname 'map?] `(prn ~(meta (resolve fname)))) |
| 12:46 | clojurebot | (clojure.core/prn {:ns #<Namespace clojure.core>, :name map?, :file "clojure/core.clj", :line 149, :arglists ([x]), :doc "Return true if x implements IPersistentMap", :added "1.0"}) |
| 12:46 | somnium | kumarshantanu: perhaps that will work? |
| 12:47 | kumarshantanu | AH! got it -- (:name (meta (resolve (quote ~f?)))) |
| 12:48 | kumarshantanu | f? is the function name the macro accepts |
| 12:50 | kumarshantanu | somnium: raek: thanks |
| 12:50 | KLll | !time |
| 12:50 | somnium | kumarshantanu: cheers |
| 12:50 | KLll | !time |
| 12:53 | KLll | !time |
| 12:53 | Upper | I need a help here pleaseI can't find the error - http://pastebin.com/JvZgH1E7 |
| 12:54 | Upper | was created a loop/when to print a different message in each iteration |
| 12:55 | KLll | so if I do (defn fun1 ....) |
| 12:55 | KLll | then make some vector [fun1] |
| 12:55 | KLll | and then re-def it (defn fun1 something else ...) |
| 12:55 | KLll | the vector now holds the old one ? |
| 12:56 | KLll | !time |
| 12:56 | TheAnimal4 | Time is java.util.GregorianCalendar[time=1287939389109,areFieldsSet=true,areAllFieldsSet=true,lenient=true,zone=sun.util.calendar.ZoneInfo[id="Europe/Prague",offset=3600000,dstSavings=3600000,useDaylight=true,transitions=141,lastRule=java.util.SimpleTimeZone[id=Europe/Prague,offset=3600000,dstSavings=3600000,useDaylight=true,startYear=0,startMode=2,startMonth=2,startDay=-1,startDayOfWeek=1,startTime=3600000,startTimeMode=2,endMo |
| 12:56 | raek | Upper: you don't have any call to recur |
| 12:56 | KLll | oops :P |
| 12:57 | raek | Upper: see http://clojure.org/special_forms#Special%20Forms--%28recur%20exprs*%29 |
| 12:58 | Upper | hm right |
| 13:01 | raek | Upper: the basic code building block of a functional programming language is an expression, not a statement |
| 13:01 | raek | (+ 2 i) means take i and add two and return that. it does not change i |
| 13:14 | kumarshantanu | is it a bug that pos? throws exception on nil? |
| 13:15 | kumarshantanu | ,(pos? nil) ; expected false, right? |
| 13:15 | clojurebot | java.lang.NullPointerException |
| 13:15 | gfrlog | ,(pos? "haha I'm a string") |
| 13:15 | clojurebot | java.lang.ClassCastException: java.lang.String cannot be cast to java.lang.Number |
| 13:15 | gfrlog | ,(num nil) |
| 13:16 | clojurebot | nil |
| 13:39 | riddochc | Anybody got suggestions for decent reading material to understand Java IO, nio, netty, etc. from a Clojure context? Got a little project I'm playing with, and aleph seems nicely suited to it, but I'm running up against a pretty steep learning curve here. |
| 13:41 | riddochc | I suspect non-Clojure contexts would do, too, since I'm familiar enough with the Clojure side of things to be able to translate it... but I'm not very familiar with the Java APIs, and they seem tremendously more complicated than I would've expected. |
| 13:47 | rhudson | riddochc, I suspect you'd do well to start with the netty documentation. |
| 13:47 | rhudson | I don't think you really have to understand the details of nio (thankfully!) to grok netty |
| 13:48 | rhudson | All you really need to know about nio to start with is that the asynch stuff is based on the OS select |
| 13:49 | riddochc | rhudson: Hm. I'll try reading it again, then. |
| 13:49 | riddochc | rhudson: Is it just me, or does everything seem to assume that a protocol will be layered on top of HTTP? |
| 13:50 | rhudson | Seems the way of the world these days... |
| 13:50 | rhudson | The advantage is that the server only needs to open ports 80 & 443 |
| 14:00 | KirinDave | Hey |
| 14:00 | gfrlog | hi |
| 14:00 | KirinDave | Earlier someone had been linking some new screencasts to all different parts of clojure |
| 14:00 | KirinDave | Like several on vars, several on refs, etc |
| 14:00 | KirinDave | Does anyone still have that link? I lostit |
| 14:01 | maravillas | the full disclojure screencasts? |
| 14:01 | raek | this one? http://www.pluralsight-training.net/microsoft/olt/course/toc.aspx?n=clojure-concurrency-tutorial |
| 14:01 | maravillas | http://vimeo.com/channels/fulldisclojure |
| 14:01 | KirinDave | raek: Those, idneed. |
| 14:01 | KirinDave | Thanks |
| 14:01 | raek | KirinDave: this is a goldmine: http://alexott.net/en/clojure/video.html |
| 14:02 | KirinDave | Dang |
| 14:02 | KirinDave | That's solid. |
| 14:03 | TakeV | What is exactly meant by "synchronous" and "unsynchronous" when talking about the difference between refs and atoms? And coordinated for that matter. |
| 14:04 | gfrlog | I can explain it after this chess game |
| 14:05 | TakeV | Sure. :) |
| 14:05 | KirinDave | So my webmachine->clojure port is in basic working order. |
| 14:05 | KirinDave | It doesn't handle everything and the tests aren't there, but I'm considering open sourcing it. |
| 14:05 | gfrlog | crap I lost |
| 14:05 | KirinDave | I'm not sure if I should do so today or tomorrow. |
| 14:06 | KirinDave | Like today is the tail-end of the conj, so... |
| 14:06 | gfrlog | TakeV: refs and atoms are both synchronous, so I think that issue should only come up when comparing either to agents |
| 14:06 | gfrlog | does that sound right? |
| 14:06 | KirinDave | gfrlog: Yeah |
| 14:07 | TakeV | gfrlog: I'm not sure what that term means, though. Likewise when discussing if they are coordinated or not. |
| 14:07 | gfrlog | TakeV: okay, so a for the synchronous ones (refs/atoms) |
| 14:07 | KirinDave | TakeV: Where did you see this? |
| 14:08 | gfrlog | they are evaluated in the current running thread, so your code doesn't proceed until the expession is finished evaluating |
| 14:08 | gfrlog | in contrast, when you send a function to an agent, the (send) call returns immediately, and the function gets evaled later on some other thread |
| 14:09 | gfrlog | so that's the sync/async distinction -- did it make sense? |
| 14:09 | TakeV | It does. Sounds somewhat like how locking works. |
| 14:09 | gfrlog | I think the explainer part of my brain is a bit muddled |
| 14:09 | KirinDave | TakeV: While it might involve locks, that's not what's going on |
| 14:10 | KirinDave | TakeV: Agents receive work queues. |
| 14:10 | KirinDave | TakeV: Atoms and refs do not. |
| 14:10 | KirinDave | TakeV: Agents work in the threadpool, atoms and refs do not |
| 14:10 | gfrlog | the fns sent to atoms and refs get evaled immediately while your thread execution waits |
| 14:11 | TakeV | What about coordination? |
| 14:11 | gfrlog | only refs are coordinated |
| 14:11 | TakeV | What does it mean? |
| 14:11 | gfrlog | what it means is that you can update several at once, and the whole action is atomic, like a database transaction |
| 14:11 | KirinDave | If you make a transaction over multiple refs, they all get updated or do not |
| 14:12 | gfrlog | and no other thread can see them in some intermediate state |
| 14:12 | TakeV | Thank you for the explanations. :) |
| 14:12 | gfrlog | no probalo |
| 14:14 | gfrlog | ,(deref (ref 10)) |
| 14:14 | clojurebot | 10 |
| 14:15 | gfrlog | ,(detain (tain 10)) |
| 14:15 | clojurebot | java.lang.Exception: Unable to resolve symbol: detain in this context |
| 14:49 | polypus | ~ping |
| 14:49 | clojurebot | PONG! |
| 14:49 | Upper | what the difference between (juxt) and (do) ? with both I can execute two operations |
| 14:49 | gfrlog | woah |
| 14:50 | Upper | i dont know juxt exectly |
| 14:50 | gfrlog | juxt combines some functions into a new function |
| 14:50 | gfrlog | ,(juxt first last) |
| 14:50 | clojurebot | #<core$juxt$fn__3661 clojure.core$juxt$fn__3661@11a74ef> |
| 14:50 | gfrlog | so that returns a new function |
| 14:50 | gfrlog | (let [f (juxt first last)] (f [6 7 8 9 10])) |
| 14:51 | Upper | hmm i got |
| 14:51 | gfrlog | ,(let [f (juxt first last)] (f [6 7 8 9 10])) |
| 14:51 | clojurebot | [6 10] |
| 14:51 | Upper | cool |
| 14:51 | gfrlog | the new function calls both of the functions supplied to it and returns a vector of the results |
| 14:51 | raek | Upper: do is useful when you need to do side-effects |
| 14:51 | gfrlog | ,(do (+ 3 4)) |
| 14:51 | clojurebot | 7 |
| 14:52 | gfrlog | hmm |
| 14:52 | raek | (defn trace [x] (do (println "value: " x) x)) |
| 14:53 | raek | Upper: you can then wrap that trace function around an expression to make clojure print it when it is evaluated |
| 14:53 | rhudson | ,(let [f (first second last)] (f [1 2 3 4 5])) |
| 14:53 | clojurebot | java.lang.IllegalArgumentException: Wrong number of args (2) passed to: core$first |
| 14:53 | Upper | interesting |
| 14:54 | rhudson | ,(let [f (juxt first second last)] (f [1 2 3 4 5])) |
| 14:54 | clojurebot | [1 2 5] |
| 14:54 | raek | Upper: however, function bodies alreade has an "implicit do", so you don't need to write the do in that case |
| 14:56 | Upper | usually I use do like a "then" of a cond, If I just open two parenthesis the second turn an else |
| 14:57 | Upper | I understood |
| 14:58 | raek | ah, ok... sorry for over-explaining... :) |
| 14:58 | serabe | hi |
| 15:01 | raek | anyone happen to know if a java.net.Socket is completely closed when both its InputStream and OutputStream are closed? or do I have to close the Socket object too? |
| 15:02 | somnium | raek: you might need an AbstractSocketCloserFactoryFactory to really be safe |
| 15:03 | raek | :P |
| 15:04 | raek | man... factory-factories... do they really exist? |
| 15:05 | raek | no wait. don't tell me. I don't wanna know... |
| 15:05 | dakrone | raek: http://ws.apache.org/xmlrpc/apidocs/org/apache/xmlrpc/server/RequestProcessorFactoryFactory.html |
| 15:05 | somnium | http://www.docjar.org/docs/api/org/outerj/pollo/xmleditor/FactoryFactory.html |
| 15:05 | firepoet | Ouch |
| 15:14 | rata_ | hi |
| 15:15 | Upper | can i break a code in clojure? I need to stop because it is returning two values. |
| 15:16 | drewr | Upper: (throw (Exception.)) |
| 15:18 | Upper | :) works |
| 15:19 | rata_ | Upper, for debugging? |
| 15:28 | Upper | no. to final use |
| 15:28 | Upper | lazy to find a good solution |
| 15:30 | gfrlog | creating an infinite seq of primes elegantly is surprisingly tricky |
| 15:31 | rata_ | gfrlog, why? |
| 15:32 | gfrlog | rata_: particularly if by "elegantly" we mean something you can create with (iterate), such that it doesn't require much memory and doesn't compute in large chunks, and is efficient (i.e., doesn't use division) |
| 15:35 | gfrlog | it took me several tries over the course of the conj |
| 15:35 | Upper | , (doc yield) |
| 15:35 | clojurebot | Excuse me? |
| 15:35 | gfrlog | clojurebot: are your responses hard-coded? |
| 15:35 | clojurebot | It's greek to me. |
| 15:35 | Upper | lol |
| 15:35 | gfrlog | clojurebot: you mean coded in greek? |
| 15:36 | clojurebot | excusez-moi |
| 15:48 | technomancy | icey: I think I missed you at the conj; bummer. |
| 15:48 | technomancy | how goes the plugin task? |
| 15:54 | polypus | anybody here done server push (comet, websockets, etc) from clojure? |
| 15:58 | Upper | are the something wrong here? (dotimes [n 100] (test 0 1 n)) |
| 15:58 | Upper | it returns "nil" executing 1 time only |
| 15:58 | Upper | neither call my function |
| 15:58 | jackdempsey | technomancy: fwiw that deps issue didn't matter. (use 'compojure) is no longer valid i guess since 0.4 or something. thx for the help |
| 15:59 | qbg | Upper: Are you sure your function isn't being called? |
| 16:00 | Upper | i guess, my function always return a message with println |
| 16:00 | technomancy | jackdempsey: good to know. |
| 16:01 | Upper | exist other ways to make a loop? |
| 16:01 | qbg | Upper: Post the code that isn't working |
| 16:02 | qbg | Including the definition of test |
| 16:02 | qbg | Do you get an error when loading your code? test is also the name of a function in clojure.core |
| 16:06 | Upper | qbg: see http://pastebin.com/g2HkDdP4 - and I do (loopTest 100) |
| 16:09 | qbg | It looks like quadradoPerfeito is broken |
| 16:12 | qbg | When I run your code it is throwing the exception that you throw, so that is why it is only being run once |
| 16:13 | Upper | ah maybe |
| 16:13 | qbg | Also, the cond has two :else conditions statements |
| 16:13 | qbg | *conditions |
| 16:13 | qbg | And the return value of the cond form isn't even used! |
| 16:14 | qbg | If the first :else case of the cond is ever invoked, you will get a NullPointerException because you have an extra set of parens |
| 16:15 | qbg | That first :else condition also does some math, but then throws away the value |
| 16:16 | qbg | The code is also not formatted idiomatically |
| 16:17 | Upper | tks, i will try to fix it |
| 16:29 | jjido | What are the dates of the Clojure conj? Is it finished? |
| 16:30 | FFUser | yep |
| 16:30 | jjido | was it good? |
| 16:31 | qbg | There are reports that it was very good |
| 16:32 | nickik | form what I read on twitter it was fantastic |
| 16:32 | nickik | im really waiting for the videos |
| 16:32 | jjido | nickik: thanks |
| 16:33 | qbg | Does anyone know of a syntax-rules implementation for Clojure? |
| 16:37 | rata_ | I don't understand why when I compile a file for the first time in swank, it goes smoothly, but when I compile it for the second time the test (is (expression? p)) fails, but nothing has changed |
| 16:41 | gfrlog | clojure conj featured muffins |
| 16:46 | technomancy | ivey: I must have missed running into you at the conj; how goes? |
| 16:46 | ivey | technomancy: nah i wasn't there, sadly. |
| 16:47 | ivey | it's going well. |
| 16:47 | ivey | how was it? |
| 16:52 | amalloy | afternoon, jackdempsey |
| 16:56 | FFUser | ok I have a problem here |
| 16:56 | FFUser | let's say you have a fn |
| 16:56 | FFUser | and you have this: (dotimes [num (count some-list)] |
| 16:56 | FFUser | (let [elem (some-list num)] |
| 16:57 | ivey | technomancy: i spent the conj fighting with google reader XML. working on a tool to fetch my starred items and send them to readitlater, but reader API is undocumented. |
| 16:57 | FFUser | (if (= (:name elem) the-search-string) elem nill) |
| 16:58 | FFUser | the problem here is of course that this doesn't make the function return the right element |
| 16:58 | FFUser | but just the result of the last if |
| 16:58 | FFUser | in other words how do I jump out of the loop and return the result |
| 16:58 | raek | I think you are reimplementing 'some'... :) |
| 16:59 | raek | or a more specialized variant of it |
| 16:59 | FFUser | doesn't some just return true/false? |
| 16:59 | MayDaniel | ,(some #{3} [1 2 3]) |
| 16:59 | clojurebot | 3 |
| 16:59 | rata_ | ,(doc some) |
| 16:59 | clojurebot | "([pred coll]); Returns the first logical true value of (pred x) for any x in coll, else nil. One common idiom is to use a set as pred, for example this will return :fred if :fred is in the sequence,... |
| 16:59 | qbg | ,(some #(= (:name %) "foo") [{:name "bar"} {:name "foo"}]) |
| 16:59 | clojurebot | true |
| 16:59 | FFUser | see? true / false |
| 17:00 | qbg | ,(some #(if (= (:name %) "foo") %) [{:name "bar"} {:name "foo"}]) |
| 17:00 | clojurebot | {:name "foo"} |
| 17:00 | FFUser | oh ok |
| 17:00 | FFUser | still in general |
| 17:00 | rata_ | is it possible that (class obj) returns x and (instance? x obj) return false? |
| 17:00 | FFUser | how do you deal with loops and lack of return / break statement? |
| 17:00 | amalloy | FFUser: can you make a gist or something? i can't quite follow what you're trying to ask |
| 17:01 | amalloy | FFUser: nm, i see it was answered already; i was stuck in some scrollback :P |
| 17:01 | qbg | FFUser: loop/recur would be primitives to use |
| 17:01 | raek | FFUser: loops return, unless you do a recur |
| 17:01 | FFUser | ok |
| 17:02 | FFUser | so basically if I want to end loop prematurely I can't use stuff like doseq and dotimes |
| 17:02 | qbg | Most functions that you would want are just a composition of some pre-existing ones though. |
| 17:02 | qbg | FFUser: Don't try to think in terms of loops |
| 17:02 | raek | FFUser: also, there is rarely any need to iterate over the indicies of the items and then get the item of that index |
| 17:02 | FFUser | ok but I need that |
| 17:02 | mrBliss | when you do (first (something-lazy ...)) it also ends prematurely |
| 17:03 | FFUser | I can find if item is in the coll (some) but I also need the index |
| 17:03 | FFUser | because I want to swap it |
| 17:03 | qbg | ,(first (filter #(= (:name %) "foo") [{:name "bar"} {:name "foo"}])) |
| 17:03 | clojurebot | {:name "foo"} |
| 17:03 | rata_ | FFUser, you need the function indexed and some |
| 17:04 | raek | FFUser: you happen to have the book "Programming Clojure"? it has an exmaple of just that |
| 17:04 | FFUser | I have a vector of maps and I want to update the map with :name = parameter |
| 17:04 | FFUser | basically replace it with a new map |
| 17:05 | raek | FFUser: ah, that chapter is available for free: http://media.pragprog.com/titles/shcloj/flow.pdf |
| 17:05 | qbg | FFUser: only the first one with (= :name parameter) or all of them? |
| 17:06 | FFUser | first one will suffice |
| 17:06 | raek | FFUser: 2.6 "Where's My for Loop", page 7 |
| 17:06 | raek | or 72, if you follow the books own page numbering |
| 17:06 | FFUser | I have Clojure in Action |
| 17:07 | rata_ | FFUser, (for [m maps] (assoc m :name parameter)) |
| 17:07 | raek | (defn indexed [coll] (map vector (iterate inc 0) coll)) |
| 17:07 | amalloy | or (map #(assoc % :name param) maps) |
| 17:08 | rata_ | for is lazy, so it doesn't matter whether you want the first one or everyone... it will do you just the work you need |
| 17:08 | rata_ | (map also) |
| 17:09 | qbg | (defn foo [pred f coll] (map #(if (pred %) (f %) %) coll)) |
| 17:09 | rata_ | is it possible that (class obj) returns x and (instance? x obj) return false? |
| 17:09 | qbg | Where pred is a predicate function for updating, and f is the update function (applies to all matches) |
| 17:10 | qbg | rata_: Do you have a case where that happens? |
| 17:10 | FFUser | :) |
| 17:10 | FFUser | I think I like the solution where you append indexes :) |
| 17:10 | FFUser | I better not time this solution though |
| 17:10 | FFUser | so many allocations it will make your head spin :D |
| 17:14 | amalloy | rata_: no, that should be impossible |
| 17:14 | qbg | (defn foo [x] (instance? (class x) x)) will throw a NullPointerException if you pass in nil though |
| 17:15 | rata_ | qbg, yes, but it's difficult to make a gist of that |
| 17:16 | qbg | Due you use classloaders? |
| 17:16 | rata_ | the most weird thing about it is that when I compile it for the first time it works perfectly |
| 17:18 | rata_ | I really don't get it... it seems to be a problem with swank |
| 17:18 | rata_ | maybe I use (ns ... (:use ...)) too much |
| 17:21 | rata_ | if I compile the file twice, the (instance? x obj) doesn't work anymore |
| 17:21 | rata_ | `_´ |
| 17:21 | qbg | What is x? |
| 17:22 | qbg | I suspect either x or obj are being redefined and the other isn't |
| 17:23 | Nafai | Are there any tools that use nREPL yet? It's an interesting looking project. |
| 17:23 | rata_ | x is Agent where Agent is (defrecord Agent [...]) |
| 17:24 | qbg | Reevaluating defrecord will replace the old class with the new one |
| 17:24 | qbg | (IIRC) |
| 17:25 | amalloy | qbg: that's correct |
| 17:25 | qbg | If obj isn't being redefined, that could be it |
| 17:26 | Sweetshark | Hi all, I want to call stuff in a clojure jar from Java. I created a jar in netbeans with enclojure and it compiles just fine. I added the jar file to the project where I want to use it from. I see the symbols and everything compiles fine. However, when I run it, the call fails. With a Java jar file it works fine the way I did it. Any hints? |
| 17:28 | qbg | Sweetshark: Are you using a class generated in Clojure from Java, or are going through clojure.lang.RT to invoke a function? |
| 17:30 | rata_ | qbg, and is there any way to make defrecord not to generate a new class when it already exists one? |
| 17:31 | Sweetshark | qbg: I tried both (I am now using RT). Right now I have a Java class in the clojure jar but it does not even get enter that (plain Java) method. Hang on, I have a suspicion ... |
| 17:33 | qbg | If you are going through RT, make sure the namespace has been required |
| 17:33 | Sweetshark | ... *puff* there goes my suspicion: no, that was not the problem ... |
| 17:34 | Sweetshark | qbg: How? Do you have a link? |
| 17:34 | qbg | I've only done this once, but I just invoked require from clojure.core |
| 17:34 | qbg | (probably a better way) |
| 17:36 | rata_ | is there any way to make defrecord not to generate a new class when it already exists one? |
| 17:36 | Sweetshark | well, I now have a plain java wrapper class in the clojure jar an call that ... should at least that always work? |
| 17:37 | FFUser | can someone tell me if I'm using clojurebox, where do I have to put my Irc.clj with namespace spur.irc to get it to load in repl with require spur.irc |
| 17:37 | amalloy | rata_: i don't think so. you could probably wrap the defrecord in a (when) of some kind that checks whether the class already exists? |
| 17:38 | amalloy | but then if you changed the field list, that would prevent it from getting updated on your next compile |
| 17:44 | amalloy | hey Raynes, wb. did you end up having pants leftover after the flight? :) |
| 17:44 | rata_ | amalloy, I prefer that it doesn't get updated than this annoying problem with its redefinition |
| 17:44 | Raynes | amalloy: I kept them all, actually. |
| 17:45 | amalloy | well done. i left you a present on sexpbot |
| 17:45 | Raynes | I'm sick as hell at the moment. |
| 17:45 | Raynes | I'll probably get to that tomorrow if I feel like it. |
| 17:45 | Raynes | Thanks. <3 |
| 17:45 | amalloy | aww |
| 17:47 | rata_ | I'm looking now for a function that check if a class is defined... I don't like try and catch :P |
| 17:52 | qbg | rata_: Reflection? |
| 17:52 | rdeshpande | howdy all |
| 17:54 | rata_ | qbg, do you know of a way to do it? |
| 17:54 | mister_roboto | rata_: what do you mean "defined"? if it's available on the classpath to be loaded? |
| 17:54 | rata_ | I was hoping java.lang.Class/forName could help, but it throws ClassNotFound |
| 17:54 | jackdempsey | amalloy: hey there, just got internet back |
| 17:54 | jackdempsey | how's it goin |
| 17:54 | rata_ | mister_roboto, if it's in the environment |
| 17:55 | mister_roboto | rata_: the JVM can't possibly tell you about classes that are not on the classpath since it doesn't magically know about them. The "environment" is the classpath |
| 17:56 | Sweetshark | qbg: got a bit further, however now i get an "Var clojure.core/refer is unbound" error. Any idea on how to fix that? |
| 17:56 | mister_roboto | rata_: i guess you could go around and open every jar you can find at the OS level and see if it contains the class :) |
| 17:56 | amalloy | jackdempsey: nothing special. i've been here since june, and this is the first time it's rained. need to buy an umbrella, i guess :P |
| 17:56 | rata_ | mister_roboto, after you do a (defrecord x ...), x is in the environment |
| 17:57 | jackdempsey | amalloy: wow ok. i was going to say, is it like this? feels like a light storm |
| 17:57 | mister_roboto | rata_: ah, ok. i thought you meant regular java classes from outside your program |
| 17:57 | rata_ | mister_roboto, no |
| 17:58 | rata_ | mister_roboto, that'd require some magic |
| 17:58 | mister_roboto | rata_: exactly :) aren't there namespace functions to search for such bindings? (clojure newbie here) |
| 17:59 | rata_ | mister_roboto, I hope so, but I don't know either |
| 18:00 | mister_roboto | rata_: does this help? http://stackoverflow.com/questions/2012651/clojure-namespace-method-to-see-defined-objects |
| 18:03 | rata_ | mister_roboto, no, that's only useful for vars, not for classes |
| 18:03 | rata_ | (i.e., records) |
| 18:05 | amalloy | rata_: you could check for the instance of the var you don't want redefined |
| 18:05 | amalloy | presumably if you don't want the class redefined it's because you have a var that's an instance of the old class already |
| 18:07 | rata_ | amalloy, I don't even understand why the var doesn't get updated when I compile it for the second time |
| 18:08 | rata_ | maybe :import should go before :use |
| 18:10 | rata_ | no, putting :import before :use doesn't help either |
| 18:12 | rata_ | :reload-all goes after :use? :import? :require? |
| 18:15 | Raynes | (:use my.stuff :reload-all) |
| 18:20 | rata_ | yes, it seems to work now with (:use ... :reload-all) :) the only negative side-effect it's that now takes ~20 secs to run the tests, because it has to recompile everything |
| 18:23 | FFUser | time |
| 18:23 | TheAnimal | FFUser: 25.10.2010 12:24:00 +0200 |
| 18:24 | FFUser | debugging clojure is challenging |
| 18:31 | zakwilson | I'm trying to upload files with compojure/ring. I'm not sure how to access the uploaded file (it appears to be a string containing the filename) |
| 18:33 | FFUser | can someone give me some pointers |
| 18:33 | FFUser | http://pastebin.com/YMSy62sZ |
| 18:34 | FFUser | I find myself losing track of what's a data structure and what's a function |
| 18:34 | FFUser | since it's all same nameing convention |
| 18:34 | rata_ | FFUser, are you using emacs? |
| 18:35 | FFUser | yep |
| 18:35 | rata_ | in which function do you have the problem? |
| 18:36 | FFUser | just general readability problem |
| 18:36 | FFUser | the code works fine |
| 18:36 | nickik | format your code write for one |
| 18:37 | FFUser | with java I usually keep things organised by splitting into classes |
| 18:37 | FFUser | and by limiting the number of public methods |
| 18:38 | FFUser | which limits the amount of way the classes can interact with each other |
| 18:38 | rata_ | in clojure you have namespace and private and public functions |
| 18:38 | FFUser | loose coupling |
| 18:39 | FFUser | in OOP you want the classes loosely coupled and I have to somehow make my clojure programs do the same |
| 18:40 | rata_ | yes, in dynamic languages you have loosely coupled objects by default (IIRC) |
| 18:40 | FFUser | not really |
| 18:40 | FFUser | it's a design thing |
| 18:40 | nickik | in clojure everything is loosly coupeld because every function (should) be indipendend |
| 18:40 | FFUser | one that my coworkers fail badly |
| 18:40 | amalloy | FFUser: not an answer to your actual question, but i notice you do the following a lot: (first (filter #(= (:name %)) coll)) |
| 18:40 | FFUser | that's not what loose coupling is |
| 18:40 | rata_ | FFUser, why? |
| 18:41 | rata_ | FFUser, what's loose coupling for you? |
| 18:41 | amalloy | this can be replaced with (some (comp #{target} :name)) |
| 18:41 | amalloy | (where target is the name you're looking for) |
| 18:42 | FFUser | in OOP it is when classes (larger unit of functionality than function) have limited number of |
| 18:42 | nickik | @amalloy wanted to say that to |
| 18:42 | nickik | *too |
| 18:42 | FFUser | exposed methods through which other classes can influence them |
| 18:42 | FFUser | in clojure every function can pretty much call any other function usually |
| 18:42 | rata_ | FFUser, that's not true if you use namespaces and private functions |
| 18:43 | nickik | define data and some functions on those data then put that stuff in a namespace and define some of the functions privat and some public |
| 18:43 | FFUser | thanks ammaloy |
| 18:43 | rata_ | also, you definition of loose coupling resembles more the one of encapsulation |
| 18:43 | nickik | true |
| 18:43 | FFUser | they are related concepts |
| 18:45 | nickik | just think of it like this in FP a Class is a namespace. Then you can define private and public functions with defn or defn-. Its the same as in java just without protected. |
| 18:46 | rata_ | FFUser, they don't seem to be related: http://en.wikipedia.org/wiki/Loose_coupling |
| 18:47 | FFUser | nickik: in that case I'd easily split my code into 4 namespaces with 3 functions each |
| 18:47 | rata_ | loose coupling is the use of interfaces in Java |
| 18:47 | nickik | i agree that the are related if you encapsulate a object the write way its easy to have loose coupling |
| 18:47 | FFUser | if you asked me to craft classes out of it |
| 18:48 | FFUser | yes that's what I meant |
| 18:49 | rata_ | FFUser, then do that if you want your code more organized |
| 18:49 | FFUser | seems like it |
| 18:49 | FFUser | I was also looking for some kind of coding convention |
| 18:49 | FFUser | like in C++ you have hungarian notation |
| 18:50 | mister_roboto | FFUser: Hungarian notation is for encoding types in the name. functions are just functions though |
| 18:50 | nickik | @FFUser that seams to be alot. namespaces a usually a little bigger for conventions you can look at http://www.assembla.com/wiki/show/clojure/Clojure_Library_Coding_Standards |
| 18:50 | zakwilson | Loose coupling means that if A doesn't need to know about B, it doesn't. How you communicate that in your code is up to you, though namespaces do provide a mechanism to make it easy. |
| 18:51 | FFUser | mister roboto: clojure doesn't have types but it has vars that are bound to data, vars bound to FNs and vars bound to mutables (atoms, refs) |
| 18:52 | zakwilson | Clojure has types. They're attached to the data, not the variable. |
| 18:52 | mister_roboto | zakwilson: loose coupling means something a bit stronger than that. it means that if A uses B, it doesn't depend on how B is implemented. i think that falls out of FP automatically if your function is referentially transparent |
| 18:52 | FFUser | it was my idea to make different name prefixes for these 3 kinds |
| 18:53 | nickik | i would do that look into :"Follow clojure.core's example for idiomatic names like pred and coll" in the document i linked |
| 18:54 | nickik | in general: functions should read like verbs and data should read like nouns |
| 18:54 | FFUser | yeah I use same thing in java |
| 18:55 | FFUser | sometimes these names can be hard to craft though |
| 18:55 | rata_ | mister_roboto, that isn't it... it that if A uses B, probably you mean that A uses an interface that have the methods you need |
| 18:55 | mister_roboto | FFUser: why would you need a special idiom for mutable var names when you already have to use a special form to access them? doesn't that tell you everything? |
| 18:55 | FFUser | making function name verb-like but not too vague often results in extremely long names :D |
| 18:56 | FFUser | it tells me everything when reading correct code |
| 18:56 | mister_roboto | rata_: the only reason interfaces enable loose coupling is BECAUSE they make it impossible to depend on the implementation |
| 18:56 | FFUser | the problem is forgetting to use the special form |
| 18:56 | FFUser | the compiler won't warn me |
| 18:57 | mister_roboto | rata_: the only visibility you have to the "used" class is the "protocol" |
| 18:57 | rata_ | yes, that is |
| 18:58 | rata_ | OOP is about procedural abstraction |
| 18:58 | mister_roboto | rata_: oops is about many things. encapsulation, data hiding, inheritance, locality of data and methods which operate on the data, etc |
| 18:59 | mister_roboto | s/oops/OOP/ |
| 18:59 | sexpbot | <mister_roboto> rata_: OOP is about many things. encapsulation, data hiding, inheritance, locality of data and methods which operate on the data, etc |
| 18:59 | rata_ | I think a good read about that is http://www.dcc.uchile.cl/~etanter/ooplai/adt-oo.html |
| 19:00 | rata_ | I don't think encapsulation, data hiding, inheritance and locality of data are much related to OOP in general... they are related to some kinds of OOP implementations |
| 19:01 | mister_roboto | rata_: http://en.wikipedia.org/wiki/Object-oriented_programming like I said, OOP is about many things. sure you can leave out the bits you don't want to talk about but they are still part of OOP |
| 19:01 | rata_ | FFUser, I think you'll enjoy this article (by Stuart Halloway): http://www.nofluffjuststuff.com/blog/stuart_halloway/2009/08/rifle_oriented_programming_with_clojure |
| 19:02 | nickik | the three thinks alan kay said are the base of OO are: Encapsulation, Subtype polymorphism, Object inheritance |
| 19:04 | FFUser | too bad people I work with only use Encapsulation and even that one badly |
| 19:04 | rata_ | nickik, then every language that's based on delegation instead of inheritance isn't object-oriented? |
| 19:04 | rata_ | I don't think so |
| 19:05 | nickik | no, I'm just pointing out what the original definition is. Today everthing is diffrent. |
| 19:06 | nickik | FP isn't the same as it was 40-50 ago. |
| 19:06 | FFUser | imagine a bunch of void return methods on a single class named "processSomething" with no arguments, which load stuff from DB and then mutate half a dozen huge java beans, some dealing with state (data) storage and some dealing with UI state |
| 19:06 | rata_ | nickik, thus I think the core of OOP is message passing and procedural abstraction |
| 19:06 | mister_roboto | rata_: i think the key thing is that some features of traditional OOP, like reuse through inheritance only, is bad. so delegation is preferred. however, even a modern OOP like java and .NET has inheritance. |
| 19:07 | rata_ | FFUser, that's gonna be difficult to test for sure |
| 19:07 | FFUser | I am tasked with adding functionality to such existing projects |
| 19:07 | nickik | thats the problem with descutions like this everybody means something else when he sais OO or FP |
| 19:07 | FFUser | I have absolutely no idea which beans any of these functions affects under which conditions |
| 19:08 | rata_ | mister_roboto, that's not modern OOP... also inheritance and classes is just one way to implement OOP |
| 19:08 | mister_roboto | FFUser: you mean like adding new functionality without changing the existing code? that kind of code isn't testable |
| 19:09 | FFUser | adding new business logic into existing UI |
| 19:09 | FFUser | well JSFs |
| 19:09 | FFUser | and I don't understand the business logic already implemented, it's domain specific and you need experts to make specifications |
| 19:09 | mister_roboto | rata_: what is a modern OOPL that you are talking about then that doesn't have inheritance, for example? |
| 19:10 | FFUser | anyway, clojure is like my vacation from work |
| 19:10 | FFUser | and work is my nightmare |
| 19:10 | mister_roboto | FFUser: that's a bad spot to be in, but all too common. can you modify the existing code to start injecting dependencies? |
| 19:10 | rata_ | JavaScript doesn't use inheritance... Scala uses inheritance and is more modern than Java or C# |
| 19:10 | FFUser | don't have enough hours allocated to refactor code |
| 19:11 | mister_roboto | rata_: javascript uses prototype based inheritance |
| 19:11 | FFUser | bonus points: people who did this call me an academic when I talk about OOP. Needless to say, none of them have an actual degree in CS |
| 19:12 | rata_ | mister_roboto, that's not inheritance, that's delegation |
| 19:13 | rata_ | this is an interesting topic, but I'm going now to eat something... see you later guys :) |
| 19:13 | mister_roboto | rata_: prototype inheritance is still reuse by depending on implementation of the prototype |
| 19:14 | mister_roboto | rata_: i suggest reading about javascript and inheritance |
| 19:14 | nickik | @FFUser i'm doing boring database IO with ASP classic thats no fun either |
| 19:15 | rata_ | one has to be cautious when reading about those topics... there's a lot of people (even academics) out there that mix up ADTs and objects |
| 19:15 | mister_roboto | FFUser: i know exactly the kind of code you're dealing with. if you can't refactor, at least try to write some good tests before modifying it |
| 19:15 | mister_roboto | FFUser: although it's damn hard to even test such code |
| 19:16 | mister_roboto | FFUser: everything is a giant integration test - can't tease apart the components in a big ball of mud |
| 19:16 | rata_ | if they confuse ADTs and objects, to mix up inheritance and delegation would be even easier |
| 19:17 | FFUser | I'm not optimistic about the future of dealing with other developers |
| 19:17 | nickik | so good night i have to get up early to do some more boring stuff at work :) |
| 19:18 | FFUser | in my coutry about 10% of developers have BS in CS, 45% have associate's degree(I think that's what it's called) in CS and 45% have high school education |
| 19:21 | mister_roboto | rata_: http://www.cs.rit.edu/~atk/JavaScript/manuals/jsobj/ javascript prototype inheritance is true inheritance. you aren't holding onto a prototype handle and delegating to it, unless you also count c++ vtables as holding on to ancestor references and doing delegation |
| 19:21 | FFUser | time |
| 19:21 | TheAnimal | FFUser: 25.10.2010 01:22:18 +0200 |
| 19:28 | mister_roboto | FFUser: and in every other country, more and more development is outsourced to countries with lots of degreed programmers who, unfortunately, just started programming professionally on the program you're giving them :) |
| 19:31 | FFUser | It's terrible here. And the CS faculty had 180 spots, 360 applicants and you needed to be a mixed C grade/D grade student to get in. |
| 19:31 | FFUser | a lot of them drop out and work as programmers |
| 19:32 | FFUser | now imagine dropouts who had high school math graded C work as programmers |
| 19:33 | FFUser | anyway, enough griping about the state od development around here |
| 19:33 | FFUser | good night |
| 20:03 | yayitswei | Is there a way to splice a list into arguments (what the splat operator in Ruby does) without using a macro? I'm trying to turn a list into arguments for recur. |
| 20:04 | amalloy | apply |
| 20:05 | amalloy | though i'm not sure that works for recur. recur is probably a special form |
| 20:05 | amalloy | ,(doc recur) |
| 20:05 | clojurebot | Gabh mo leithscéal? |
| 20:05 | yayitswei | it is a special form |
| 20:05 | yayitswei | so I don't think I can use apply |
| 20:05 | amalloy | no, you can't |
| 20:06 | jackdempsey | is it a variable list? can't destructure it |
| 20:06 | amalloy | i think the usual way to do this would be destructuring |
| 20:07 | amalloy | ,(loop [[a b] (range)] (if (= 10 a) b (recur (map + [a b])))) |
| 20:08 | clojurebot | Execution Timed Out |
| 20:08 | amalloy | er, that's not what i meant |
| 20:08 | amalloy | ,(loop [[a b] (range)] (if (= 10 a) b (recur (map inc [a b])))) |
| 20:08 | clojurebot | 11 |
| 20:10 | amalloy | yayitswei: does that help? |
| 20:10 | yayitswei | amalloy: still reading it :) |
| 20:13 | yayitswei | amalloy: what's the (range) for? |
| 20:13 | amalloy | just a convenient initial value for the loop |
| 20:13 | amalloy | sets a=0, b=1 |
| 20:14 | yayitswei | oh i see |
| 20:15 | yayitswei | so the recursive function should take one argument, a list, instead of arbitrarily many |
| 20:16 | amalloy | right |
| 20:16 | amalloy | and then pull apart the list however you want |
| 20:17 | yayitswei | amalloy: got it-- thanks! |
| 20:17 | amalloy | or, have your arbitrarily-many function public, internally implemented as a loop around a list |
| 20:17 | yayitswei | if I really wanted to make it a |
| 20:17 | yayitswei | oh yeah that's what i was just going to ask |
| 20:23 | rata_ | mister_roboto, I think that link shows how to simulate inheritance in javascript |
| 20:23 | rata_ | many features of class-based languages, such as inheritance, can be simulated in a delegation-based language |
| 20:24 | rata_ | http://en.wikipedia.org/wiki/Prototype-based_programming |
| 20:24 | mister_roboto | rata_: no, it shows how inheritance DOES work in Javascript. it's just showing how to you structure that sort of inheritance hierarchy, comparing Java to Javascript, where the first is class-based inheritance and the second is prototype-based inheritance |
| 20:24 | mister_roboto | rata_: that's just how it works. look up constructors and prototypes in javascript. that's what they are for |
| 20:25 | rata_ | mister_roboto, look at the prototype-based programming article in wikipedia |
| 20:26 | mister_roboto | reading |
| 20:28 | mister_roboto | rata_: ok, so i'll buy that it's an ambiguity :) it's not like typical delegation where you are explicitly delegating calls to some delegate, however. you only reference the prototype in javascript typically to set up the prototyype chain so this inheritance of behavior happens automatically when you construct an object |
| 20:29 | mister_roboto | rata_: the rest of the time you just use the instance directly. if you still want to call that delegation, it seems to me that it's j ust a non-useful blurring of concepts |
| 20:31 | rata_ | mister_roboto, that's why I said that use of prototypes is an emulation of inheritance :) |
| 20:31 | rata_ | also the OOPLAI book (a work in progress yet) explains the differences between class-based and prototype-based languages very well IMHO http://www.dcc.uchile.cl/~etanter/ooplai/ |
| 20:32 | rata_ | do you have read PLAI? |
| 20:32 | mister_roboto | rata_: ok ok, i see your point. if the language is hiding the "delegation" from you when you are accessing an instance behavior, it seems to me no different than c++ hiding it by internally accessing the vtable |
| 20:32 | mister_roboto | rata_: i mean insofar as discussing whether a language has "inheritance" proper |
| 20:33 | mister_roboto | rata_: it's just an implementation detail. to call it "emulated" doesn't enhance understanding of what it is or does |
| 20:34 | mister_roboto | rata_: what does inheritance mean if not having behavior and properties automatically propagate through the chain of dependent objects? |
| 20:34 | rata_ | it's not hiding the delegation at all... it's just using it to implement inheritance-like constructs |
| 20:35 | mister_roboto | rata_: when i call jsobject.someproperty, i don't know if it's a local or coming from the prototype |
| 20:35 | mister_roboto | rata_: that's not hiding it? |
| 20:35 | rata_ | that's not hiding it... that's how delegation works |
| 20:36 | rata_ | inheritance definition depends on classes |
| 20:36 | mister_roboto | or setting up the prototype chain |
| 20:36 | mister_roboto | my example... is that not hiding the delegation? |
| 20:36 | rata_ | yes, that's not hiding the delegation |
| 20:37 | mister_roboto | rata_: ok, then i guess we cannot agree on that point |
| 20:38 | rata_ | if object jsobject doesn't know how to interpret the message 'someproperty', then it's going to delegate that message to other object |
| 20:38 | rata_ | we can't agree on that point |
| 20:38 | mister_roboto | rata_: just like the c++ object delegates via the vtable. it's a language implementation detail of how to locate hte property |
| 20:38 | mister_roboto | i totally agree with what you just said |
| 20:39 | rata_ | the important difference between them is that delegation occurs between objects and inheritance happens between classes |
| 20:39 | rata_ | the vtable is an implementation detail |
| 20:47 | mister_roboto | this is actually kind of interesting because earlier you were claiming that inheritance isn't part of OOP but you seem to be saying that class-based OOP is actually the only way to do inheritance |
| 20:50 | rata_ | yes, I was saying inheritance isn't part of OOP, but part of class-based OOP |
| 20:52 | amalloy | ummmm, no offense guys, but could you take this discussion to #oop or something? i don't want to miss any clojure-related messages in the flood |
| 20:52 | mister_roboto | sorry amalloy, you're right |
| 20:52 | rata_ | sorry amalloy |
| 20:53 | ymasory | why is there no "lein run"? what am i missing? |
| 20:53 | mister_roboto | my final statement is only that i think it is pointless to draw a line between "true" and "emulated" inheritance. i will shut up now |
| 20:54 | amalloy | ymasory: how does lein know what function you want to run? or do you want it to start up a repl and then eval everything in your project, maybe? |
| 20:55 | rata_ | just-in-time for the clojure-related question :) |
| 20:55 | ymasory | amalloy: not sure if there's a dedicated start point in clojure. sbt runs the first main function it can find with the matching signature |
| 20:56 | ymasory | it seems like a pretty slow procedure to say lein repl and then type out a start point |
| 20:57 | amalloy | ymasory: you can specify the main function in project.clj, and then when you java -jar the result of lein jar, it should call that function |
| 20:57 | ymasory | thanks |
| 20:57 | raek | there is some feature to set the starting namespace. I do not know if that also automatically requires that namespace |
| 20:59 | Adamant | clojurebot: do you have a neural net processah lahk Ahnold? |
| 20:59 | clojurebot | Huh? |
| 20:59 | mister_roboto | amalloy: how does that work? does it put that function inside a main()? |
| 21:00 | amalloy | mister_roboto: every clojure function turns into a java class. i imagine it renames the main class's function main, and it certainly puts an entry in the jar manifest |
| 21:00 | raek | if you add :main your-namespace-here, the repl will start in that namespace |
| 21:01 | raek | ah, and there's also :repl-init-script |
| 21:02 | amalloy | raek: cool. does that affect swank too? |
| 21:03 | raek | no idea :) |
| 21:03 | mister_roboto | if I had to decide between using lein or cake, is there any clear advantages to choosing one? i haven't used them, only did some reading and they seem to do the same thing |
| 21:05 | rata_ | raek, where do you put that ":main your-ns"? |
| 21:05 | amalloy | mister_roboto: one nice feature of cake is that it will keep jvms running in the background to speed up launch time of all cake tasks |
| 21:05 | amalloy | otoh, if you're strapped for RAM, it's probably inconvenient to keep killing those |
| 21:06 | raek | ymasory: one common way seems to be to only have function and constant definitions at the top level of the source files. (i.e., when you load a file, the application doesn't start.) then, you provide a -main function to start your application. |
| 21:06 | raek | rata_: in your project.clj file |
| 21:07 | raek | but still, when launcing the repl you have to type stuff |
| 21:07 | mister_roboto | amalloy: so if you're not tight on RAM then cake has the lead :) |
| 21:07 | rata_ | raek, in (ns ...)? |
| 21:08 | amalloy | that's been my experience. but lein is a little older and more stable/tested. they also have incompatible plugin architectures, so if someone's written a lein plugin you really want... |
| 21:08 | amalloy | but for the most part they're compatible so it should be easy to switch if that happens |
| 21:08 | raek | rata_: I'm sorry... what in (ns ...)? |
| 21:08 | amalloy | rata_: no, in the project.clj file at the top level of your lein/cake project |
| 21:09 | rata_ | raek, that ":main your-ns" |
| 21:09 | rata_ | ah ok |
| 21:09 | rata_ | sorry |
| 21:09 | rata_ | read only the first msg |
| 21:11 | raek | ok, I can confirm that setting the main namespace will cause that namespace to be loaded when you start the repl |
| 21:12 | raek | so, you could see the main namespace as a startup script, if you want to |
| 21:34 | mister_roboto | how do i make an entity bean using cake? (kidding!) is it a fairly typical thing to use any old editor (emacs or whatever) to create the code and then use lein/cake to package it for release? |
| 21:34 | hiredman | yes |
| 21:36 | amalloy | mister_roboto: yep, pretty normal. CCW users might have their own thing, but a lot of us use emacs/cake |
| 21:37 | mister_roboto | amalloy: so far i only used CCW to build fairly small programs that i just ran at the repl by typing it in. i really need to go to the next step of having a full automated build process and i cake seems to be a very good choice |
| 21:38 | amalloy | it certainly is a good choice. but laurent might have something that integrates better with eclipse, i don't know |
| 21:39 | mister_roboto | amalloy: when i use CCW, i tpically just execute the clj file and leave the resulting repl running. then i've been copy/pasting new code down into the repl rather than killing it and re-running the script file(s). this sounds clumsier than emacs with its repl integration (Swank?) but i haven't tried that approach |
| 21:41 | hiredman | thats fine for dev |
| 21:41 | hiredman | but when you deploy you build a jar |
| 21:52 | mister_roboto | hiredman: right. i've been doing java development for too many years now :) |
| 21:53 | mister_roboto | hiredman: maven and ant before that. need something for clojure now and i guess it's gonna be cake |
| 21:59 | amalloy | mister_roboto: cake and lein are both built on top of maven |
| 22:00 | amalloy | eg, lein/cake pom creates a pom.xml file you can manage with maven if you prefer |
| 22:01 | mister_roboto | amalloy: that's good in that i'll understand what's going on underneath and i can point it to our in-house artifactory repo for the dependencies. however, i think all the management looks like it will be best done via project.clj |
| 22:11 | ymasory | why can't clojure put in the "recur" bit by itself? at least in some simple cases? |
| 22:16 | somnium | ymasory: there are a few threads on the mailing list about it. the principle reason seems to be that since it would only be possible in some cases, better to make it explicit everywhere. |
| 22:17 | somnium | ymasory: plus you can always use scheme :P |
| 22:19 | ymasory | gotcha. thanks. seemed a little funny in the simple cases |
| 22:22 | ymasory | can i get the previous line back in the repl? |
| 22:28 | mister_roboto | install rlwrap like here: http://programmingzen.com/2010/07/13/how-to-setup-clojure-from-scratch/ or use "cake repl" like here: http://github.com/ninjudd/cake |
| 22:29 | mister_roboto | ymasory: maybe there's an easier way but rlwrap worked well for me. a standalone repl is annoying without history |
| 22:33 | ymasory | no kidding, thanks |
| 22:35 | ymasory | while i'm at it. why doesn't clojure allow forward-references to functions? other lisps do |
| 22:38 | mister_roboto | ymasory: you mean like this or something else? http://en.wikibooks.org/wiki/Clojure_Programming/Concepts#Mutual_Recursion |
| 22:40 | somnium | ymasory: you can use declare for forward declarations |
| 22:41 | ymasory | somnium: do other lisps require forward declarations? |
| 22:41 | somnium | ymasory: I don't think so |
| 22:42 | somnium | I don't know how CL does it, but I do think R6RS scheme really got that part right (scoping of top levels) |
| 22:42 | somnium | still, adding (declare ...) isn't so painful |
| 22:45 | ymasory | painless as C :) |
| 22:49 | somnium | ymasory: aw, surely Clojure isn't in the same league as C in terms of inflicting pain on programmers :) |
| 23:36 | ymasory | what does the & mean in function signatures? |
| 23:37 | dsantiago | It means any number of additional arguments, which will all be put into the name given after the & as a list. |
| 23:38 | ymasory | ah thanks |