#clojure log - Jul 11 2014

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

0:03 trptcolin: https://groups.google.com/forum/#!topic/clojure/n25aZ5HA7hc/discussion

0:06 puredanger_: generally things like this are nice to fix but we tend to prioritize "things don't work as they should" over "does not reject bad input" or "asymmetries in the library". I know liras are not moving real fast right now - we've been prioritizing various feature-related efforts instead. I expect at some point to get back to focusing on moving existing tickets and patches forward more diligently.

0:07 as always, writing great tickets http://dev.clojure.org/display/community/Creating+Tickets and patches http://dev.clojure.org/display/community/Developing+Patches makes everything smoother

0:07 trptcolin: yep, 100% support :)

0:09 hiredman: puredanger_: so fixing aot compilation is high on the list then, since it destroys homes and eats children and small pets?

0:12 puredanger_: it is. it's also hard and complicated. are you talking about http://dev.clojure.org/jira/browse/CLJ-322 or something else?

0:14 hiredman: puredanger_: given how many things break given aot, I think the existing issues are sort of whack-a-mole

0:16 puredanger_: I know of a few specific issues. I need help with collating a more comprehensive set of issues on the design wiki, and assessing their importance and how to address them.

0:20 here's the list tagged in jira currently: http://dev.clojure.org/jira/secure/IssueNavigator.jspa?reset=true&jqlQuery=project+%3Dclj+and+labels+%3D+aot+and+status+in+%28+open%2C+%22in+progress%22%2C+reopened%29

0:23 CLJ-1241 is screened and waiting for Rich. CLJ-1330 is on the work list for 1.7 and needs more evaluation. A couple others are in various stages of the pipeline.

0:23 I have no idea how to prioritize those though or what's NOT in that list

0:34 jephree: does anyone know if its possible to change both variable delimiters "{{" in selmar?

0:35 puredanger_: hiredman: I made a page with those here http://dev.clojure.org/display/design/AOT+Problem+Overview - please add more info

1:32 abaranosky: what's the new hotness these days?

1:51 cespare|home: Does clojure.walk/macroexpand-all not handle macros that use &env?

1:51 and is there an alternative that does?

1:59 hiredman: cespare|home: it depends a lot on what the macros do with &env

2:00 &env can leak compiler internals, which if a macro uses, it is going to be really hard to provide via some other macro expander

2:00 lazybot: java.lang.RuntimeException: Unable to resolve symbol: env in this context

2:07 ddellacosta_: ,(println "test")

2:07 clojurebot: test\n

2:07 ddellacosta: ,(println "test")

2:07 clojurebot: eval service is offline

2:07 ddellacosta: hiredman: testing ignore list status. can you enable clojurebot for me? thanks

2:08 \nick ddellacosta_

2:08 d'oh

2:08 ddellacosta_: hiredman: testing ignore list status. can you enable clojurebot for me? thanks

2:10 well, lovely to be dealing with adults here

2:15 cespare|home: hiredman: my macro is only looking at the keys in &env (checking the type tags)

2:56 hhenkel: Good morning all...I'm still haveing an issue using jolokia-client-java within clojure. I tried to reproduce the issue from java but there it seems to work.

2:57 I created an easy to follow clojure "test-case" and also added the java stuff here: https://www.refheap.com/88077

2:57 Anyone able to tell me what is the difference between the clojure stuff and the java stuff?

2:58 For reference this is (in my understanding) the relevant class that is used for the execute part: https://www.refheap.com/88049

4:54 mnngfltg: Is there something like "partial" that applies the argument to the end (rather than the beginning) of arg list of the target function?

4:56 Basically, I want to turn a fn with optional arguments into a predicate (that takes only one argument).

4:57 hyPiRion: mnngfltg: sounds like you can just use anonymous functions then

4:58 ,(let [f #(- % 1)] (f 10))

4:58 clojurebot: 9

5:06 mnngfltg: hyPiRion, true; I was just wondering if there's an equivalent of `partial` for that

5:07 hyPiRion: mnngfltg: not that I know of, unfortunately.

5:30 swi: Hello. I'm new to clojure so excuse me for maybe stupid question. I can't figure out perfectly what the 'real-world-usage' of (delay)? I understand that it define some function but not execute it before we (force) it to get answer, and then it cache answer. But, in that way, this function have only one returned value for whole tim eprogram is running. What the meaning than ?

5:32 hyPiRion: swi: One immediate example I can give you is how Leiningen works: We do it to delay loading of files from startup until we really need them. If we don't need them, we don't have to load them, and we save time.

5:34 swi: hyPiRion: so it' realy one-time function in program life cycle?

5:37 hyPiRion: swi: Right, it's an expression which is only performed once, and only the first time you need the value it returns.

5:44 mnngfltg: hyPiRion, thanks, I'll use #(apply ...) then

5:47 hyPiRion: mnngfltg: yeah, if you want something general, I'd suspect that's the easiest

5:48 mnngfltg: hyPiRion, that seems to work: (defn partial-opt [f & more] (fn [x] (apply f x more)))

5:50 hyPiRion: mnngfltg: yeah, looks good if you only need to support single argument functions.

5:51 mnngfltg: hyPiRion, yes, I want to generate predicates, for use with (some-fn)

5:53 hyPiRion: right

5:55 mnngfltg: being net to clojure (or functional programming) I have to say I'm enjoying working with higher order functions immensely :)

6:00 hyPiRion: Yeah, it's a nice change from imperative languages. Really good for your brain with a bit of variation =)

6:08 Glenjamin: i've been trying to write clojure in javascript lately, its much more clunky :(

6:08 it's amazing how much of a difference being able to use keywords as functions makes

6:11 gfixler: ,(:indeed {:indeed :truedat})

6:11 clojurebot: :truedat

6:13 swi: hyPiRion: Thanks :)

6:16 hhenkel: I'll poll once again....anyone able to explain what goes wrong here: https://www.refheap.com/88077 ?

6:20 pyrtsa: hhenkel: Wild guess, (.execute client [HeapMemoryUsage PeakThreadCount]) should be (.execute client HeapMemoryUsage PeakThreadCount)?

6:21 vijaykiran: hhenkel: did you see my message yesterday about it not working either in Java Program ?

6:22 hhenkel: pyrtsa: Constructor is: J4pReadRequest(String pObjectName, String... pAttribute)

6:22 vijaykiran: Yes, I did also added working code at the refheap stuff.

6:23 vijaykiran: Did not see you comming back online.

6:23 vijaykiran: hhenkel: oh - sorry. I didn't see the channel log yet

6:23 hhenkel: vijaykiran: https://www.refheap.com/88077

6:24 pyrtsa: Also as shown in the link the requests are working for a single execute.

6:24 pyrtsa: hhenkel: You have `client.execute(req1,req2);` in the Java counterpart. That translates to (.execute client req1 req2), not (.execute client [req1 req2])

6:26 hhenkel: pyrtsa: I'll give it a try. The source for the execute is here: https://www.refheap.com/88049 L180

6:26 Calls L196 afterwards

6:27 pyrtsa: I get a IllegalArgumentException No matching method found: execute for class org.jolokia.client.J4pClient clojure.lang.Reflector.invokeMatchingMethod (Reflector.java:80)

6:28 pyrtsa: So many overloads... which one are you trying to call? Maybe adding the correct type hint might help the Clojure compiler choose the right one.

6:29 I don't have many more ideas to help.

6:29 hhenkel: pyrtsa: The trace shows: at org.jolokia.client.J4pClient.execute(J4pClient.java:182)

6:32 vijaykiran: hhenkel: strange - I get exception with your Java class too

6:35 hhenkel: vijaykiran: What kind of exception? You wrote about https status 302...

6:35 imho this is for a redirection

6:35 vijaykiran: hhenkel: https://gist.github.com/vijaykiran/f8ff6636d4ec84fd0c60

6:36 hhenkel: yes, 302 is for redirect - I was tracing through the code and somewhere there was a 302 when I tried last time

6:36 hhenkel: https://gist.github.com/vijaykiran/2397f3a004206031a57f this is what I tried yesterday

6:39 hhenkel: vijaykiran: That's strange...

6:40 vijaykiran: I started adding some output to the jolokia-client-java to see if stuff is passed allong correct.

6:40 vijaykiran: hhenkel: see the comment on the gist for 302

6:41 hhenkel: vijaykiran: So far I see that the requests reach the L199 in https://www.refheap.com/88049 in the list.

6:42 vijaykiran: The 302 was in the jetty log?

6:42 vijaykiran: hhenkel: can you try with http://localhost:8080/Jolokia/ as url ?

6:42 hhenkel: damn - that's the problem

6:43 hhenkel: vijaykiran: Hmm?

6:44 vijaykiran: hhenkel: one sec

6:46 hhenkel: https://gist.github.com/vijaykiran/936752f6ba00f19252bc << fixed

6:50 hhenkel: vijaykiran: hmm, I'm trying but something is wrong...

6:53 vijaykiran: hhenkel: well - this https://gist.github.com/vijaykiran/af2e46da2c178831bf26 works for me, as expected

6:58 hhenkel: vijaykiran: Yes, I got it working as well...I'm currently trying to understand why...?

6:59 vijaykiran: hhenkel: well - without / there's a redirect to / - which returns 302 and the JSON Parser inside jolokia-client chokes on that

7:00 hhenkel: vijaykiran: aaarrrgghhhh.

7:01 vijaykiran: hhenkel: looks like .execute(1-req) and .execute(req1 ...) follow different code paths

7:01 hhenkel: anyway - that's an exercise for you ;)

7:01 hhenkel: vijaykiran: Thank you very much for your time and help!

7:03 vijaykiran: hhenkel: yw

7:04 hhenkel: you should probably ask the jolokia guys for more detailed error message or file a bug, perhaps

7:07 hhenkel: vijaykiran: Yes, that might be a good idea, hopefully one out of the 10 people ideling in the channel will wake up...

7:13 vijaykiran: I'm testing that currently against a weblogic server now and I got more strange behaviour...

7:17 vijaykiran: https://www.refheap.com/88082

7:21 vijaykiran: hhenkel: so if you don't have first two printlns - it fails ?

7:21 hhenkel: vijaykiran: correct...

7:22 vijaykiran: One execute is enough to have it working...

7:22 vijaykiran: hhenkel: hmm - that's strange indeed.

7:23 hhenkel: I don't have weblogic installed for trying out though

7:24 hhenkel: vijaykiran: One thing that is different is the version of the jolokia on the weblogic

7:24 Maybe something is broken in the old version on the weblogic.

7:25 I will try to update that first.

7:25 vijaykiran: hhenkel: could be

7:29 mbac: so, sticking, say, 15 million integers into a sequence OOMs my laptop pretty quickly

7:30 should i expect this to be efficient or do i need to make an actual array if i want this to not eat 500MB of RAM?

7:35 dhruvasagar: Hi guys, has anybody used apache spark with clojure ?

7:37 vijaykiran: mbac: do you really need all of them in memory ?

8:22 Glenjamin: mbac: how much memory do you have? i've had more than that in memory without issues before

8:23 generally if you have that much data in memory you've chosen to trade memory use for cpu time :)

8:52 rritoch: Hi, does leiningen provide a way to deploy to a maven branch? I've been using lein deploy releases and lein deploy snapshots which are configured in the project.clj :repositories but I don't see any place to specify a branch name.

8:57 stuartsierra: rritoch: I don't think Maven has a notion of "branch" names. Do you mean a "qualifier"?

8:57 rritoch: stuartsierra: I'm referring to the releases:branch plugin

8:58 http://maven.apache.org/maven-release/maven-release-plugin/examples/branch.html

8:58 stuartsierra: rritoch: oh, no idea then, sorry

8:58 rritoch: stuartsierra: I've also seen this "qualifier", is that functionally similar to a branch?

8:59 stuartsierra: rritoch: No, "qualifier" is just an extra identifier that gets tacked on to the Maven groupId / artifactId / version.

8:59 rritoch: I'm working on a project that's using git for source control and maven for binary releases and it would be bad if releases on the branch conflict with releases from the master.

9:01 stuartsierra: rritoch: You may want to try asking in #leiningen later today when the U.S. West Coast comes online :)

9:01 rritoch: stuartsierra: Thanks, I didn't know they had their own channel

9:01 stuartsierra: the line between leiningen and clojure is fairly blurry

9:03 stuartsierra: rritoch: It's quite clear, really. Clojure is the language, maintained by Rich Hickey and contributors under the contributor agreement. Leiningen is a project management tool, maintained by Phil Hagelberg on GitHub.

9:04 TimMc: ...and contributors. Phil quite encourages that.

9:07 rritoch: stuartsierra: Thanks for the clairification, though I've never tried running any clojure applications on anything other than leiningen.

9:08 whodidthis: i heard its possibl to create jar out of a clojure application and run it on java runtime environment

9:08 TimMc: rritoch: All lein does is set up classpaths, really.

9:08 mbac: Glenjamin,

9:08 vijaykiran,

9:09 ToxicFrog: whodidthis: yes. You probably want the 'lein uberjar' command?

9:09 mbac: the question is, should clojure be able to represent 15 million integers in less than 500M of heap

9:10 vijaykiran: mbac: http://www.javamex.com/tutorials/memory/object_memory_usage.shtml should answer your question

9:10 mbac: of course i can tweak the dynamic with time-space tradeoffs, but i'm surprised that i seem to OOM when i try to force a 15 million int sequence

9:10 so i wonder if i'm doing something horrible, like using a non-tail recursive algorithm

9:11 Glenjamin: lazy sequences are relatively expensive memory-wise

9:11 as theres a lot of intermediate computations that are wrapped in an object

9:12 you can use reducers to optimise object allocation, which reduces memory footprint and increases throughput

9:13 TimMc: rritoch: If you wanted, you could bundle your .clj files up into a zip file (renamed with a .jar extension, perhaps) and run java -cp your-stuff.jar:clojure.jar:etc clojure.main -e '(require 'your.ns) (your.ns/-main)' or something like that.

9:13 But why would you? :-)

9:14 mbac: yeah, i might just stuff them all into an array and resign myself to unsexy imperative loops

9:14 :'(

9:15 TimMc: rritoch: Actual example I just tried, using `lein cp` to build the classpath for me: java -cp `lein cp` clojure.main -e "(require 'adhoc.core) (adhoc.core/-main)"

9:17 (And I'm wrong about needing to jar up the files; they can just live in an unpacked source directory.)

9:20 Glenjamin: mbac: have a look at core.reducers, you may find this is sufficient

9:20 rritoch: TimMc: So leiningen also handles all dependency loading? I'm looking at the output of lein CP and most of them are pointing to my ~/.m2 folder

9:20 mbac: hmm

9:20 will do

9:28 stuartsierra: TimMc: `java … clojure.main -m adhoc.core` will also work.

9:29 mbac: Glenjamin, it's not clear to me from the description that reducers should be more space efficient

9:37 Glenjamin: mbac: if you are using lazy sequences, they will be

9:37 the storage-at-rest is unchanged though

9:47 mbac: if i do [lein repl] and then (def x (doall (take 12345678 (range)))) my heap hits 1G and i get java.lang.OutOfMemoryError: GC overhead limit exceeded

9:48 so, you contend something like doall with reducers would make that not happen?

9:50 stuartsierra: `doall` forces the entire sequence to be realized in memory.

9:50 mbac: agree

9:50 i don't understand why 12345678 numbers should consume 1G of memory

9:50 Glenjamin: if you do (into [] (take 12345678 (range)) what do you get?

9:52 stuartsierra: mbac: A couple of reasons. A realized sequence will be stored in something like a linked list. And because generic containers in Java can't hold primitive numbers, each number has to be boxed in a Java Object.

9:53 mbac: no doubt

9:54 but if you could represent each number in 8 bytes, that implies 10x overhead per number to stick it into a sequence

9:55 stuartsierra: A Java Object is around 17 bytes of overhead, at least. Integers in Clojure are Longs, so that's 8 bytes per number. That's over 300 MB right there. Add in the sequence overhead, heap fragmentation, and the extra space Java needs in the heap for GC regions, you could get to 1 GB pretty easily.

9:55 mbac: yikes. welp, that explains it.

9:56 so i guess i do want to stuff these into an array

9:57 Glenjamin: if you can avoid realising the whole sequence at once you'd be ok too

9:57 what is it you're building?

9:58 stuartsierra: mbac: Yes. You could also check out primitive vectors (`vector-of`).

9:58 mbac: i'm comparing mp3s

9:59 and the compare involves several passes. i could conceivably re-arrange things to make it one pass but, if that's not as sexy

10:00 and if it won't be sexy i may as well just stuff them into an array

10:00 stuartsierra: mbac: You may be interested in https://github.com/candera/dynne as a source of examples for handling audio data in Clojure.

10:01 mbac: sweet, thank you!

10:02 stuartsierra, btw, glad to run into you again! we met once at your lisp-nyc presentation in 2009 on implementing altlaw.org :)

10:02 stuartsierra: mbac: Oh wow, that takes me back. :)

10:05 mbac: i had the (somewhat trolly) question about when will clojure get monads because monads are like the haskell programmer's version of blub paradox vs lisp

10:05 ;)

10:08 hhenkel: vijaykiran: I updated the jolokia version on weblogic but I'm still failing. :(

10:13 vijaykiran: I sniffed with wireshark and I see that if I request a single value that there is a jsessionid in the post (multiple requests).

10:14 vijaykiran: hhenkel: are the versions in sync ? May be debugging and stepping through will help (?)

10:14 hhenkel: If I only do a post I see the request to authenticate, then I see the reply only containing auth data but no request data.

10:15 TimMc: stuartsierra: Yeah, but I think lein actually uses -e since the main ns may not be AOT'd.

10:15 hhenkel: Yes, the versions are both 1.2.2

10:15 TimMc: Just demo'ing that it's totally doable by hand.

10:15 vijaykiran: hhenkel: difficult to guess what's wrong without installing Weblogic for me .. I think :(

10:16 hhenkel: vijaykiran: Yes, I guess so.

10:16 stuartsierra: TimMc: `clojure.main -m` doesn't require the main ns to be AOT-compiled either.

10:16 hhenkel: vijaykiran: I could try and deploy without the need to authenticate I guess.

10:17 TimMc: stuartsierra: Oh! Point.

10:17 vijaykiran: hhenkel: hmm yeah - that's a good point

10:17 stuartsierra: I forget when that was added, maybe 1.3 or 1.4.

10:19 TimMc: rritoch: Yes, lein also pulls down the dependencies that you specify in your project.clj (which is a lein-specific file).

10:20 I think you could write a fairly small Makefile to capture the core leiningen functionality (although that would be a bad idea.)

10:24 hhenkel: vijaykiran: Okay, looks like there is an issue with the authentication.

10:25 vijaykiran: Or to be more precise there seems to be an issue with auth and post requests.

10:26 vijaykiran: hhenkel: ok - perhaps time to poke jolokia channel - looks like this is slightly OT for this channel :)

10:29 hhenkel: vijaykiran: I guess I found the problem...

10:31 vijaykiran: For the auth stuff to work I need to add the org.jolokia.client.BasicAuthenticator to the ClientBuilder.

10:32 vijaykiran: It looks like everything is fine now.

10:32 vijaykiran: hhenkel: cool :) but what exactly are you trying to build ?

10:32 hhenkel: analytics ? monitoring

10:36 hhenkel: vijaykiran: JVM Montitoring - more or less

10:36 vijaykiran: We got around 80 JVMs running weblogic + around 140 - 180 other jvms

10:37 vijaykiran: I want to have some base line data of different values and jolokia got the ability to run within every jvm.

10:38 I allready got a script fetching data from jolokia, but not with the official java client jar ( the one that drove me nuts).

10:39 Current PoC is to fetch data from jolokia, transform it and send it to riemann.

10:39 From there it is send to graphite at the moment with grafana as a frontend.

10:40 I also got a implementation of a zabbix connector to send data there.

10:40 vijaykiran: that's the main idea.

10:41 vijaykiran: hhenkel: sounds like fun - jolokia seems to have "REST" like api - why not just use the normal httpclient with JSON payloads ?

10:42 hhenkel: vijaykiran: Yes, it is quite easy to get data out of it. Idea to switch to the jolokia client was, that they add features from time to time.

10:43 And instead of reinventing the wheel over and over it might be easier just to use their jar.

10:44 For example with java 1.7.06 or something oracle added the possibility to subscribe to gc events

10:44 vijaykiran: hhenkel: ah - that makes sense

10:44 hhenkel: One of the big planned features of jolokia 2.0 is to provide subscription via websockets

10:45 vijaykiran: hhenkel: hmm - nice, then you can build a direct UI on top of it then

10:45 hhenkel: So it would be much easier to get notified of events instead of pulling.

10:46 vijaykiran: Yes, some people use it with javascript: http://www.nurkiewicz.com/2011/03/jolokia-highcharts-jmx-for-human-beings.html

10:46 But I want to have historical data so that I'm able to see what the values looked alike in the paste

10:46 s/paste/past

10:47 jjwatt: does anyone have a good core.async example for writing to a file from a channel? I have it working with blocking takes in a loop, but that's probably just one little record off my channel at a time. I'd kind of like to build up a buffer and blast everything from that buffer to a file every so often.

10:47 hhenkel: That's the reason why I want to go with riemann (different backends / alarming / etc) and something like grahpite + grafana

10:48 vijaykiran: hhenkel: okay - I'm working on a system which emits events as well - but we are using ELK (ElasticSearch/Logstash/Kibana) for visualizing the events

10:49 hhenkel: vijaykiran: What kind of events? Only log data or jmx values as well? I would love to play around with it but we allready got splunk in place...

10:51 vijaykiran: Ah, you also joined #jolokia... :) There is not much happening there...from time to time rhuss joins he is the main dev behind it.

10:52 vijaykiran: hhenkel: the events are logged by different components - we log them as JSON and push to logstash

10:52 hhenkel: or logstash "tails" them rather

10:53 hhenkel: it is more of a BI dashboard for users

10:56 hhenkel: vijaykiran: That also sound interessting. Mine is more for devs + ops people - maybe somtime in the future we got some monitor showing stuff

10:57 vijaykiran: I gotta leave...friday evening...I should not stay to long in the office. :)

10:57 vijaykiran: Thanks again for your help.

10:57 vijaykiran: hhenkel: :) ok - have fun

11:26 mnngfltg: I seem to remember reading somewhere that I should only "memoize" pure functions. But now I'm wondering if that makes any sense at all.

11:27 justin_smith: mnngfltg: if what makes any sense?

11:27 dnolen_: mnngfltg: that is correct

11:27 justin_smith: mnngfltg: what happens if you memoize a call to println?

11:28 mnngfltg: justin_smith, yes of course, the second call won't print anything

11:28 justin_smith, but how about caching database queries?

11:28 justin_smith: that's because println is impure

11:28 is your db immutible?

11:28 if not, it is impure

11:28 mnngfltg: no, it's nut immutable

11:29 not :)

11:29 justin_smith: select from users limit 1 order by last_visited

11:29 mnngfltg: but I still might want to cache DB queries for some time, might I not?

11:29 justin_smith: clearly I would not want to cache that

11:29 Glenjamin: if your DB connection can fail, it is impure :)

11:29 justin_smith: there is that too

11:30 mnngfltg: Glenjamin, ah... good point

11:30 Glenjamin: i would say you can't safely memoize an impure function

11:30 but you can cache it sensibly, which amounts to about the same thing

11:30 justin_smith: mnngfltg: you can't just cache results - you would need some logic that decides which results are cachible, and likely some logic to clear caches under specific conditions. I work on a project where we do things like that, but it is error prone and not just a question of using memoize.

11:30 dnolen_: mnngfltg: the main takeaway you don't want to use standard lib `memoize` for that - you need caching far more fine grained

11:31 mnngfltg: okay, so I'll have to write my own caching function (say, by storing it in an atom)

11:31 dnolen_: `memoize` is for pure functions - nothing else to know

11:31 mnngfltg: how about core.cache then?

11:32 Glenjamin: core.cache is probably reasonable

11:33 mnngfltg: ok

11:33 memoization is only useful for caching expensive computations then, not for expensive I/O

11:34 justin_smith: mnngfltg: core.cached has other cachine variants

11:34 mnngfltg: justin_smith, you're right of course, but often very simple caching behavior is enough

11:36 justin_smith, I'll look into it, thanks (and thanks to everyone else)

11:37 arrdem: justin_smith: you did see the core.cache race condition thread on clj-dev, right?

11:38 justin_smith: oh, no I didn't

11:39 arrdem: justin_smith: nevermind me I'm just a stormcrow. that was a core.memoize issue not a core.cache issue

11:40 justin_smith: https://github.com/clojure/core.cache link btw

11:42 mnngfltg: arrdem, looks like it was fixed: http://dev.clojure.org/jira/browse/CMEMOIZE-5

11:43 arrdem: mnngfltg: http://dev.clojure.org/jira/browse/CMEMOIZE-15 is the active one it seems

12:26 daniel__: [

12:26 sry

12:26 trptcolin: ]

12:26 daniel__: :)

12:27 trptcolin: whew that was close

12:28 pedrosantos: quit

12:42 daniel__: whats the idiomatic way to check if a string is in another string (case insensitive)?

12:42 filter re-matches?

12:43 arrdem: (fn [x y] (= (clojure.string/lower x) (clojure.string/lower y))) ?

12:44 daniel__: arrdem: not =, if its a substring

12:44 * arrdem missed "is in"

12:47 arrdem: daniel__: I'd do a string lower on both and then use re-matches. no need to filter.

12:48 daniel__: remember to use re-pattern to get a regex from a string.

12:48 daniel__: i have a vector and want to filter it for maps with a certain matching property

12:49 anyway, thanks arrdem, think i got it

13:00 bryanmaass: I dropped off after that funcgo page was posted last night.

13:01 https://github.com/eobrain/funcgo#using-vectors

13:01 “Getting cleaner syntax using infix notation” with +, maybe I get it.. but with into? really?

13:03 bbloom: bryanmaass: especially because "into" reads backwards

13:04 jfcaron: Is there a general consensus on the best Clojure book for someone new to lispy and functional languages, but not new to programming in other languages like C++ and Python?

13:04 I'm interested in learning clojure for hobby video game making.

13:06 Shayanjm: jfcaron: I'm learning as well, and Clojure for the brave & true was a nice introductory book

13:08 jfcaron: Oh, and it assumes emacs too. I guess that should be expected for a lispy language?

13:08 Thanks Shayanjm, I'll look into it.

13:08 Shayanjm: jfcaron: clojure for the brave & true doesn't assume it

13:08 and I actually don't use emacs. I use st3

13:08 aperiodic: jfcaron: take a look at the foreword of Joy of Clojure and see if it appeals to you: http://joyofclojure.com/foreword/index.html

13:09 I really enjoyed the book, but I also picked it up after a few months of playing with clojure

13:12 bryanmaass: Shayanjm: how is your experience with clojure in st3? I used st3 when picking up clojure before packing up shop and learning emacs.

13:12 Shayanjm: fine-ish

13:12 The tools haven't really matured to the level necessary for long term work I imagine

13:12 things like SublimeREPL are fine for small testing, but if you need features like nREPL that works with the latest lein you're out of luck

13:13 but the added benefit: I don't have to deal with reconfiguring another editor/relearning hotkeys

13:13 bryanmaass: Yeah, emacs is a beast imho

13:13 Shayanjm: yeah I imagine if I started out using emacs for everything

13:13 life would've been much simpler

13:13 bryanmaass: learning it was its own paralell struggle.

13:13 agree, Shayanjm

13:13 Shayanjm: but tbh, I'm fine with SublimeREPL for now

13:14 if i need nREPL to connect to a running instance, I just pull up a terminal window next to my code

13:14 ofc I lose the ability to hotkey my code into the window

13:14 but what're you going to do

13:14 Frozenlock: nrepl in the terminal :-/

13:14 Shayanjm: Yeah I know Frozenlock :\

13:14 Frozenlock: Emacs is absolutely worth it.

13:14 bryanmaass: I’d agree Frozenlock

13:14 Shayanjm: I can see that

13:14 but I don't think i'm ready to part with ST3 yet

13:15 bryanmaass: Sad that there’s not a super awesome guide to picking it up, that i’m aware of.

13:15 Frozenlock: Programming languages come and go, but Emacs remains.

13:15 Shayanjm: I'll probably end up learning emacs down the road

13:15 but as of right now: I don't have a big enough push to really dive in

13:15 arrdem: Frozenlock speaks the truth

13:15 Shayanjm: also good news lol - I think I have access to a super computer so I can keep developing this thing lol

13:15 arrdem: Shayanjm: which one? (TACC user)

13:16 Shayanjm: arrdem: TACC. I'm a UT student so apparently I need to get a faculty member to sponsor me

13:16 duck1123: Now that it's so easy to include packages, Emacs is so much easier than when I first started learning it

13:16 Shayanjm: Trying to get access to stampede

13:16 arrdem: Shayanjm: YISSSSSS

13:16 bryanmaass: duck1123: what do you mean?

13:16 duck1123: I first started learning emacs before elpa was a thing

13:17 arrdem: Shayanjm: what are you working on?

13:17 bryanmaass: duck1123 wow, I see.

13:17 Shayanjm: NLP stuff with articles, arrdem

13:17 basically a really intelligent news reader

13:17 extracts topics/keywords from article contents, sentiment analysis, etc.

13:18 then builds categories around live-news which are (or will be?) subscribable

13:18 bryanmaass: Shayanjm: do you work at prismatic? :P

13:18 arrdem: Shayanjm: cool! lemme know what your experience running Clojure on Stampeed's like. I'm on the UT-SCC team so most of what I get to run on Stampeed or our cluster is fortran stuff not my own code.

13:18 Shayanjm: bryanmaass: haha no but interestingly enough I had a meeting with someone two days ago who knows the founder

13:19 arrdem: Shayanjm: I've been threatening to build some really resource intensive Clojure program just so I can say I threw Stampeed at Clojure for a while tho :D

13:19 Shayanjm: hahahaha arrdem: "Chris" @ TACC just got back with me saying I need to find a professor whose research will benefit from the work I'm doing

13:20 and definitely will let you know arrdem. I'm still trying to figure out approximately what resource I'm going to need

13:20 arrdem: Shayanjm: odds are you can just abuse condor for what you're working on. TACC is really tight fisted with Stampeed access and billing.

13:20 Shayanjm: I assume you have a UTCS account.

13:20 Shayanjm: arrdem: what's the difference between condor & stampeed

13:20 I do, but I'm a EE student

13:20 took a CS class for shits

13:20 arrdem: Shayanjm: heathen.

13:21 Shayanjm: heh heh heh

13:21 secret agent

13:21 arrdem: Shayanjm: Condor runs on the CS lab boxes. Stampeed has its own cluster of such amaze wow very seekret up to date l8est from intel hardware

13:21 Shayanjm: Yeah so as of this moment: I'm like maxing my MBP

13:22 and I haven't even scaled functionality to user-level yet

13:22 so I'm going to have to figure out some new development cycle for building this thing locally and live-testing it elsewhere

13:22 which I suppose would be my big push to get a better nREPL workflow going...

13:23 arrdem: eh... have you hit a wall where your dev box can't handle the app anymore?

13:23 Shayanjm: yep

13:23 arrdem: or do you just have a friggin enormous dataset.

13:23 Shayanjm: Actually I'm running against a neural net

13:23 so the data set is just realtime streamed data, nothing persisted

13:23 it just takes up a shitton of RAM though

13:23 arrdem: do you have a sense for the extent to which you're RAM bound rather than CPU bound?

13:24 Shayanjm: I'm hitting >4GB currently. I could probably optimize down to the 3-4 range for this current set of features

13:24 but once I start scaling to user-level

13:24 I'm probably just going to need to get more boxes

13:24 the problem isn't so much 'getting' the data, it's allocating enough resources to process so much of it in parallel

13:24 arrdem: yeah. and due to UT AUPs you could probably get away with doing dev on Condor, but you totally can't do that for production.,

13:25 Shayanjm: I could throw everything in series and have it take up much less mem, but then it'll also take FOREVER to do anything half-useful

13:25 Yeah exactly

13:25 so for production, I was thinking of an interesting solution

13:25 the neural net is really what powers this - so I'd need to persist it to some central location that's visible to all nodes

13:25 I could then have a set of scrape nodes, and a set of process nodes, each handling requests in a round-robin fashion

13:26 the problem is going to managing these actions though

13:26 arrdem: :D

13:26 Shayanjm: and I really really hope clojure has some nice libraries that I can use specifically for that sort of scale.

13:27 arrdem: my experience has been that Clojure doesn't actually have amazing tooling for cluster operations sadly. it's not hard, but I didn't find a good go-to solution last time I looked.

13:27 Shayanjm: I found this: https://github.com/amitrathore/swarmiji

13:27 but not really sure about its state since the last commit was in 2011.

13:28 arrdem: oh damn that was written against Clojure 1.1.0

13:28 yeah... don't use that.

13:28 Shayanjm: yeahhhh

13:28 I could just do a really dumb scale

13:28 abstract it to the network layer

13:28 throw a bunch of nodes up behind a loadbalancer

13:29 persist state with a central DB/node or something

13:29 but then that's no fun

13:29 arrdem: "fun" :D

13:29 Shayanjm: this a student start up or are you just honking around?

13:29 Shayanjm: just learning Clojure + ML at the same time lol

13:30 arrdem: lol nice

13:30 Shayanjm: but I guess it could technically become a 'thing'

13:30 I sold my first startup when I was a freshman so I'm not really looking to dive into anything just yet haha

13:30 * arrdem is jelly

13:31 Shayanjm: lolol it wasn't a big company or anything, just a little side thing I had since I was like a sophomore in HS

13:31 Now I just consult

13:31 which is fun, because the people who hire me tend to have really really interesting problems

13:32 arrdem: you in town for the summer man?

13:32 jollygood: is there a function that returns true if one string is a contained within another?

13:32 Shayanjm: Yup, until mid august

13:33 arrdem: sweet. I gotta drag you out for coffee sometine.

13:33 Shayanjm: for sure. You live near campus?

13:34 arrdem: I'm at my folks in westlake for the summer but it's easy for me to get in to campus.

13:34 Shayanjm: ah gotcha

13:34 * arrdem needs more excuses to come in to town

13:34 Shayanjm: Cool, I'll pm you my number. Text me whenever you want to grab a coffee :P

13:34 arrdem: ballin

13:39 jollygood: how to find if s1 is contained (is a substring of) in s2? (something "foo" "..foobar..") => true

13:40 MarcInNYC: @jollygood Use re-find or String#contains

13:41 (.contains "...foorbar..." "foo")

13:41 (re-find #"foo" "...foobar...")

13:47 jollygood: ,(.contains "...foorbar..." "foo")

13:47 clojurebot: true

13:47 jollygood: cool thanks

14:39 xy86: is there a recommended form validation library?

14:40 Fare: validate what?

14:40 xy86: html/http forms

14:41 arrdem: xy86: what property of form data was Fare's question.

14:42 xy86: arrdem: sorry i dont understand the question

14:43 arrdem: http://yogthos.github.io/lib-noir/noir.validation.html

14:43 amalloy: xy86: arrdem is telling you that Fare is asking you what about your data you'd like to validate

14:43 i figured involving a fourth person would make this practically a sitcom

14:43 arrdem: (inc amalloy)

14:43 lazybot: ⇒ 149

14:44 amalloy: (i would have left out the explanation and let a *fifth* person accuse me of sitcommery, but i love that juicy karma)

14:44 arrdem: will inc for lulz

14:46 xy86: ha. im feeling kind of stupid right now. regardless, im not looking to validate any one specific thing, it is just that in python there are general purpose form validation libraries that let you specify 'this field is a number', this is a zipcode, etc

14:46 im not sure that gives any more relevant information...

14:47 i saw multiple libraries if i google, it is just they are not the same ones used 3 years ago and id rather pick one that is maintained and preferrably widely used

14:51 can anyone vouch for formative in particular?

14:53 zamaterian: prismatic's schema

14:55 xy86: zamaterian: i like what i see, good suggestion

14:56 aaelony: Learning more about defrecords. ...but stuck on the seemingly simple issue of how to flatten the vector I am trying to pass to the defrecord. https://www.refheap.com/88095

15:01 gfredericks: aaelony: apply

15:02 amalloy: i'm sure he'd figure it out if he only applied himself more

15:02 clojurebot: I don't understand.

15:02 teslanick: ,(defrecord Foo [a b c d])

15:02 clojurebot: sandbox.Foo

15:02 aaelony: I always forget apply.

15:02 teslanick: ,(apply ->Foo [ 1 2 3 4 ])

15:02 clojurebot: #sandbox.Foo{:a 1, :b 2, :c 3, :d 4}

15:02 amalloy: ~clojurebot |would| figure it out if he only applied himself more

15:02 clojurebot: Ack. Ack.

15:02 aaelony: gfredericks: thank you

15:03 teslanick: Arrow-constructor syntax is weird to me.

15:03 aaelony: me too

15:03 teslanick: map-> constructor syntax makes more sense because it's saying what it intends: map to record-of-this-name.

15:03 gfredericks: teslanick: it's just a function name, not special syntax

15:04 teslanick: Suppose that's true. It seems weird to me that using defrecord declares a magically-named function.

15:04 And that there are multiple entry points for creating records.

15:04 gfredericks: teslanick: in any case, what would you say ->Foo is creating a Foo from?

15:04 fields->Foo?

15:06 teslanick: Dunno. Seems like (new Foo 1 2 3 4) is ok, or (apply Foo [1 2 3 4]). I'm sure that's the JS programmer in me talking, and that there are other considerations that make that behavior untenable.

15:07 But whatever, I'm just commenting that defrecord makes multiple symbols, and I consider that surprising behavior

15:09 gfredericks: teslanick: well that first one works

15:09 but it's not a var, and vars are useful for some things

15:09 the latter couldn't work because Foo is a class

15:40 bacon1989: So I was wondering, is there an easy way to eval something only within the context of a given namespace, and return to a former namespace?

15:40 stuartsierra: bacon1989: not really

15:41 What is it you want to do?

15:41 bacon1989: hmm, I want to have some sort of repl

15:41 bryanmaass: Does anyone have an argument for using large-ish lets?

15:42 bacon1989: but where i'm calling load-string doesn't have access to certain (require... 'd stuff I want loaded at runtime

15:42 stuartsierra: bacon1989: You can set the "current" namespace with `in-ns`, but it doesn't always do what you think.

15:43 mikerod: stuartsierra: I've been using clojure.tools.namespace.parse

15:43 bacon1989: well, I juse want a separate namespace when I perform the evaluation

15:43 mikerod: However, we recently stumbled on a use-case

15:43 where we want the ns transitive deps

15:43 to be in order

15:44 bacon1989: but I want to require some nifty things that would be useful from the commandline

15:44 mikerod: as they would be loaded - so like top-to-bottom as they are declared

15:44 bacon1989: i'm wondering if maytbe I should jsut write a separate file containing the repl, call the function, and check to see if the certain things I want are required beforehand

15:45 mikerod: I've noticed that clojure.tools.namespace.parse may *almost* maintain this order with `deps-from-ns-decl`, but it puts it in a set in the end so we lose it.

15:47 stuartsierra: mikerod: Given all the bizarre forms of `ns` in the wild, I don't think I could ever guarantee to preserve order, but you could define your own `deps-from-ns-decl` that doesn't call `set`.

15:48 The actual load-order is undefined anyawy.

15:49 mikerod: stuartsierra: I thought about that. I noticed `deps-from-ns-form` is private. I wasn't sure that any sort of order was guaranteed. So I didn't know where to go from there.

15:50 We want the lexical ordering top-to-bottom as namespace deps are declared. We are trying to use that order for some sort of initialization we are doing.

15:50 stuartsierra: The private def means I'm not making any promises to keep that function there. But you can still call a private function with @#'foo or fork it to customize the behavior to suit your needs.

15:52 mikerod: what didd you mean "load-order" is undefined?

15:53 stuartsierra: mikerod: I mean there's nothing in Clojure that promises that files will be loaded in any particular order. That's just an implementation detail. For example, if a namespace already exists, `require` will not reload it unless you specify `:reload`.

15:55 mikerod: stuartsierra: ah yes, I know about the ns not reloading files. What we are really trying to get is transitive ns deps vars in their order they are declared

15:55 so, top-to-bottom ns deps, top-to-bottom var defs

15:56 So in the end we get all vars as they are "def"ed in order as you walk the ns depenendency chain

15:56 dependency*

15:56 stuartsierra: tools.namespace only parses `ns` forms, not var definitions. You may want something like tools.analyzer.

15:58 mikerod: Yeah, we were going to manually order the vars

15:58 once we had the the ns's in order

15:59 perhaps tools.analyzer has something

15:59 I appreciate the feedback on this.

16:07 stuartsierra: mikerod: In that case, my feedback is not to base any assumptions on the order in which files are loaded. :)

16:14 Bronsa: stuartsierra: that's unrealistic when you have i.e. a defmulti on a namespace and a defmethod for that same multimethod on another namespace

16:14 you *need* to load the namesace with the defmulti before the other one

16:17 andyf_: arrdem: Ping

16:17 arrdem: andyf_: pong

16:17 mi6x3m: hey clojure, any way to check if a NS exists other than find-ns?

16:18 andyf_: arrdem: Thanks for the cheatsheet generator updates. Tweaking them more now so that new vars added since Clojure 1.3 also point to Grimoire pages

16:18 arrdem: Should I just leave special forms pointing at Clojure official docs for now, I guess?

16:19 mikerod: stuartsierra: hah, I guess that sounds good. However, we were trying to do some delayed-initialization stuff to var values. We wanted to do this in the "natural" order that var dependencies work in at compile time.

16:19 Which is top-to-bottom in their ns, and top-to-bottom in ns decls.

16:19 arrdem: andyf_: my pleasure. yeah I'd leave special forms and reader stuff pointing to the official docs. still not sure how I want to get that stuff into grimoire, but there are blank pages waiting for ink.

16:20 andyf_: thanks for the search version btw. you partially solved #18 for free :D

16:21 andyf_: arrdem: Have you considered adding contrib libs to Grimoire? If ClojureDocs.org really does update soon, they might update that, too, so not necessarily high priority

16:21 stuartsierra: mikerod: Sounds like a compiler to me. :) You might be interested in https://github.com/clojure/clojure/tree/fastload

16:22 arrdem: andyf_: clojure.tools.* and friends? I hadn't thought about it and I think I'd need to redesign some stuff to be more inline with what crossclj does in order to support that.

16:22 andyf_: with all due respect to the contrib maintainers, contrib docs are worse on average than core's docs so I probably wouldn't bother.

16:22 mikerod: stuartsierra: we are doing DSL stuff. It is compiler-like here.

16:23 andyf_: Also thanks for search is due to Francois du Toit, who implemented it

16:24 arrdem: andyf_: if you think that'd be valuable I'm open to it, I just think it's a ton more work to replicate something that the "official" clojure autodocs already do.

16:24 not that those have a ton of google-foo

16:25 andyf_: The main potential advantage over official docs are user contributed examples. Gotten many of those yet, other than initial copy from ClojureDocs.org?

16:25 arrdem: not a one sir go fish

16:25 * Bronsa really dislikes autodoc

16:26 arrdem: and the clojuredocs.org import was kinda janky.. I think I'll wind up reworking the way I did that as part of 0.2.0.

16:26 since apparently there's interest in an examples API and right now examples are monolithic.

16:27 mikerod: What is this fastload? looks like clj's github to me. Maybe this was a joke? hah

16:27 arrdem: also right now examples have the bloody user=> prompt and aren't valid Clojure source so I can't use TANAL to create links to used vars.

16:27 andyf_: You should suggest 'git clone' and file io as an API :-)

16:27 arrdem: lol I may yet do this. api.grimoire.arrdem.com doesn't exactly roll off the tongue :P

16:28 lodin: I'm trying to use tools.analyzer(.jvm) to analyze clojure expressions. I want to maintain separate environments, but when using (with-env ...) I haven't found a way to "resume" analysis when I have a new chunk of code. Does anyone have any clue?

16:28 stuartsierra: mikerod: `fastload` is an experimental branch of Clojure designed to improve startup time, mostly by deferring compilation of Vars, I think.

16:28 mikerod: Oh, I just realized this is a branch... interesting

16:30 PigDude: i know the other clojure cool kids are laughing when i refer to a protocol method implementation as Foo#bar ... how do you write this out?

16:31 (bar Foo)? )

16:31 :)

16:31 puredanger: mikerod: yes, it also caches classes. I find it's generally ~10% faster for startup type things

16:32 amalloy: PigDude: the clojure notation for class methods is Foo/bar, but it's not really used much for protocol functions

16:32 puredanger: being evaluated (along with the direct branch, which goes further) for future Clojure

16:32 amalloy: i think it would be understood, though

16:32 PigDude: arent' the two very differen though?

16:32 stuartsierra: amalloy: I'd read Foo/bar as a static method.

16:33 PigDude: my misgiving about Foo#bar notation is that Foo#bar, Foo/bar etc puts the Foo first

16:33 mikerod: puredanger: Oh nice. This is definitely interesting. I'm going to look through some of the diff here.

16:33 PigDude: note i'm talking about implementations, so Foo is a record/type name, not a protocol name

16:33 hiredman: protocols don't have methods

16:34 they are collection of functions

16:34 stuartsierra: Yeah. I think the protocol isn't really part of the name.

16:34 puredanger: PigDude: protocol functions are functions in the namespace, just like other functions

16:34 bacon1989: ,(ns foo)(defn test [] "test")(ns bar)(use 'clojure.repl)(dir foo)

16:34 clojurebot: nil

16:34 bacon1989: huh

16:35 is there a way to reference the namespace of something declared as ':as' etc

16:35 PigDude: puredanger: sure, but namespaces have no place in this discussion afaik

16:36 hiredman: i know that

16:36 hiredman: but nobody read my first message?

16:36 hiredman: i asked: how do you refer to protocol method implemtnation? Foo#bar (ruby-style) is ugly to me

16:36 *method implementation*, not specification in protocol definition

16:37 hiredman: PigDude: how do you refer to different multimethod implementations?

16:37 stuartsierra: Oh, I see, 'Foo' is the record in this case

16:40 PigDude: yea :)

16:40 stuartsierra: I just point and say "that thing"

16:40 PigDude: hiredman: don't know! right now i'd probably refer to the namespace where it is implemted

16:41 hiredman: but that depends on how it's being used. i was just curious if any shorthand around this stuff had crystalized

16:46 lodin: hiredman: (get-method meth dispatch-val) gives you the method for a dispatch value, but it doesn't work for protocol methods it seems.

16:47 sdegutis: Hello.

16:47 Is Clojure 6.0 the current version?

16:47 abp: sdegutis: yup

16:47 justin_smith: you mean 1.6.0?

16:48 sdegutis: abp: thanks

16:48 justin_smith: I thought the 1. was implied.

16:48 abp: Hi, i'm writing a webapp with om and want to show a selection of "strategies"

16:48 available in the clojurescript client. The strategies are clojurescript

16:48 functions with metadata.

16:48 So I thought about analyzing modified cljs-files for new functions with metadata and push those fn infos to the browser, to render a list.

16:48 Then I could use sourcemaps to get from function ns+names to js functions. Are there better approaches? It should be editor but not necessarily browser-repl/auto-push-library independent.

16:48 sdegutis: Hmm I should look into Om.

16:49 abp: yup

16:49 justin_smith: sdegutis: I had a bad mixup recently, where I was supposed to be using a version 2.0 and was using 1.2.0

16:49 sdegutis: Sorry I can't be more help than wondering something aloud.

16:49 justin_smith: Ouch.

16:50 This feels like it should be Clojure's theme song: https://www.youtube.com/watch?v=GihSA4V2UYw

16:50 abp: sdegutis: What the hell happened in #clojure-social? Also, pleeease recreate.

16:50 sdegutis: abp: #clojure-offtopic

16:50 and I can't go there I'm banned.

16:50 abp: aww

16:50 lol

16:50 why?

16:50 clojurebot: because that's not how macros work

16:50 lodin: abp: How do you plan to analyze the cljs files?

16:50 abp: :D

16:50 sdegutis: abp: Because I asked to be banned.

16:50 abp: sdegutis: you're a macro, bot said so

16:51 sdegutis: bots never lie

16:51 it's one of their rules

16:51 abp: Yea basically they can't.

16:52 sdegutis: "Rest assured that all lethal military androids have been taught to read and provided with one copy of the Laws of Robotics. To share."

16:54 "If you feel that a lethal military android has not respected your rights as detailed in the Laws of Robotics, please note it on your self-reporting form."

16:54 I believe that qualifies as on-topic because someone mentioned robots.

16:56 dbell: I've run into this a few times lately, and it's been eating at me---what's the idiomatic way to treat a map sequentially? I've had a few cases where I want both the key-value random access of a map, but the sequentialness of a vector

16:57 hiredman: what you want is a database with multiple indices, so build a composite structure of two maps indexing different things

16:57 sdegutis: dbell: maps have no order; you can turn it into a vector of 2-element vectors and sort it if you want

16:57 abp: sdegutis: Actually 'bots, but "Laws of 'botics" takes some of your quotes sound.

16:58 sdegutis: dbell: sort-by should do that just fine iirc

16:58 abp: syntax error: near line 1: "'bots, but"

16:58 abp: dbell: reduce?

16:59 sdegutis: dbell: &(sort-by first {:a 1 :b 2 :c 3})

16:59 dbell: &&(sort-by first {:a 1 :b 2 :c 3})

16:59 lodin: dbell: Can you elaborate? maps are seqable.

16:59 abp: sdegutis: errnr: 56724 , not allowed in symbols?

16:59 sdegutis: uhh clojurebot

16:59 abp: error code: 2

16:59 ,(sort-by first {:a 1 :b 2 :c 3})

16:59 clojurebot: ([:a 1] [:b 2] [:c 3])

17:00 dbell: yeah, sorry, didn't mean to ask and bail

17:00 sdegutis: lazybot: why didn't you eval the thing that started with &&?

17:01 dbell: i'm particularly caught up w/an Om project, where the data structure has to be a map or a vector, and I want to map rendering across a collection, but i want to preserve call-by-id

17:01 TEttinger: sdegutis ##(sort-by first {:a 1 :b 2 :c 3})

17:01 lazybot: ⇒ ([:a 1] [:b 2] [:c 3])

17:02 sdegutis: oh that one

17:02 thnkas

17:02 dbell: I probably just need to learn about cursors more thoroughly

17:02 abp: dbell: have you considered core.async for centralized state updates?

17:02 sdegutis: dbell: what cursors?

17:02 dbell: abp: how does that play nicely w/the tranaction-oriented nature of om's state-change model?

17:03 mikerod: Why does this work? (def x x)

17:03 abp: dbell: https://github.com/KitchenTableCoders/immutable-stack/blob/master/contacts/src/cljs/contacts/core.cljs#L135

17:03 mikerod: The var is then just Unbound

17:03 dbell: sdegutis: https://github.com/swannodette/om/wiki/Cursors

17:04 mikerod: Does the compiler consider the x being def'ed in scope of its init expr?

17:04 dbell: abp: reading...

17:04 amalloy: mikerod: well, consider (defn f [x] (inc (f x)))

17:04 mikerod: And is this specifically implemented to support "corecursion"

17:04 amalloy: oh... good point

17:04 lodin: mikerod: Also consider (def x) (def y x).

17:05 amalloy: mikerod: it's actually a misleading point, because that expands to (def f (fn f [x] (inc (f x)))), but it does sound good

17:05 mikerod: :P

17:05 abp: maybe reducers are going to be the new channel comprehension lib :)

17:06 dbell: abp:

17:06 mikerod: Yeah, I knew that (fn f [<args>] <body>) would put the fn name `f` in scope of the <body>

17:06 amalloy: anyway, when an expr is compiled, first it's scanned for var definitions, then those vars are created, then the form is compiled with them in scope

17:06 or something like that

17:06 dbell: I kind of jumped at what you said b/c I've been thinking about this, but

17:06 lodin: /whois mikerod

17:06 dbell: I'm actually trying to figure out how to mesh reactive data structures and om's state model

17:06 mikerod: amalloy: Interesting. I just never expected this to work, until I saw the classic fibonacci example.

17:07 lodin: not sure how that example relates. That is 2 separate var defs?

17:07 abp: dbell: reactive as in rx?

17:07 dbell: yeah

17:08 abp: dbell: no idea

17:08 dbell: so I think we may have miscommunicated there

17:08 np

17:08 abp: dbell: it's about observables

17:08 dbell: rx? yeah

17:08 but yeah

17:09 i'm using channels on components which trigger transactions on the central state

17:09 Bronsa: amalloy: (defn x [] x) expands to (def x (fn [] x)) not to (def x (fn x [] x))

17:09 amalloy: really? i thought there was a self-name in there somewhere

17:10 mikerod: If that is the case, then the ex is a relevant one again.

17:10 lodin: mikerod: Sure. But since that works, it is not unreasonable for (def x x) to work, since any (def x ...) can be rewritten to (do (def x) (def x ...)).

17:10 Bronsa: amalloy: it changed a while ago

17:10 mikerod: lodin: fair enough

17:10 I guess I'd like to read through some of how the compiler deals with that.

17:11 abp: dbell: Then you probably should use atom-state and channels?

17:11 Bronsa: mikerod: there's nothing much to know, once the compiler parses a def expression it interns the var before analyzing the var expr

17:12 amalloy: Bronsa: more than that, even: it interns the var before analyzing any of the top-level form the var is in

17:12 i think. right?

17:13 Bronsa: uhm, not exactly

17:13 lodin: mikerod: I realized that this is a bit unfortunate. Try (def x (recur)). Will give compiler error, but an x has still been created and is unbound. Doesn't feel good.

17:13 abp: dbell: There's also https://github.com/tonsky/datascript but I never tried that.

17:13 Bronsa: ,(let [a x] (def x))

17:13 clojurebot: #<CompilerException java.lang.RuntimeException: Unable to resolve symbol: x in this context, compiling:(NO_SOURCE_PATH:0:0)>

17:13 Bronsa: amalloy: ^

17:13 dbell: yeah i haven't either

17:13 mikerod: Bronsa: ah, yeah I see

17:13 dbell: hoping to stay more lightweight, but that might not be an option

17:14 Bronsa: amalloy: what makes you say something like that?

17:14 amalloy: there's some confusing behaviour where the var is interned before its metadata is analyzed I guess

17:14 dbell: abp: for state/channels, yeah, maybe

17:14 amalloy: i guess i'm just wrong, unless this changed recently too

17:14 Bronsa: not AFAIK

17:15 abp: dbell: a few channels and om with https://github.com/Prismatic/om-tools should be lightweight and convenient enough.

17:15 Bronsa: ,(def ^{:foo x} x)

17:15 clojurebot: #'sandbox/x

17:15 dbell: the graph topography changes as part of the application, so I'm kind of intimidated by shuffling all those channels around all the time

17:15 Bronsa: amalloy: ^ that's probably what you were thinking about

17:15 mikerod: ,(meta x)

17:15 clojurebot: nil

17:15 amalloy: nah, you give me too much credit

17:15 Bronsa: ,(meta #'x)

17:15 clojurebot: {:ns #<Namespace sandbox>, :name x, :file "NO_SOURCE_PATH", :column 0, :line 0, ...}

17:15 dbell: o hey

17:15 mikerod: woops, thanks...

17:15 Bronsa: ,(:foo (meta #'x))

17:15 dbell: prismatic to the rescue again

17:15 clojurebot: #<Unbound Unbound: #'sandbox/x>

17:15 abp: dbell: prismatics graph and schema are cljs compatible too

17:15 dbell: om with graph would work

17:15 mikerod: Bronsa: that is weird

17:16 amalloy: i think i'm mixing it up with stuff like (when false (def x 1)) causing x to be def'd

17:16 mikerod: but cool I guess? hah

17:16 abp: dbell: yep, ai lipe to the recue :)

17:16 *lisp

17:16 mikerod: amalloy: that is news to me...

17:16 Bronsa: amalloy: ah, yeah

17:16 mikerod: It is def'ed but not initialized it seems.

17:16 amalloy: mikerod: var creation is unconditional

17:17 it happens when the def form is compiled, not when it's run

17:17 mikerod: Yeah, I guess that is why you should always follow the advice of not trying to do weird nested var def's

17:21 amalloy: @@(def x (delay @x))

17:26 mikerod: that one is painful to think about

17:27 well, I guess not so bad

17:30 TimMc: ,@@(def x (delay @x))

17:30 clojurebot: #<StackOverflowError java.lang.StackOverflowError>

17:30 TimMc: *nod*

17:31 Bronsa: ,@(def x (delay @x))

17:31 clojurebot: #<Delay@ade1b6: :pending>

17:31 Bronsa: wut.

17:31 ah.

17:32 metellus: ,x

17:32 clojurebot: #<Delay@ade1b6: :pending>

17:32 metellus: ,@x

17:32 clojurebot: #<StackOverflowError java.lang.StackOverflowError>

17:32 TimMc: ,@x

17:32 clojurebot: #<StackOverflowError java.lang.StackOverflowError>

17:33 lodin: The imperative semantics of def irk me a bit.

17:36 mikerod: lodin: I can't think what specifically is "imperative semantics" about it

17:37 lodin: mikerod: Typically you use it for its side effects and you don't care about the return value. And the side effect persists even if you have a compilation error in the form.

17:38 kristof: I don't follow why that's a bad thing.

17:39 TimMc: lodin: If that makes you twitch, you should look at the source for defonce.

17:42 lodin: kristof: I haven't really considered the implications of this, but I guess you could have that def returns a data structure, that, when "returned" to the top level, was added to a namespace.

17:47 hiredman: you get a statically linked top level environment, something like mls repl

17:47 not very appealing

17:47 lodin: hiredman: What do you mean by statically linked top level?

17:48 hiredman: (and what's mls repl?)

17:49 hiredman: well the "imperative semantics of def" means def creates vars that operate as mutable reference cells, and for things in the top level enviroment you link via the mutable refence cell, so if the mutable refence cell changes the next time you get the updated value

17:49 wildnux: hi, what does the & { :as opts } mean in this function: (defn character [name & {:as opts}] (ref (merge {:name name :items #{} :health 500} opts)))

17:49 hiredman: the "more functional" approach would be to model the top level enviroment as basically a special case of let

17:50 mikerod: lodin: ok, I see what you mean by that

17:50 I wish all of Namespaces worked in a persistent map sort of wya

17:50 way*

17:50 hiredman: so if you def something, and then use it, then redef it, the uses will not see updated values, like (let [x 1 f (fn [] x) x 2] (f))

17:51 michaniskin: ~korks

17:51 clojurebot: korks is keywords or a seq of keywords (like update or update-in) used in om i.e. transact! and update!

17:51 michaniskin: ROFL

17:51 lodin: hiredman: Why is is desirable to be able to redefine the vars? REPLs?

17:51 hiredman: lisp in small pieces has a section on choosing a linking strategy for the toplevel which constrasts different approaches

17:51 lodin: sure

17:52 dbell: oh cool

17:52 wildnux: all arguments after name will be treated as kvkvkvkvkv of a map

17:52 wildnux: dbell: oh that is for the implicit let binding?

17:53 dbell: so (character "joe" :occupation :protagonist :nemesis :villain)

17:53 yeah

17:53 hiredman: ml (the language) takes the "treat top level things as a special kind of let" approach

17:53 lodin: hiredman: Nice, will look it up.

17:53 kristof: lodin: because vars are variables

17:53 hiredman: the book is like a million dollars on amazon though

17:53 kristof: which should be... variable

17:54 wildnux: dbell: what does #{} signify?

17:54 dbell: #{} is the clojure shorthand for a set literal

17:54 lodin: hiredman: But the shipping is FREE! ;-)

17:54 dbell: just like [] makes vectors and () makes lists

17:54 hiredman: I think I actually had rich recommend it to me when I asked him about implementing a lisp, and then my eyes kind of bugged out

17:54 dbell: #{} makes sets

17:54 hiredman: ~logs

17:54 clojurebot: logs is http://clojure-log.n01se.net/

17:54 wildnux: dbell: got it

17:54 dbell: thanks

17:55 dbell: np

17:55 lodin: kristof: Usually, outside the repl, I never use the vars as variables.

17:56 mikerod: hiredman: eyes bugged out due to the price or the content?

17:56 wildnux: dbell: one quick question, can we not just say [name & {}] instead of [name & {:as opts}] ?

17:56 lodin: kristof: I guess if you need that functionality you can put an atom in the var? (Never actually used atoms, but I reckon that's what they're for, right?)

17:57 dbell: wildnux: the problem is then you have no binding to the map

17:57 amalloy: i remember being unpleasantly surprised by code like (defprotocol IFoo (foo [this])) (def multifoo (partial map foo)) (extend-protocol IFoo nil (foo [this] nil)) (multifoo [nil nil nil])

17:57 hiredman: mikerod: the price

17:57 amalloy: (re: the discussion on var mutation and saving old values)

17:59 arrdem: do we have a parallel doseq form?

17:59 hiredman: amalloy: do a see a jira issue in the future with "protocol functions shouldn't be used as HOFs" in it?

18:00 amalloy: hiredman: it's actually more specific than that. (defn multifoo [xs] (map foo xs)) would work fine

18:00 mikerod: hiredman: ah, I see it now

18:00 hiredman: amalloy: sure

18:00 mikerod: amalloy: so this is an issue with what partial is doing?

18:00 amalloy: mikerod: no, partial doesn't do anything relevant

18:01 mikerod: This seems scary to me

18:01 I'm not sure what causes the problem though.

18:01 amalloy: the issue is that when you call partial with foo, you get a snapshot of the value of the var #'foo, and partial saves that. but when you extend-protocol, the var #'foo is updated with a new value

18:01 hiredman: foo takes the value of the var foo, which extend the protocol mutates, but in the top level call it takes the value of the var before the extend has mutated it

18:02 kristof: lodin: changing vars for dynamic binding, then

18:03 mikerod: Makes me curious for: (defprotocol IFoo (foo [this])) (defn multifoo [] (partial map foo)) (extend-protocol IFoo nil (foo [this] nil)) ((multifoo) [nil nil nil])

18:03 amalloy: would work fine

18:03 mikerod: So the fn bodies are safe

18:04 amalloy: wat

18:04 mikerod: stupid question? hah

18:04 ybit3: i think i've asked this before, but i'm looking for a way to do something like lein install "org.clojure/clojure '1.6.0'" --save and have the dependency installed into the project.clj dependencies

18:05 is there something like this in lein?

18:05 mikerod: (defn multifoo [] (partial map foo)) -- I guess this doesn't take the "snapshot" version of foo

18:05 kristof: lodin: Is that not a legitimate use-case? Defing something and then using (binding . . .) in some code where you need implicit vars for context

18:05 amalloy: mikerod: well, it snapshots every time multifoo is called

18:05 mikerod: ok

18:05 amalloy: so like, (let [f (multifoo)] (extend-protocol ...) (f [nil nil nil])) would fail

18:06 lodin: kristof: Yes. But I guess you wouldn't be surprised if I'm not a fan of dynamic bindings either? ;-)

18:07 mikerod: Got it. Good example.

18:11 ybit3: recommended server framework for clojure?

18:12 kristof: lodin: Sometimes you need them

18:12 lodin: Well, sometimes I need them. :P

18:12 lodin: kristof: Like when? (Other than redirecting output.)

18:13 kristof: lodin: Try writing an editor like emacs without dynamic binding!

18:13 Descending a abstract data type and keeping track of the context

18:14 lodin: Really, a lot of the code in emacs depends on the ability to stack a binding onto the env and popping it off

18:15 And the only way you can handle that is either with dynamic scope or explicitly passing things in as arguments. Which are equivalent, but one is unwieldy, the other is useful because it's implicit.

18:15 lodin: kristof: I don't think they're really equivalent.

18:16 kristof: I believe in implicit vars for the exact same reason I don't make every function expect something like a Maybe monad that could be an error

18:16 lodin: kristof: lazy seqs at least used to be an issue. Don't know about current versions.

18:16 boxed: how do I call ArrayList.remove(int)? I can’t get clojure to not box the int so it calls ArrayList.remove(Object) instead

18:16 ybit3: i can't decide between caribou, luminus, moustache, compojure, or pedestal?

18:16 i'm mostly accustomed to writing apps in rails and express

18:17 amalloy: appropriate username, boxed

18:17 kristof: lodin: They certainly are! You can either lob that binding as far down as possible or you can hand it off gently. It's certainly the same thing. But if you use that var a lot farther down the callstack than you bound it, are you really going to want to pass it manually?

18:17 boxed: amalloy: heh, didn’t think of that

18:17 amalloy: should just be (.remove ^ArrayList xs (int 1)), no?

18:17 arrdem: can't have raw integers running around now can we? machine primitives are so unsightly...

18:17 lodin: kristof: I'm be inclined to say yes, but I haven't implemented any emacs. :-)

18:18 s/I'm/I'd/

18:18 kristof: lodin: That was just a good, complicated example. The point is that it happens. It's the reason Common Lisp implemented both dynamic and lexical binding.

18:18 mikerod: ArrayList.remove(int) being overloaded with Object seems nasty to me

18:18 kristof: And clojure, in tandem.

18:19 mikerod: That is very funny that boxed had a question about boxing though

18:21 Frozenlock: ,(sort ["a1" "a2" "a10"])

18:21 clojurebot: ("a1" "a10" "a2")

18:22 Frozenlock: Any function to sort with the numbers?

18:22 *as well

18:22 lodin: kristof: If you just use them as implicit variables you need to keep track of when the expression they're used in is evaluated though.

18:23 boxed: amalloy: thanks, that works… is that a way to avoid going through the reflection system or something?

18:23 Frozenlock: For emacs I have this https://www.refheap.com/88097, but I'd be nice if it's already somewhere in Clojure.

18:23 lodin: kristof: like in (let [f (bindings [*x* 3] (fn [y] (+ *x* y)))] ...).

18:24 amalloy: boxed: well, if the compiler has sufficient type information, it will emit non-reflective method calls. type-hinting is one way to give it type information, although not the only way

18:24 lodin: s/bindings/binding/

18:28 ohpauleez: ybit3: It really comes down to what are you building and what are your needs?

18:28 kristof: lodin: That looks fine to me and I don't see anyone needing to keep track of anything

18:28 ohpauleez: Oh those, Pedestal is the only one that is truly async

18:29 it also embraces the "data over functions over macros" found in other Clojure systems, like Datomic

18:29 And if you need something like url-for, I think it may be the only one that supports that

18:29 kristof: lodin: Imagine that instead of *x* being 3, *x* is something like current-working-directory

18:30 lodin: I think it's good to trust the most recent function call to have the most up-to-date and specific information. So if it gets rebound later, I won't care.

18:33 lodin: kristof: OK I see what you're getting at.

18:34 ybit3: ohpauleez: i've narrowed it to luminus, compojure, pedestal

18:34 kristof: And I see why you might be wary of using a dynamically scoped variable!

18:34 ybit3: i'm building a POS system

18:35 it's going to auth users, store payments, fetch payment history

18:35 lodin: kristof: Maybe a key part of your last line is "up-to-date". I read that as you have (informally anyway) an external state that changes.

18:39 kristof: lodin: By up-to-date, I didn't mean external state, I meant context of computation. But yes, you might have a ref floating around somewhere that you can occasionally read from in calls.

18:39 arrdem: andyf_: http://grimoire.arrdem.com/ live!

18:40 kristof: No actually, I don't think that's a good use of dynamic vars. I dunno!

18:40 lodin: In common lisp, you often use defparameter for dynamically scoped variables. The name "parameter" should be clear about what kinds of situations you use it for.

18:40 lodin: kristof: I got that. That's why I said informally. What is defined as "external" is kind of arbitrary, I guess.

18:41 andyf_: arrdem: email sent to Clojure group about new cheatsheet variants

18:41 lodin: kristof: True. Does parameterized functions not sound a lot like objects though? (Not talking about Java classes and objects here.)

18:42 arrdem: andyf_: just saw it. thanks!

18:43 kristof: lodin: If by parameterized functions you mean functions that make use of dynamically scoped variables then no, they sound nothing like objects.

18:45 lodin: kristof: Of course not dynamically :-), just parameterized. Like a record that implements protocol functions. The protocol functions are parameterized over the record's fields.

18:47 Jaood: arrdem: http://grimoire.arrdem.com/1.6.0/clojure.core/some/#example-0 - some html problems?

18:47 * arrdem mutters darkly

18:47 amalloy: your repl doesn't automatically print </pre> after each expression, Jaood?

18:48 arrdem: Jaood: yeah thanks for that. I won't bother fixing it for now because I expect to blow the entire examples system as currently implemented away in the next version.

18:48 Jaood: darn, my repl is broked ;)

18:48 lodin: kristof: Of course you need to pass the records explicitly then, but you also conceptualize the computation context (and make that dependency explicit).

18:51 seancorfield: Gershwin looks interesting... hybrid of Clojure and Factor... wondering if it's possible to mix .gwm Gershwin files and .clj Clojure files easily in a single project...

18:53 arrdem: Jaood: just looked at the source, that's weirdness I'm getting from ClojureDocs. Those examples have the <pre> </pre> on Clojuredocs they're just actually rendering there.

18:54 * arrdem generates no inline HTML, Markdown/Liquid for life

18:54 technomancy: huh, is liquid decent?

18:55 arrdem: eh... it's a toss up for me between Liquid and Org.

18:56 kristof: lodin: Then sure

18:56 technomancy: wait, what is this for?

18:56 org for HTML templating?

18:56 kristof: lodin: Actually, yes

18:56 clojurebot: Gabh mo leithscéal?

18:57 kristof: lodin: Many OO languages have effective methods as function pointers stored in the object's struct. Or something.

18:57 lodin: So you could consider those function pointers to be the "dynamic" bindings.

19:20 andyf_: arrdem: Note that cheatsheet has never had a complete list of all vars yet. The current most conspicuous absence are the vars in clojure.core.reducers. Suggested additions are welcome there

19:24 arrdem: andyf_: yeah that's something cbp has been saying for a while that we need a "real" whole var set search. Maybe 0.3.0 material but I'm not super motivated to write some javascript.

19:26 andyf_: I've needed to take a serious look at reducers for a while anyway so that may be something I throw you this weekend but who knows.

19:26 stuartsierra: I wouldn't expect the cheatsheet to have *every* Var.

19:27 Bronsa: at least it includes fnext

19:27 andyf_: No rush, but certainly a welcome addition if someone has a good suggestion. Alex Miller has updated clojure.org/reducers recently and is looking for feedback there

19:28 stuartsierra: Me, neither, but there may still be a few reasonable additions other than reducers.

19:28 stuartsierra: sure

19:30 jdkealy: Hi I was wondering if anyone would dissuade me from storing all my dates as timestamps (ints) as i consider the querying possibilities possably easier to use

19:31 arrdem: clocks are totally monotonic I have no idea what you're talking about

19:31 technomancy: jdkealy: as long as they're in UTC, seems legit

19:31 Bronsa: andyf_: what version of t.a.j does eastwood use?

19:31 andyf_: Complete list of vars not on the cheatsheet is at the end of this file, in case anyone is curious: https://github.com/jafingerhut/clojure-cheatsheets/blob/master/src/clj-jvm/TODO.txt

19:32 Bronsa: 0.2.2

19:32 Bronsa: Not so easy to tell now that it is copied in as source code :-)

19:33 stuartsierra: I think of the cheatsheet as a pointer to the most commonly-used functions, not an exhaustive reference.

19:33 jdkealy: ok. so everything needs to be converted to UTC.. damn, why the hell are dates so confusing!

19:33 Bronsa: andyf_: uhm ok, there was a performance regression since 0.2.0 that'll get fixed in the next release

19:34 stuartsierra: We have API docs for reference, the cheat sheet is useful to help people find the stuff they need to know.

19:34 andyf_: Bronsa: I intend to keep the file copy-dep-scripts/deps/project.clj up to date to help me keep track

19:34 dbasch: jdkealy: you don't *need* to convert them, but might as well use the standard

19:34 jdkealy: if anyone sees a date as an int, they will assume seconds since the unix epoch

19:35 jdkealy: right that makes sense... but in a library like moment.js, if i had a user select their timezone, date, and time, getting a timestamp should be UTC, no ?

19:35 ahh ok

19:35 andyf_: stuartsierra: I am sure it is beyond "most commonly used" now, but in my mind the grouping into categories is one of its nicest features

19:35 jdkealy: ok will test that, and that's a question for another channel. thanks!

19:36 Bronsa: ,(meta ^:foo (fn [])) ;; does anybody know if this is documented behaviour?

19:36 clojurebot: {:foo true}

19:38 andyf_: Bronsa: I've been away from Eastwood for a month due to work busy-ness, but should get time for some updates in a few weeks. I really would like to add the ability to disable warnings at a per-expression level next, with no affect on compiled code

19:40 amalloy: Bronsa: what part of it are you wondering about?

19:41 jdkealy: i have a follow up question. if had an event with a start date (for simplicity, i'm using overtly simplified timestamps)... start-date = 2, end-date = 10... client queries for any event happening between 5 and 9... because the event is happening on 6,7,8 it should return true. considering the vars were set to ?start, ?end, ?query-start, ?query-end, how would i detect there is an intersection there

19:41 Bronsa: amalloy: ##(meta ^:foo (vector 1))

19:41 lazybot: ⇒ nil

19:42 Bronsa: amalloy: metadata on the fn* form is attached to the fn method

19:42 s/method/object

19:42 jdkealy: actually... a better case is client queries for between 1 and 3 (query start date being before the event start date... the area of my confusion)

19:42 Bronsa: I haven't seen that documented anywhere

19:43 amalloy: Bronsa: it's probably an accident

19:43 Bronsa: amalloy: on reify that behaviour is actually documented

19:43 arrdem: Bronsa: as Fns are IObj this seems like the obvious behavior..

19:43 amalloy: or, well, actually the macro fn is going out of its way to preserve that meta

19:44 Bronsa: arrdem: not really, ^:foo (fn []) is different from (with-meta (fn []) {:foo true})

19:44 amalloy: arrdem: not so! because ^:foo is hinting, not the function, but the *list* '(fn []]), which is consumed by the compiler

19:44 Bronsa: yeah, that

19:44 arrdem: so my example above, ^:foo (vector 1), the returned vector doesn't have the meta attached

19:45 amalloy: yeah both the fn macro and the fn* special form in the compiler are explicitely preserving that metadata

19:45 amalloy: it'd actually be impossible for ^:foo (vector 1) to get its meta attached, since vector is a function rather than a macro

19:46 Bronsa: amalloy: you could implement that in the compiler

19:46 but that wouldn't make any sense and would be broken

19:46 amalloy: yeah

19:47 Bronsa: it was just a silly example of a call returning an IObj

19:47 amalloy: this is vaguely related to http://dev.clojure.org/jira/browse/CLJ-865, and i use any excuse to link to that

19:48 Bronsa: t.a does The Right Thing™ there

19:49 amalloy: thank goodness. i couldn't even quite figure out what the right thing is, let alone convince clojure/core of it. what is the right thing?

19:50 Bronsa: (https://github.com/clojure/tools.analyzer.jvm/blob/master/src/main/clojure/clojure/tools/analyzer/jvm.clj#L160-L162

19:51 kristof: Clojure uses a single FixedThreadPool to manage async blocks

19:51 Bronsa: it doesn't break any existing code

19:51 kristof: Go tried something similar to this before 2012 and found that accessing the global lock was a pretty central point of contention

19:52 Bronsa: amalloy: wait, the ticket makes preserving metadata opt-in?

19:52 that's kinda useless.

19:52 amalloy: Bronsa: opt-out, iirc. i haven't touched it in years

19:53 oh

19:53 yes, rich asked me to add an opt-in version of the patch, which you'll see in the comments i said is totally useless

19:54 Bronsa: it totally is

19:54 whatever

20:05 amalloy: does anyone know why clojure.core/list is defined as an IFn in clojure.lang.PersistentList, instead of in clojure.core? it's like the only function i know of that is built that way

20:06 ,list

20:06 clojurebot: #<clojure.lang.PersistentList$1@1dfacc4>

20:07 amalloy: this also means it's the only function you can't put metadata on

20:08 andyf_: Wild guess, which you probably have a better idea how to answer than I do: some early bootstrap use of it in core.clj ?

20:08 Bronsa: usually when I have those kinds of questions I make the change and see if/what breaks when compiling clojure

20:10 amalloy: andyf_: i don't think so - it should be possible to just write (def list (fn* [& args] (PersistentList/create args))). but sure, good advice, Bronsa

20:11 Bronsa: amalloy: there's probably no reason why it can't be redefined in core, but if it's defined in RT it probably means it's required somewhere for bootstrapping

20:11 or that it's just a leftover.

20:15 amalloy: so it looks like PersistentList.create assumes you don't give it nil, and PersistentList.creator.invoke includes a nil check. if clojure.core/list checks for nil, and then delegates to create, that's a correct implementation

20:16 however, PersistentList.creator.invoke has some optimizations in it that would be no fun to include in clojure.core

20:19 arrdem: andyf_: someone just got referred to my / by your github.io page. bug?

20:20 andyf_: arrdem: Probably. Let me check all the generated links

20:37 Do you mean a URL of http://grimoire.arrdem.com/ ?

20:38 arrdem: andyf_: I appologize I think that the report was in error and that I was seeing two different people on different sources

20:38 andyf_: No prob. I don't see any links like that in my HTML

20:41 seangrove: Using core.typed, how can I annotate that an argument is hash-map with 3 required keys?

20:41 Trying to use the core.typed/ann form, I suppose that could be wrong

20:43 Ah, nvm, believe I got it

21:56 drusellers: trying to do an 'update-in' into an array - i feel like I am missing something obvious as my solution seems overly complex. any help would be appreciated https://gist.github.com/drusellers/dca7bc2f46ae9ecb6785

22:03 gfredericks: drusellers: you can pass `conj` and `athlete` as args to update-in instead of making a custom function

22:04 but I think the main thing is that if you want to be updating by :id you should probably use a map from :id to division instead of a vector

22:05 drusellers: gfredericks: yup, that's what i am thinking too.

22:05 kind of a palm to face

22:05 gfredericks: it's kind of surprising how rarely you need to use the indexed lookup/update on vectors

22:06 it's kind of unnatural for application data

22:08 it's kind of my third statement that starts with "it's kind of"

22:20 onr: please tell me Clojure seemed tooo alien at first, then you eventually found it useful

22:21 i'm looking at clojure codes, everything seems weird

22:21 eggsby: ya onr and the first clj I wrote was horrifying

22:23 onr: glad to hear :)

22:24 nathan7: Hey humans

22:24 I'm trying to use ClojureScript

22:24 onr: hi

22:24 nathan7: and for some reason, defmacro appears to be entirely absent

22:26 ah, found it

22:26 jollygood: hi. i am curious why did clojure opt for unhygienic macros like the ones in common lisp and not hygienic macros like in scheme? did Hickey discuss this somewhere?

22:27 nathan7: no idea about the latter, but most Clojure macros use automatic gensyms and such as not to interfere with their place of use

22:27 syntax-quote respecting namespaces also helps

22:28 ,`(fn)

22:28 clojurebot: (clojure.core/fn)

22:28 nathan7: so, effectively you get everything true hygiene would give you

22:28 eggsby: doesn't proper use gensym make macros hygienic?

22:28 nathan7: Yeah, effectively

22:28 ,`(fn [x#] x#)

22:28 clojurebot: (clojure.core/fn [x__49__auto__] x__49__auto__)

22:28 nathan7: jollygood: ^

22:29 eggsby: like, not clobbering binding names

22:29 nathan7: You have to do your best to clobber

22:29 ,`~'clobber

22:29 clojurebot: clobber

22:29 nathan7: or, for a better example

22:29 ,`(fn [~'clobber] ~'clobber)

22:29 clojurebot: (clojure.core/fn [clobber] clobber)

22:32 eggsby: ya, sometimes it's useful to borrow things like binding names from the outside scope :)

22:34 cespare: is it possible from a class to its namespace?

22:35 jollygood: I see.. so what would capturing an identifier look like in clojure?

22:36 nathan7: jollygood: I'm not sure what 'capturing' means here

22:39 jollygood: referring to the variable name defined outside of our macro

22:40 arrdem: jollygood: what do you mean "variable". A def outside of the macro? a let bound symbol outside of the macro?

22:41 jollygood: either a let or a def outside of the macro, whatever is in the scope at the place macro is used

22:43 basically, how would we avoid using gensym?

22:43 if we needed to

22:49 halogenandtoast: Is there any better way to do this: (merge ball { :x (+ (:x_speed ball) (:x ball)) :y (+ (:y_speed ball) (:y ball)) })

22:49 arrdem: halogenandtoast: get the some implementation of `update`.

22:49 s/the/thee/g

22:50 $google flatland useful update

22:50 lazybot: [useful 0.11.2 - Clojars] https://clojars.org/org.flatland/useful

22:50 arrdem: https://github.com/arrdem/oxcart/blob/master/src/oxcart/util.clj#L80

22:51 (-> ball (update :x + (x_speed ball)) (update :y + (:y_speed ball)))

22:52 halogenandtoast: Hmm

22:53 Being relatively green, I’m not sure I get everything that is happening there. Are you claiming I should use “useful” or “oxcart” here.

22:54 oxcart seems like not the answer.

22:54 And perhaps that’s just an example usecase?

22:55 but the thread-first macro is probably a good idea here.

22:57 amalloy: alternatively, something like (into ball (for [[pos speed] [[:x :x_speed] [:y :y_speed]]] [pos (+ (pos ball) (speed ball))]))

23:00 halogenandtoast: Thanks guys, I have some direction now.

23:07 kegund: So new guy on Win7. I'm long on emacs.. linux.. and just finished SICP. I'm not getting stable repls inside of emacs. What route should I take for full clojure??? cygwin&emacs-live? ssh to: CentOS+bash+emacs... Native windows? Any pointers accepted kindly.

23:09 platz: I've tried the cygwin route in the past and I'm done with it

23:09 why doesn't the repl work

23:09 kegund: done with it? you run it now or never again.

23:09 catern: i'd recommend ssh to CentOS

23:09 or you could ssh to a VM

23:10 kegund: My Cent is a VM... though remote

23:10 catern: a local VM

23:10 kegund: I'll see what I can do...

23:11 catern: the remote CentOS presumably would work, but CentOS 6 is so old and old

23:19 amalloy: kegund: i do my at-home coding in a local ubuntu vm

23:21 catern: ugh, you people not running Linux

23:21 how do you survive?

23:22 eggsby: catern: it's fine, really

23:25 * Jaood conces

23:30 kegund: Ahhh. So I got sh#t from screen about fake ttys... I'm on local bash << via VMw << via RDC... Oh well. my souped up laptop isn't geared for storage... so no local VMs :(

23:32 ;;;; show key!!!

23:32 Jaood: what is VMw?

23:33 kegund: Set of VMware VMs.

23:33 Jaood: why are you not sshing to the vm?

23:38 kegund: Jaood (still figuring out IRC again). I can't ssh to the VM because I'm local private IP and VM is another local private IP. No port work done.

23:46 catern: eggsby: i don't believe you, you've just developed coping mechanisms

23:46 kegund: how do you usually connect to the vm?

23:54 kegund: So I can't get Lein installed without a --no-check-certificate .... is that legit?

Logging service provided by n01se.net