Re: [ANN] Discontinuing 4clojure.com

2021-07-14 Thread Alan Malloy
There have been a number of requests on this thread for me to transfer the 
4clojure.com domain name to a designated successor. I'm open to that in 
principle, but there are a couple issues.

   1. I don't actually own the 4clojure.com domain name. That belongs to 
   4clojure's founder, dbyrne, who has been renewing it and pointing it at my 
   server. I imagine he will be happy to transfer it, but there might be 
   organizational hiccups I'm not aware of. If a successor is chosen, we can 
   loop him in then.
   2. I wouldn't want to transfer the domain to someone who turns out to be 
   unable to use it - maybe setting up a copy of 4clojure is harder than one 
   might imagine, since it's all 10-year-old technology. If any of the 
   prospective new owners already have a copy of 4clojure running under a 
   different domain name, I'd love to see it. Of course, the 4ever-clojure 
   guys have already done this.
   3. This is more of a "me" problem because my interaction with the 
   Clojure community for years has just been the tiny IRC room and Stack 
   Overflow, but so far all the offers to take on the mantle have come from 
   people and companies I've never heard of. Maybe you're all pillars of the 
   community now, but I just don't know it. I'd hate to give the name over to 
   a group planning to do something nefarious with collected email addresses, 
   for example. I feel like kinda a jerk for asking, since it's not like I was 
   the greatest maintainer, but I don't suppose there are any old-time 
   Clojurists who can vouch for any of these groups? Feel free to email me 
   privately (amalloy@ the domain in question, for now!) if you'd prefer not 
   to be on record as favoring one of these groups over the others.


On Monday, July 12, 2021 at 9:13:09 PM UTC-7 brando...@gmail.com wrote:

> Thank you Alan for all the work and time put into 4clojure, and thank 
> those of you who've started and contributed to 4ever-clojure!
>
> Cheers,
> Brandon
>
> On Sun, Jul 11, 2021 at 2:38 PM Alan Malloy  wrote:
>
>> I've also exported the problem data: 
>> https://drive.google.com/file/d/1hHrygxAs5Do8FpHC9kphYnmyTwZvISnb/view?usp=sharing
>> . 
>>
>> On Sunday, July 11, 2021 at 2:22:33 PM UTC-7 Alan Malloy wrote:
>>
>>> I'm happy to see this project, and I think exporting some data is a 
>>> reasonable compromise. Rather than re-learn how to do any fancy mongodb 
>>> stuff to make it into "pretty" json, I've just done a raw JSON export of 
>>> the solutions collection, which is world-readable at 
>>> https://drive.google.com/file/d/1UQHznThT_eVTBjmLGz3yME8L3teGygUs/view?usp=sharing.
>>>  
>>> I'm contemplating doing a partial export of the users collection too: I 
>>> could connect usernames to IDs without including the email addresses or 
>>> passwords, which would let you rebuild most of the user information. But 
>>> I'm not totally sure this is a good idea: some people may not want their 
>>> usernames shared, or associated with their solutions. Does anyone in this 
>>> thread have an opinion?
>>>
>>> On Tuesday, July 6, 2021 at 9:58:29 AM UTC-7 oxa...@gmail.com wrote:
>>>
>>>> Thank you Alan for all your contributions :)
>>>>
>>>> Hosting things and maintaing them is really hard. We, the LambdaIsland 
>>>> team, are already maintaining clojurians-log and clojureverse and it's 
>>>> definitely not easy!
>>>>
>>>> With a wonderful idea from @borkdude and his `sci` library, I built 
>>>> "4ever-clojure": a completely static version of 4clojure which runs using 
>>>> cljs + sci. It interprets the code in the browser itself. 
>>>>
>>>> It's live at: 4clojure.oxal.org  (Source code at: 
>>>> https://github.com/oxalorg/4ever-clojure  I'm planning to move it 
>>>> under the clojureverse github org)
>>>>
>>>> I have 2 asks from you if it is feasible:
>>>> 1. An export of all solutions (only solutions, no user data needed) - 
>>>> the community is already coming up with some amazing ideas of hooking up 
>>>> user solutions to automatically commit to a Github repo 
>>>> 2. Possibility of transfering *4clojure.com <http://4clojure.com> *-or- 
>>>> *4clojure.org <http://4clojure.org> *over to us so that we can host 
>>>> 4ever-clojure there (instead of on a separate domain)
>>>>
>>>> Thanks!
>>>> - Mitesh
>>>>
>>>> On Tuesday, July 6, 2021 at 5:56:10 PM UTC+5:30 Srihari Sriraman wrote:
>>>>
>>>>> Hey Alan, we really like 4clojure. We've suggested 

Re: [ANN] Discontinuing 4clojure.com

2021-07-11 Thread Alan Malloy
I've also exported the problem 
data: 
https://drive.google.com/file/d/1hHrygxAs5Do8FpHC9kphYnmyTwZvISnb/view?usp=sharing.
 

On Sunday, July 11, 2021 at 2:22:33 PM UTC-7 Alan Malloy wrote:

> I'm happy to see this project, and I think exporting some data is a 
> reasonable compromise. Rather than re-learn how to do any fancy mongodb 
> stuff to make it into "pretty" json, I've just done a raw JSON export of 
> the solutions collection, which is world-readable at 
> https://drive.google.com/file/d/1UQHznThT_eVTBjmLGz3yME8L3teGygUs/view?usp=sharing.
>  
> I'm contemplating doing a partial export of the users collection too: I 
> could connect usernames to IDs without including the email addresses or 
> passwords, which would let you rebuild most of the user information. But 
> I'm not totally sure this is a good idea: some people may not want their 
> usernames shared, or associated with their solutions. Does anyone in this 
> thread have an opinion?
>
> On Tuesday, July 6, 2021 at 9:58:29 AM UTC-7 oxa...@gmail.com wrote:
>
>> Thank you Alan for all your contributions :)
>>
>> Hosting things and maintaing them is really hard. We, the LambdaIsland 
>> team, are already maintaining clojurians-log and clojureverse and it's 
>> definitely not easy!
>>
>> With a wonderful idea from @borkdude and his `sci` library, I built 
>> "4ever-clojure": a completely static version of 4clojure which runs using 
>> cljs + sci. It interprets the code in the browser itself. 
>>
>> It's live at: 4clojure.oxal.org  (Source code at: 
>> https://github.com/oxalorg/4ever-clojure  I'm planning to move it under 
>> the clojureverse github org)
>>
>> I have 2 asks from you if it is feasible:
>> 1. An export of all solutions (only solutions, no user data needed) - the 
>> community is already coming up with some amazing ideas of hooking up user 
>> solutions to automatically commit to a Github repo 
>> 2. Possibility of transfering *4clojure.com <http://4clojure.com> *-or- 
>> *4clojure.org 
>> <http://4clojure.org> *over to us so that we can host 4ever-clojure 
>> there (instead of on a separate domain)
>>
>> Thanks!
>> - Mitesh
>>
>> On Tuesday, July 6, 2021 at 5:56:10 PM UTC+5:30 Srihari Sriraman wrote:
>>
>>> Hey Alan, we really like 4clojure. We've suggested using it for training 
>>> most people at nilenso and we're very thankful to you and all the 
>>> contributors for that!
>>> We (nilenso) would be up for picking up the hosting costs, and also some 
>>> other operations or development work if needed.
>>>
>>> It would be even better if we could work together and turn this into a 
>>> community owned project (ex: clojurists together 
>>> <http://clojuriststogether.org>). That might also assuage your concerns 
>>> about data ownership.
>>>
>>> The questions, and solutions that the community has put together on 
>>> 4clojure over the last decade are very valuable as a learning tool. Perhaps 
>>> we can find a way to keep them around without attributing them to a user? 
>>> One idea might be to deactivate all existing accounts, and remove the user 
>>> data (email, passwords, other PII) etc while keeping the questions and 
>>> solutions from those users.
>>>
>>> We would be sad to see 4clojure go away, hope we can find a way for it 
>>> to live on.
>>>
>>> Cheers,
>>> Srihari
>>>
>>> On Tuesday, July 6, 2021 at 1:12:44 PM UTC+5:30 Robert P. Levy wrote:
>>>
>>>> Hi Alan,
>>>>
>>>> Just as a thought.  If it's minimal work on your end (eg. if the folks 
>>>> from Roam research who chimed in above pick it up) why not clear the 
>>>> password hashes and let the new maintainer handle the communication that 
>>>> passwords need to be reset?
>>>>
>>>> Rob
>>>>
>>>> On Sun, Jul 4, 2021 at 1:26 PM Alan Malloy  wrote:
>>>>
>>>>> TL;DR: Turning off 4clojure.com by the end of July 2021
>>>>>
>>>>> Hello, 4clojure problem solvers. You've probably noticed SSL errors on 
>>>>> 4clojure.com over the last week. The old decrepit system 4clojure 
>>>>> runs on has finally gotten out of date enough that I can't even figure 
>>>>> out 
>>>>> how to get it recent enough that SSL certs will auto-renew anymore.
>>>>>
>>>>> In principle I could start from scratch on a new server and move 
>>>>> 

Re: [ANN] Discontinuing 4clojure.com

2021-07-11 Thread Alan Malloy
I'm happy to see this project, and I think exporting some data is a 
reasonable compromise. Rather than re-learn how to do any fancy mongodb 
stuff to make it into "pretty" json, I've just done a raw JSON export of 
the solutions collection, which is world-readable at 
https://drive.google.com/file/d/1UQHznThT_eVTBjmLGz3yME8L3teGygUs/view?usp=sharing.
 
I'm contemplating doing a partial export of the users collection too: I 
could connect usernames to IDs without including the email addresses or 
passwords, which would let you rebuild most of the user information. But 
I'm not totally sure this is a good idea: some people may not want their 
usernames shared, or associated with their solutions. Does anyone in this 
thread have an opinion?

On Tuesday, July 6, 2021 at 9:58:29 AM UTC-7 oxa...@gmail.com wrote:

> Thank you Alan for all your contributions :)
>
> Hosting things and maintaing them is really hard. We, the LambdaIsland 
> team, are already maintaining clojurians-log and clojureverse and it's 
> definitely not easy!
>
> With a wonderful idea from @borkdude and his `sci` library, I built 
> "4ever-clojure": a completely static version of 4clojure which runs using 
> cljs + sci. It interprets the code in the browser itself. 
>
> It's live at: 4clojure.oxal.org  (Source code at: 
> https://github.com/oxalorg/4ever-clojure  I'm planning to move it under 
> the clojureverse github org)
>
> I have 2 asks from you if it is feasible:
> 1. An export of all solutions (only solutions, no user data needed) - the 
> community is already coming up with some amazing ideas of hooking up user 
> solutions to automatically commit to a Github repo 
> 2. Possibility of transfering *4clojure.com <http://4clojure.com> *-or- 
> *4clojure.org 
> <http://4clojure.org> *over to us so that we can host 4ever-clojure there 
> (instead of on a separate domain)
>
> Thanks!
> - Mitesh
>
> On Tuesday, July 6, 2021 at 5:56:10 PM UTC+5:30 Srihari Sriraman wrote:
>
>> Hey Alan, we really like 4clojure. We've suggested using it for training 
>> most people at nilenso and we're very thankful to you and all the 
>> contributors for that!
>> We (nilenso) would be up for picking up the hosting costs, and also some 
>> other operations or development work if needed.
>>
>> It would be even better if we could work together and turn this into a 
>> community owned project (ex: clojurists together 
>> <http://clojuriststogether.org>). That might also assuage your concerns 
>> about data ownership.
>>
>> The questions, and solutions that the community has put together on 
>> 4clojure over the last decade are very valuable as a learning tool. Perhaps 
>> we can find a way to keep them around without attributing them to a user? 
>> One idea might be to deactivate all existing accounts, and remove the user 
>> data (email, passwords, other PII) etc while keeping the questions and 
>> solutions from those users.
>>
>> We would be sad to see 4clojure go away, hope we can find a way for it to 
>> live on.
>>
>> Cheers,
>> Srihari
>>
>> On Tuesday, July 6, 2021 at 1:12:44 PM UTC+5:30 Robert P. Levy wrote:
>>
>>> Hi Alan,
>>>
>>> Just as a thought.  If it's minimal work on your end (eg. if the folks 
>>> from Roam research who chimed in above pick it up) why not clear the 
>>> password hashes and let the new maintainer handle the communication that 
>>> passwords need to be reset?
>>>
>>> Rob
>>>
>>> On Sun, Jul 4, 2021 at 1:26 PM Alan Malloy  wrote:
>>>
>>>> TL;DR: Turning off 4clojure.com by the end of July 2021
>>>>
>>>> Hello, 4clojure problem solvers. You've probably noticed SSL errors on 
>>>> 4clojure.com over the last week. The old decrepit system 4clojure runs 
>>>> on has finally gotten out of date enough that I can't even figure out how 
>>>> to get it recent enough that SSL certs will auto-renew anymore.
>>>>
>>>> In principle I could start from scratch on a new server and move 
>>>> 4clojure over, but I won't. 4clojure has been piggybacking along on a 
>>>> server that I use for personal reasons, and over the years I have less and 
>>>> less reason to keep paying for that server - it's now pretty much just 
>>>> 4clojure costing me an embarrassing amount of money every month because I 
>>>> haven't wanted to disappoint the community by shutting it down. This SSL 
>>>> thing is just what made me finally pull the trigger.
>>>>
>>>> I don't have a specific EOL date in mind, but so

[ANN] Discontinuing 4clojure.com

2021-07-04 Thread Alan Malloy
TL;DR: Turning off 4clojure.com by the end of July 2021

Hello, 4clojure problem solvers. You've probably noticed SSL errors on 
4clojure.com over the last week. The old decrepit system 4clojure runs on 
has finally gotten out of date enough that I can't even figure out how to 
get it recent enough that SSL certs will auto-renew anymore.

In principle I could start from scratch on a new server and move 4clojure 
over, but I won't. 4clojure has been piggybacking along on a server that I 
use for personal reasons, and over the years I have less and less reason to 
keep paying for that server - it's now pretty much just 4clojure costing me 
an embarrassing amount of money every month because I haven't wanted to 
disappoint the community by shutting it down. This SSL thing is just what 
made me finally pull the trigger.

I don't have a specific EOL date in mind, but sometime near the end of the 
month, since that's the billing cycle. Until that time, 4clojure still 
works, as long as you don't mind clicking through the security warnings - 
it really is still me hosting the site, and since the connection is still 
HTTPS (albeit with an invalid cert) I think that means your data is still 
safe. If you have solutions to problems you're proud of, you've still got 
some time to print them out and put them up on your refrigerator.

I'm not seeking new maintainers. I'd feel uncomfortable handing over a 
database with so many email addresses and password hashes in it to anyone. 
The service has had a good run - just over a decade since the first release 
.
 
I hope you enjoyed it during that time.

-- 
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/clojure/385cdef8-fa40-47ba-b5b1-0b3a7cc34935n%40googlegroups.com.


Re: Strictly tagged clojure

2015-08-08 Thread Alan Malloy
That might be a nice feature, but it would be quite different from what we 
did. We kept our extension (almost) entirely additive, so that old code 
will have unchanged behavior in strict mode, and strict code will continue 
to compile and run correctly when compiled with a version of clojure with 
no support for this strict mode. Your proposed feature would create 
function declarations that are uncompilable in any existing version of 
clojure, which I doubt anyone would find acceptable anytime soon.

On Saturday, August 8, 2015 at 4:44:02 AM UTC-7, Shantanu Kumar wrote:

 This is a very useful enhancement indeed. I wonder if it is feasible (or 
 if it makes sense) to extend this to have type based overloading:

 (defn foo
   ([^TypeA a] ..)
   ([^TypeB b] ..))

 Shantanu

 On Friday, 7 August 2015 11:40:42 UTC+5:30, Alex Miller wrote:

 Hey Reid, 

 I've forwarded this over to Rich and Stu to take a look at.

 Alex

 On Thursday, August 6, 2015 at 11:46:09 AM UTC-5, Reid McKenzie wrote:

 Hello all,

 Alan Malloy and I recently implemented[1] and contributed[2] an opt-in
 strict tags mode to Alexander Yakushev's Skummet compiler. To
 summarize the linked blog post and merge request, we created the
 `clojure.core/*strict-tags*` dynamic var which may either be set by
 users at the namespace level a la `clojure.core/*warn-on-reflection*`
 or set on a per-fn basis with the `^:strict` metadata annotation. When
 in strict mode, type hints are interpreted not as optional and late
 checked hints (the Clojure default) but as eagerly checked static
 types on tagged locals and expressions.

 The effect of these changes is to greatly reduce the number of
 checkcast instructions emitted when performing tagged interop should
 users opt into using strict mode and accept the requisite
 responsibility for managing their types.

 While the odds that these changes will be accepted as-is are slim, we
 think they represent a valuable addition to the language and so
 present them for your consideration.

 - Reid

 [1] - http://blog.factual.com/strictly-tagged-clojure
 [2] - https://github.com/alexander-yakushev/clojure/pull/1



-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Re: Size of Java serialized Clojure data structures

2015-08-07 Thread Alan Malloy
You must be doing something wrong, or describing your method badly, because 
the vector [:a1 1] doesn't take nearly that much space in my experiments. 
The first object you write to a stream requires quite a bit of overhead, 
but after that future objects are relatively cheap. Here's an example you 
can try yourself:

user (def baos (ByteArrayOutputStream.))
user (def oos (ObjectOutputStream. baos))
user (.writeObject oos [:a1 1])
user (.size baos)
671
user (.writeObject oos [:a1 1])
user (.size baos)
719
user (.writeObject oos [:a1 1])
user (.size baos)
767
user (.writeObject oos [:x 2])
user (.size baos)
845

So the first write takes around 600 bytes of overhead, and each write of 
[:a1 1] takes around 40-50 bytes. Writing a new vector with two different 
objects takes more, because it can't reuse references to constants like 
:a1, but it is still just 80 bytes. Nowhere near 1KB per small vector.

On Friday, August 7, 2015 at 6:31:46 AM UTC-7, icamts wrote:

 Yes. I suggested nippy. The question is about the size of Java serialized 
 Clojure data structures. Can a two element vector be 1kB in size? Why 
 serialization in my REPL experiment (see the code following the link in my 
 previous mail) produces a 80MB byte buffer while prevayler logs are 1GB?

 Il giorno venerdì 7 agosto 2015 13:51:45 UTC+2, Gary Verhaegen ha scritto:

 You should probably look at Clojure-specific solutions, starting with EDN 
 (i.e. essentially pr-str), fressian, transit or nippy.

 Clojure data structures have a lot of properties that can be exploited 
 (we only care about the abstract type and the actual data), so a serializer 
 can make a lot of assumptions that a generic Java solution can't.




-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Re: [ANN] lein-4clj

2014-03-19 Thread Alan Malloy
Can you explain the difference between this 
and https://github.com/bfontaine/lein-fore-prob? I haven't really looked 
since back when https://github.com/broquaint/lein-foreclojure-plugin was 
new (in lein 1!), but it seems like there is a lein2 plugin already.

On Wednesday, March 19, 2014 4:37:46 PM UTC-7, Alex Engelberg wrote:

 4clojure http://www.4clojure.com/ is a great site for practicing 
 various datatypes and concepts in Clojure. However, the code editor on the 
 website is somewhat limited, mostly because it doesn't have a REPL to test 
 out individual parts of your code. I'm not affiliated with 4clojure in any 
 way, but I've created a leiningen plugin for working on 4clojure problems 
 in the comfort of your own IDE.

 https://github.com/aengelberg/lein-4clj
 See the readme for more information and examples.

 Enjoy!
 --Alex


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.


Re: Is ^{:once true} still necessary for lazy-seqs?

2014-02-20 Thread Alan Malloy
^:once is absolutely needed for lazy seqs, because it allows the 
closed-over variables to get cleared while the lambda is *still running*, 
rather than waiting for it to finish. You can see the difference in this 
repl session:

user (let [x (for [n (range)] (make-array Object 1)), f (^:once fn* [] 
(nth x 1e6))] (f))
#Object[] [Ljava.lang.Object;@402d3105
user (let [x (for [n (range)] (make-array Object 1)), f (fn* [] (nth x 
1e6))] (f))
; Evaluation aborted.

Of course you may need to tune the numbers to make sure it runs out of 
space on your machine, but the point is that without ^:once, the lambda f 
holds onto the head of x, in case f is called again. ^:once constitutes a 
promise to only ever call it once, and so the sequence is cleaned up as 
soon as possible. My example doesn't use LazySeq, but I hope you can see 
how the same considerations apply there.

On Tuesday, February 18, 2014 9:39:06 AM UTC-8, pron wrote:

 lazy-seq marks it's supplied lambdata with ^{:once true} to prevent the 
 memory leak described at the bottom of this page http://clojure.org/lazy
 .
 However, while going over the code for clojure.lang.LazySeq, I noticed 
 that ever since this commit by 
 Richhttps://github.com/clojure/clojure/commit/9253928ba2330b9929eb26577ba20047fb24c5de#diff-829faa850c65e040e132cd9243bf7ac2R42,
  
 LazySeq doesn't extend AFn, but rather contains a reference to the lambda, 
 fn, which it nullifies immediately after the first use, supposedly 
 preventing any leaks caused by closed locals.
 So my question is, is ^{:once true} still necessary for lazy-seqs, or does 
 this (pretty old) change to LazySeq make it redundant?

 Ron



-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.


Re: Project Euler problem in clojure

2013-06-20 Thread Alan Malloy
More importantly than any of these things, he is hanging onto the head of a 
very, very large sequence with (def lazytri (map triangle (range))). This 
will lead to serious memory pressure, and perhaps eventually a slowdown as 
this sequence takes up all the memory in his app and the GC strains to make 
a tiny bit of room for other temporary objects. Instead of defining it and 
then immediately using it, he should simply inline its definition into its 
use, so that the GC is able to free up the bits of it that are no longer in 
use.

On Thursday, June 20, 2013 7:23:43 AM UTC-7, Meikel Brandmeyer (kotarak) 
wrote:

 Hi,

 Am Donnerstag, 20. Juni 2013 15:19:40 UTC+2 schrieb John Holland:

 (defn triangle [n] (reduce + (range n))) 
 (def lazytri (lazy-seq (map triangle (range 


 Some quick idea: here is a major difference in your clojure and your java 
 implementation. You always recompute the whole sum for each step. While you 
 only increase a counter in the java version. A better lazytri 
 implementation would be:

 (def lazytri (reductions + (range 1 Long/MAX_VALUE)))

 You don't use sqrt in your clojure version? inc is faster than (+ 1 ...). 
 zero? is faster than (= 0 ...).

 Kind regards
 Meikel



-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: type-hints positioning convention?

2013-06-17 Thread Alan Malloy
Typehints for functions are only useful on vars. There is no code anywhere, 
as far as I know, that looks at the metadata attached to anonymous 
functions.

On Monday, June 17, 2013 11:04:45 AM UTC-7, Ambrose Bonnaire-Sergeant wrote:

 I'm not sure. I guess we're stuck with tagging locals at that point?

 Thanks,
 Ambrose


 On Tue, Jun 18, 2013 at 1:38 AM, Jim - FooBar(); 
 jimpi...@gmail.comjavascript:
  wrote:

  OK now I'm confused! If you are using an unnamed  fn form there is only 
 one place to put the return type-hin,t and that is between the 'fn' and the 
 '[...]'
 ...but, you've just demonstrated that this causes reflection...where else 
 can we put it?

 Jim


 On 17/06/13 18:33, Ambrose Bonnaire-Sergeant wrote:
  
 Seems like there's some trickery involved with using Vars. 

  This example seems to use reflection.

  user= (.length ((fn ^String [^String s] (.substring s 0 (.length s))) 
 a))
 Reflection warning, NO_SOURCE_PATH:1:1 - reference to field length can't 
 be resolved.
 1

  Thanks,
 Ambrose
  

 On Tue, Jun 18, 2013 at 1:15 AM, Ambrose Bonnaire-Sergeant 
 abonnair...@gmail.com javascript: wrote:

 Yes, it did. That's interesting. I have no idea where the .length method 
 is being inferred from in the last example. 

  Carry on :)
  
  Ambrose
   

 On Tue, Jun 18, 2013 at 1:10 AM, Jim - FooBar(); 
 jimpi...@gmail.comjavascript:
  wrote:

  so how about this then?


 nREPL server started on port 43830
 REPL-y 0.2.0
 Clojure 1.5.1
 Docs: (doc function-name-here)
   (find-doc part-of-name-here)
   Source: (source function-name-here)
  Javadoc: (javadoc java-object-or-class-here)
 Exit: Control+D or (exit) or (quit)

 user= (set! *warn-on-reflection* true)
 true
 user= (defn foo [^String s] (.substring s 0 (.length s)))
 #'user/foo
 user= (foo jim)
 jim
 user= (.length (foo jim))
 *Reflection warning, NO_SOURCE_PATH:1:1 - reference to field length 
 can't be resolved.*
 3
 user= (defn foo ^String [^String s] (.substring s 0 (.length s)))
 #'user/foo
 user= (.length (foo jim))
 3
 user= (defn ^String  foo [^String s] (.substring s 0 (.length s)))
 #'user/foo
 user= (.length (foo jim))
 3


 it worked both times didn't it?

 Jim 





 On 17/06/13 17:59, Ambrose Bonnaire-Sergeant wrote:

 After some investigation, the before-the-arglist syntax only seems 
 useful for defining fn's that return primitive types. 
 They don't seem to help resolve reflection calls.

  (require '[clojure.tools.analyzer :refer [ast]])

  ; this creates a double-emitting fn

  (ast (fn (^double [^double a] a)))
 ; =
  ;{:op :fn-expr,
 ; ...
 ; :methods
  ; ({:op :fn-method,
 ;   ...
 ;   :arg-types (#Type Ljava/lang/Object;),
  ;   :return-type #Type D}),   ;double return type here
 ;  ...
 ; :tag nil}  ; no tag
  
   ; this creates a regular old fn

  (ast (fn (^String [a] 1))) 
 ; =
 ;{:op :fn-expr,
   ; ... 
 ; ({:op :fn-method,
 ;   ...
 ;   :arg-types (#Type Ljava/lang/Object;),
 ;   :return-type #Type Ljava/lang/Object;}),  ;object return type
 ; ...
 ; :tag nil}  ; no tag
  
  ; this creates a String-hinted fn

   (ast ^String (fn a [a] 1))
  ;{:op :meta,
 ; ...
  ; :expr
 ; {:op :fn-expr,
 ;  ...
 ;  :methods
 ;  ({:op :fn-method,
 ;:arg-types (#Type Ljava/lang/Object;),
  ;:return-type #Type Ljava/lang/Object;}),
 ;  ...
 ;  :tag String}}
  
  I don't see where before-the-arglist is useful outside of primitive 
 fns.
  
  Thanks,
 Ambrose

 On Mon, Jun 17, 2013 at 7:59 PM, Jim - FooBar(); 
 jimpi...@gmail.comjavascript:
  wrote:

 Hi all,

 It seems to me that return type-hints can go either right after 
 defn, or after the doc-string. I generally, put the return type-hints 
 right before the argument vector and it seems to get rid of reflection. 
 However, I just had a look at core.contrib.strutils2 and the author(s) 
 put 
 the type hint right after 'defn' (before the var about to be defined) and 
 again it gets rid of reflection! Which one is it? both are acceptable?

 thanks in advance,

 Jim

 -- 
 -- 
 You received this message because you are subscribed to the Google
 Groups Clojure group.
 To post to this group, send email to clo...@googlegroups.comjavascript:
 Note that posts from new members are moderated - please be patient 
 with your first post.
 To unsubscribe from this group, send email to
 clojure+u...@googlegroups.com javascript:
 For more options, visit this group at
 http://groups.google.com/group/clojure?hl=en
 --- You received this message because you are subscribed to the Google 
 Groups Clojure group.
 To unsubscribe from this group and stop receiving emails from it, send 
 an email to clojure+u...@googlegroups.com javascript:.
 For more options, visit https://groups.google.com/groups/opt_out.


  
  -- 
 -- 
 You received this message because you are subscribed to the Google
 Groups Clojure group.
 To post to this group, send email to clo...@googlegroups.comjavascript:
 Note that posts from new members are moderated - please be patient with 
 your first 

Re: possible side-effect/problem in http://clojure.org/concurrent_programming

2013-06-14 Thread Alan Malloy
The laziness of map is irrelevant here, because .invokeAll is treating it 
as a collection and realizing it all immediately. Your version with for is 
just as lazy. What's actually changed is that your map and for produce 
entirely different outputs: the version with map calls test-fn, and the 
version with for produces a function which, when invoked, will call 
test-fn. Since the latter is what the original code you copied from does, 
of course only that version works. You could change your map to (map #(fn 
[] (test-fn % 1 5)) deliveries) as an easy fix, though personally I 
wouldn't use the #() syntax here; its closeness to a (fn) form is a little 
confusing. (map (fn [i] (fn [] (test-fn i 1 5))) deliveries) is equivalent, 
of course. Personally I prefer the version with the for-comprehension.

On Friday, June 14, 2013 2:30:04 AM UTC-7, Amir Wasim wrote:

 I was using the first example to make a process executing parallely


 (defn test-stm [nitems nthreads niters]
   (let [refs  (map ref (repeat nitems 0))
 pool  (Executors/newFixedThreadPool nthreads)
 tasks (map (fn [t]
   (fn []
 (dotimes [n niters]
   (dosync
 (doseq [r refs]
   (alter r + 1 t))
(range nthreads))]
 (doseq [future (.invokeAll pool tasks)]
   (.get future))
 (.shutdown pool)
 (map deref refs)))

  

 i was generating taks just like above as follows

tasks (map #(test-fn % 1 5) deliveries)

 But only one task was active at a time, although Executors was configured 
 with 4 threads. It occurred to me that map itself is lazy and it is 
 realized in doseq one at a time. A possible fix is to use for instead of 
 map to generate tasks

 I tried with the following

tasks (for [delivery_ deliveries] #(test-fn delivery_ 1 5))

 and it works and 4 threads are active during execution.





-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: I don't feel the absence of a debugger, because I've learnt enough that I don't ever need a debugger.

2013-05-28 Thread Alan Malloy
On Tuesday, May 28, 2013 1:01:46 PM UTC-7, Ben Mabey wrote:

  On 5/28/13 1:05 PM, Lee Spector wrote:
  
 On May 28, 2013, at 2:40 PM, Ben Mabey wrote:

  The flag is a system property: 
 -Dclojure.compiler.disable-locals-clearing=true.  So you can add that 
 string to your project.clj's :jvm-opts if you are using lein. This will, of 
 course, slow down your program but when I've used it in the past it hasn't 
 made it unusable for development.

  Thanks for the project.clj specifics Ben.

 It still isn't clear to me if/how I could then look at the locals after 
 hitting an unexpected exception. Perhaps Cedric's strategy described a couple 
 of messages back (which I didn't fully understand) would work here? But from 
 the lack of followup to this post 
 http://comments.gmane.org/gmane.comp.java.clojure.swank-clojure.devel/106 -- 
 I wonder if it still won't work when hitting unexpected exceptions.

  
 To do this I have been using nrepl-ritz's 'M-x 
 nrepl-ritz-break-on-exception'.  If you are using emacs and haven't looked 
 into ritz I would highly encourage taking the time to do so.  It is 
 painless to install these days and you can watch a nice presentation on it (
 https://github.com/pallet/ritz/tree/develop/nrepl#additional-resources).  
 If you aren't using emacs then I don't have any suggestions for you. :(
  
 Also, I guess I don't understand what locals clearing is in this context, but 
 why would this slow things down? If it's just preventing the clearing of 
 locals when handling an exception then I'd expect it to have no effect except 
 during an exception... Do you mean that it'll slow down code that does a lot 
 of exception handling in circumstances that aren't really exceptional? Or 
 will this flag do something very different than what I'm thinking, like 
 causing all locals everywhere to be retained forever? That'd cause problems 
 worse than just slowdowns, I would think.

  It would slow things down in that more things wouldn't be allowed to be 
 GCed as soon as they would be with locals clearing (the usual culprit being 
 lazy seqs).  Unfortunately,  I don't know enough of the details of how and 
 when locals clearing works to give you more details.  So I'd love to hear a 
 better explanation from someone who knows.


The principal problem of disabling locals-clearing is not slowing things 
down, but rather causing perfectly reasonable code to consume unbounded 
memory. For example, consider: ((fn [xs] (nth xs 1e8)) (range)). With 
locals clearing, the compiler makes sure that xs is available for GC as it 
is being processed, so that the working-set size is small. If locals 
clearing is disabled, the local reference xs is kept around in case a 
debugger wants to look at it, and so the head of xs is being held while it 
is realized, meaning a hundred-million-element range must be kept in memory 
until the function call completes.

It's definitely useful to be able to disable locals-clearing temporarily 
while debugging, but doing so in any kind of production app would be a 
disaster.

-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Bug in transients: Cannot add more than 8 items to a transient map

2013-05-11 Thread Alan Malloy
Also, maps don't have an ordering, so the function is misguided by 
definition. You can use a sorted-map, if having the map's keys is very 
important to you, but generally it's just confusion that leads to wanting 
this in the first place.

If you do decide the map must be sorted in a specific order, you could use 
something like 
https://github.com/flatland/useful/blob/develop/src/flatland/useful/map.clj#L222
 to 
create a sorted map whose comparator function knows about the ordering you 
want: (into (ordering-map [:a :b :c :d]) m), for example.

On Saturday, May 11, 2013 5:41:25 PM UTC-7, Andy Fingerhut wrote:

 What you are attempting to do is sometimes called bashing a transient in 
 place.  See these links for some discussion and examples:

 http://clojuredocs.org/clojure_core/clojure.core/assoc!
 http://clojuredocs.org/clojure_core/clojure.core/dissoc!

 Andy



 On Sat, May 11, 2013 at 3:51 PM, Wojciech Winogrodzki 
 wwinog...@gmail.comjavascript:
  wrote:

 Clojure 1.5.1.

 I'm trying to reorder a map. The keys in the map are known beforehand and 
 their order is undefined. So, I'm taking this map and construct a new 
 transient map with the keys ordered as I need them:

 defn reorder-map []
   (let [
 m {:j 10 :g 7 :b 2 :d 4 :e 5 :h 8 :i 9 :f 6 :c 3 :a 1 }
 kwds [:a :b :c :d :e :f :g :h :i :j]
 temp (transient {})
 ]
 (doseq [k kwds]
   (assoc! temp k (m k)))
 (persistent! temp)))

 It returns {:a 1, :b 2, :c 3, :d 4, :e 5, :f 6, :g 7, :h 8}. The order is 
 as I have defined, but there are *only 8 out of 10 items* in the new map.

 If I do the same with an atom, all items are taken into account, but the 
 order is not as expected:

 (defn reorder-map-2 []
   (let [
 a (atom {})
 m {:j 10 :g 7 :b 2 :d 4 :e 5 :h 8 :i 9 :f 6 :c 3 :a 1 }
 kwds [:a :b :c :d :e :f :g :h :i :j]
 ]
 (doseq [k kwds]
   (swap!  a assoc k (m k)))
 @a))

 It returns {:a 1, :c 3, :b 2, :f 6, :g 7, :d 4, :e 5, :j 10, :i 9, :h 8}

 I don't know the internals to judge in which order items are associated 
 in a map. It seems that normal association prepends; transient association 
 appends; atom association does not obey any particular order.

 Anyway,* it seems to be a bug in that the transient didn't accept more 
 than 8 items*. It should, I suppose.

 Or am I doing sth. very wrong?

 Thank you -






  -- 
 -- 
 You received this message because you are subscribed to the Google
 Groups Clojure group.
 To post to this group, send email to clo...@googlegroups.comjavascript:
 Note that posts from new members are moderated - please be patient with 
 your first post.
 To unsubscribe from this group, send email to
 clojure+u...@googlegroups.com javascript:
 For more options, visit this group at
 http://groups.google.com/group/clojure?hl=en
 --- 
 You received this message because you are subscribed to the Google Groups 
 Clojure group.
 To unsubscribe from this group and stop receiving emails from it, send an 
 email to clojure+u...@googlegroups.com javascript:.
 For more options, visit https://groups.google.com/groups/opt_out.
  
  




-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Quick question on protocols

2013-05-10 Thread Alan Malloy
Even when the interface and class you've extended them to are related by 
inheritance? I thought the most-derived implementation was chosen, and only 
when there's a tie like a class that implements two unrelated interfaces, 
both of which have had the protocol extended to them. If it were completely 
undefined, all sorts of useful idioms would become untenable. For example, 
you couldn't extend a protocol to Object and also to various other classes. 
Dave's scenario is like this, in which TUnion is more-derived than TBase, 
and so as far as I know should always win in the polymorphic dispatch. 
Reading through core_deftype's functions 'pref and 'find-protocol-impl seem 
to support this assertion; am I missing something?

On Friday, May 10, 2013 2:20:31 PM UTC-7, Stuart Sierra wrote:

 When you extend a protocol to multiple Java interfaces / abstract classes, 
 then call the methods on an instance which implements/extends more than one 
 of those, the result is *undefined*.

 The problem is that this permits multiple inheritance of concrete 
 behavior, the reason Java doesn't allow multiple base classes.

 Protocols do not (currently) have any mechanism to prefer one method 
 implementation over another.

 In general, I recommend extending protocols only to concrete types, not 
 interfaces.

 -S


 On Friday, May 10, 2013 4:45:57 AM UTC+10, Dave Kincaid wrote:

 I've not worked with protocols much, but saw a good fit recently. 
 However, I'm a little bit unsure about this situation. I have some Thrift 
 objects that I'd like to be able to easily unpack into maps, so I created a 
 protocol

 (defprotocol Unpackable
   (unpack [x]))

 Thrift has two main data types - structs and unions that need to be 
 handled differently. Structs always implement the interface TBase. Unions 
 extend the abstract class TUnion which in turn implements the interface 
 TBase. So I'm extending my protocol to these types like this:

 (extend-protocol IUnpackable
   TUnion
   (unpack [x] (unpack-union x))

   TBase
   (unpack [x] (unpack-struct x (get-meta-data (class x)

 It all seems to work correctly, but I'm a little unsure that it is 
 guaranteed to work especially in the case of a union. Since a union extends 
 TUnion, but also implements TBase will a call to (unpack the-union) do the 
 right thing (go to unpack-union instead of unpack-struct) every time?

 Thanks.



-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Quick question on protocols

2013-05-10 Thread Alan Malloy
Object is a little special, yes, so it was a bad example for me to use. But 
the code used for deciding which protocol implementation to use is pretty 
straightforwardhttps://github.com/clojure/clojure/blob/c0b81aa9d7ef30a5c252367c162bf7fb410ea4d7/src/clj/clojure/core_deftype.clj#L483-L502
.

   1. If the class implements the protocol's associated interface directly, 
   call through that
   2. If the object's class has been extended to the protocol specifically, 
   use that implementation
   3. Walk up the superclass chain (not including Object), seeing if any of 
   the concrete classes this class extends support the protocol. If so, use 
   the first one you find (which will be the most-derived class with an 
   implementation).
   4. Look through the set of all interfaces implemented by this object, 
   and see if the protocol is extended to any of them. If only one interface 
   supports the protocol, use it. If two interfaces X and Y both support the 
   protocol, and X is a superinterface of Y, then Y is preferred over X; 
   otherwise, the implementation is chosen arbitrarily.
   5. Finally, if the protocol is extended to Object, use that 
   implementation

Now, that's a description of the current implementation, and not any 
documented guarantee, but it seems like Rich went to a lot of effort to 
ensure that if you extend to a class (or interface) and its subclass (or 
subinterface), then the most concrete implementation will be used. I really 
don't think this will change in any Clojure version, and think this is 
something that you can safely rely on for your protocol implementations.

On Friday, May 10, 2013 3:16:18 PM UTC-7, David Nolen wrote:

 It was my impression that extending to Object is handled as a special case 
 - much like extend-type default in ClojureScript.


 On Fri, May 10, 2013 at 6:06 PM, Alan Malloy al...@malloys.orgjavascript:
  wrote:

 Even when the interface and class you've extended them to are related by 
 inheritance? I thought the most-derived implementation was chosen, and only 
 when there's a tie like a class that implements two unrelated interfaces, 
 both of which have had the protocol extended to them. If it were completely 
 undefined, all sorts of useful idioms would become untenable. For example, 
 you couldn't extend a protocol to Object and also to various other classes. 
 Dave's scenario is like this, in which TUnion is more-derived than TBase, 
 and so as far as I know should always win in the polymorphic dispatch. 
 Reading through core_deftype's functions 'pref and 'find-protocol-impl seem 
 to support this assertion; am I missing something?

 On Friday, May 10, 2013 2:20:31 PM UTC-7, Stuart Sierra wrote:

 When you extend a protocol to multiple Java interfaces / abstract 
 classes, then call the methods on an instance which implements/extends more 
 than one of those, the result is *undefined*.

 The problem is that this permits multiple inheritance of concrete 
 behavior, the reason Java doesn't allow multiple base classes.

 Protocols do not (currently) have any mechanism to prefer one method 
 implementation over another.

 In general, I recommend extending protocols only to concrete types, not 
 interfaces.

 -S


 On Friday, May 10, 2013 4:45:57 AM UTC+10, Dave Kincaid wrote:

 I've not worked with protocols much, but saw a good fit recently. 
 However, I'm a little bit unsure about this situation. I have some Thrift 
 objects that I'd like to be able to easily unpack into maps, so I created 
 a 
 protocol

 (defprotocol Unpackable
   (unpack [x]))

 Thrift has two main data types - structs and unions that need to be 
 handled differently. Structs always implement the interface TBase. Unions 
 extend the abstract class TUnion which in turn implements the interface 
 TBase. So I'm extending my protocol to these types like this:

 (extend-protocol IUnpackable
   TUnion
   (unpack [x] (unpack-union x))

   TBase
   (unpack [x] (unpack-struct x (get-meta-data (class x)

 It all seems to work correctly, but I'm a little unsure that it is 
 guaranteed to work especially in the case of a union. Since a union 
 extends 
 TUnion, but also implements TBase will a call to (unpack the-union) do the 
 right thing (go to unpack-union instead of unpack-struct) every time?

 Thanks.

  -- 
 -- 
 You received this message because you are subscribed to the Google
 Groups Clojure group.
 To post to this group, send email to clo...@googlegroups.comjavascript:
 Note that posts from new members are moderated - please be patient with 
 your first post.
 To unsubscribe from this group, send email to
 clojure+u...@googlegroups.com javascript:
 For more options, visit this group at
 http://groups.google.com/group/clojure?hl=en
 --- 
 You received this message because you are subscribed to the Google Groups 
 Clojure group.
 To unsubscribe from this group and stop receiving emails from it, send an 
 email to clojure+u...@googlegroups.com javascript:.
 For more

Re: style questions -- clojure newbie

2013-04-23 Thread Alan Malloy
Raynes recently released https://github.com/Raynes/least, a Clojure client 
for the last.fm API. Have you looked into just using his, rather than 
reinventing the API layer yourself?

On Tuesday, April 23, 2013 2:12:37 PM UTC-7, Huey Petersen wrote:

 Howdy,

 I'm a clojure fan but quite new to writing clojure.  I'm writing my first 
 app and had a few style questions.

 I'm doing a web service call to the lastfm api.  It returns some json like:

 {
 results: {
 albummatches: {
 album: [
 {
 name: In The Future,
 artist: Black Mountain,
 image: [{
 size: small,
 #text: http://example.com/image/url.jpg;
 }]
 }
 ]
 }
 }
 }


 One notes is that the 'album' key in the json can either be missing (0 
 results) a map itself (1 result) or the array (2+ results).

 I then want to turn it into structure like:

 {
 albums: [{
 name: In The Future,
 artist: Black Mountain,
 images: {
 small: http://example.com/image/url.jpg;
 }
 }]
 }


 Here is the clojure code I came up with:

 (defn- transform-album-images [images]
 (into {} (map (fn [image] [(:size image) (:#text image)]) images)))
  
 (defn- transform-album [album]
   (let [album (select-keys album [:name :artist :image])
 album (update-in album [:image] transform-album-images)
 album (clojure.set/rename-keys album { :image :images })]
 album))
  
 (defn search [term]
   (let [albums (api/get {:method album.search :album term})
 albums (get-in albums [:results :albummatches :album] [])
 albums (if (vector? albums) albums (vector albums))
 albums (map transform-album albums)]
 {:albums albums}))



 My main question is whether this is at all 'idomatic' clojure.  I have a 
 few specific questions too.

 - I broke out two functions -- transform-album-images and transform-album 
 -- because I wasn't sure how to squeeze them into the first function.  They 
 really have no purpose outside of the 'search' function though.  I don't 
 know why, but it kinda bugs me because it seems to detract from the main 
 function 'search' as they have to appear above 'search'.

 - the (api/get ...) call talks to an external webservice.  Everything else 
 is a 'pure' function.  Is including the (api/get) call inside the 'search' 
 function bad?  I'm a bit hazy on the write split from pure / non-pure code.

 I feel like transforming data between two representations with a side 
 effect at each end is like 90% of code I write so I'd like to get a good 
 feel for doing this in clojure :)

 Thanks for any tips.


-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Arrays and indexes

2013-04-18 Thread Alan Malloy
(for [[y cols] (map-indexed vector rows)
  [x cell] (map-indexed vector cols)]
  (display cell y x))

?

On Thursday, April 18, 2013 3:14:19 AM UTC-7, edw...@kenworthy.info wrote:

 So, I want a 2 dimensional array.

 I think the best way to implement this is a vector of vectors.

 Now I want to display that array drawing each element relative to its 
 position in the array.

 Is the best way to use doseq and manually maintain the indices? Or is it 
 to use nested for-loops manually iterating of the vector-of-vectors?


-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Type hinting generated functions

2013-04-15 Thread Alan Malloy
If all the functions you want to generate accept doubles, you can just 
modify str-sym to include a (with-meta (symbol ...) {:tag 'double}) and it 
should generate exactly the code in your hand-written version. As an aside, 
there's no reason for str-sym to be a macro: it should just be a function 
like (symbol (apply str args)).

On Monday, April 15, 2013 2:59:27 AM UTC-7, dannyg wrote:

 Hi all, 

 I was writing some code and became idly curious about making it more 
 'general' but still performant.  Specifically I thought it'd be neat 
 to auto-generate a series of vector-based operations from a single 
 specification.  So instead of many functions like this by hand: 

 (defn vadd3 [[^double a1 ^double a2 ^double a3] [^double b1 ^double b2 
 ^double b3]] 
   [(+ a1 b1) (+ a2 b2) (+ a3 b3)]) 

 I'd instead have a macro generate them. Pretty low level ops (yes not 
 really suited for clojure but I like exploring the limits) and I was 
 pretty happy with the performance: 

 (bench 1e7 (vadd3 [1.1 2.2 3.3] [2.2 3.3 4.4])) 
 Elapsed time: 1799.587 msecs 

 Here we have my attempt to generalise it: 

 (defmacro -make-vec-ops 
  [{:keys [name op start end] :or {start 2}}] 
  (cons `do (for [n (range start end)] 
  `(defn ~(str-sym- \v n name) 
 ~name 
  [[~@(for [x (range n)] (str-sym- a x)) :as ~'a] 
   [~@(for [x (range n)] (str-sym- b x)) :as ~'b]] 
 [~@(for [x (range n)] 
  `(~op ~(str-sym- a x) ~(str-sym- b x)))] 

 (bench 1e7 (v3add [1.1 2.2 3.3] [2.2 3.3 4.4])) 
 Elapsed time: 2238.391 msecs 

 The performacne isn't 'too bad' at 25% lower.  But it's frustratingly 
 close to matching the original too!  I tried toying with some other 
 answers I found about generating type-metadat.  Alas, my resulting 
 macros were either malformed (unsupported binding forms) or didn't 
 appear to generate anything in the final functions/performance was the 
 same. 

 I'd love to be wowed by a simple solution!  Heck 'any' solution that 
 works ;) 

 As an aside, the macro is pretty ugly... I tried extracting the vector 
 deconstruction to a second macro, like this 

   (defmacro -varg [a n] 
 `(~@(for [x (range n)] (str-sym- a x)) :as ~a)) 

 where str-sym- 

   (defmacro str-sym-  [ args] `(symbol (str ~@args))) 

 But couldn't quite to get it to work :/ 

 Cheers, 
 Daniel Grigg 


-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Difficulty working with complex protobuf objects [protobuf 0.6.2]

2013-04-11 Thread Alan Malloy
0.6.2 is six months old. I don't think anything about this has changed 
since then, but you should at least try [org.flatland/protobuf 0.7.2] and 
see if that does what you expect.

On Thursday, April 11, 2013 8:39:12 AM UTC-7, David Pidcock wrote:


 I have some Java classes generated elsewhere (not by the lein proto 
 plugin) and I'm wanting to use them as the basis for the [protobuf 0.6.2] 
  code interactions (for interdependency with an existing java project) 

 One thing I noticed about the output in REPL is that only the first key is 
 presented to the screen from protobuf.core.PersistentProtocolBufferMap

 Even  (keys my-proto) only shows the first key

 At first I thought I'd screwed something up,   but when I try 
 (:some-key   my-proto)   
 I get the expected result. 

 The data referenced by :some-key in this instance is another map  -- 
 almost all of the data contained in the message is complex like this. 

 Is this a bug in protobuf.core.PersistentProtocolBufferMap?  Or am I 
 missing something?




-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Function recurring regardless of condition

2013-04-08 Thread Alan Malloy
You might be interested in 
https://github.com/amalloy/clusp/blob/master/src/snusp/core.clj, my Clojure 
interpreter for SNUSP (which is brainfuck with different control-flow 
mechanics). It's purely functional, and IMO does a good job of separating 
concerns; both of those are things it sounds like you were having trouble 
with, so hopefully reading it will give you some ideas. Basically my 
approach is to have an object (hash-map) that represents the state of the 
interpreter (the world), and compile each instruction to a function 
before doing anything. Then, I just look up the instruction at the current 
position, call it on the world, and use the returned world for the next 
step.

On Saturday, April 6, 2013 4:49:36 PM UTC-7, Andrew Spano wrote:

 Hello, I'm a new clojure programmer--but after learning a bit of clojure 
 including iteration, some core high order functions, and a little bit about 
 state management I decided to try my hand on a brainfuck interpreter.

 Located here:

 https://github.com/recursor94/brainfuck.clj/blob/master/brainfuck/src/brainfuck/fuck.clj

 Handling looping complicated things.  And the way I chose to deal with 
 looping resulted in some pretty ugly functions.  I hope to clean that up in 
 the future and refractor the code into a more functional style after I've 
 finished the first draft.

 The issue is in a particular function which never stops recuring even when 
 the condition for recuring is false:

 (defn exec-instruction
   executes each function in the codemap vector in sequential order


 ([end-index]
(inc-code-pos)  ;;side affect function that moves the code pointer (I 
 have both a code pointer and a data pointer in my interpreter)
(loop [index (:index @codemap)]
  (let [codevec (@codemap :struct)
instruct (get codevec index)]
(println index: index
 instruct instruct
 minus one index: (- end-index 2))
(instruct))
  (when-not (= index (- end-index 1))
(println yeah you are)
(inc-code-pos)
(recur (inc index)
 ;;end problem
 ([]
(doseq [instruct (@codemap :struct)]
  (instruct) ;;higher order functions ftw
  (inc-code-pos


 And here is the function that triggers this function:

 (defn begin-loop
   run through a loop until current cell drops to zero
   []
   (loop [loop-counter (@cells @pointer)
  end-loop (find-end (@codemap :index)) ;;find-end returns an integer
  pos (@codemap :index)]
 (println cell counter: loop-counter
  other:  (@cells @pointer)
  at 0: (@cells @pointer)
  also: end-loop)  ;;debug output
 (exec-instruction end-loop)
 (when-not (= loop-counter 0)
   (recur (@cells @pointer) end-loop pos


 The program is supposed to stop when it reaches a closing end brace and jump 
 back to the opening brace in the code.  But the output indicates that the 
 program never gets passed the first iteration.

 For example, given this hello world brainfuck program:

  
 ++[+-]++.+.+++..+++.++.+++..+++.--..+..

 The program outputs the following:
 index: 11 instruct #'brainfuck.fuck/+pointer minus one index: 39
 yeah you are
 index: 12 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 13 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 14 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 15 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 16 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 17 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 18 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 19 instruct #'brainfuck.fuck/+pointer minus one index: 39
 yeah you are
 index: 20 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 21 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 22 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 23 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 24 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 25 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 26 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 27 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 28 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 29 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 30 instruct #'brainfuck.fuck/+pointer minus one index: 39
 yeah you are
 index: 31 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 32 instruct #'brainfuck.fuck/plus minus one index: 39
 yeah you are
 index: 33 instruct #'brainfuck.fuck/plus minus one 

Re: - operator and monads

2013-04-03 Thread Alan Malloy
Not even that: - is not a function composition operator at all, but a 
form-rewriting macro. You can perfectly well write (- [x xs] (for (inc 
x))) to get (for [x xs] (inc x)), and that is not composing any functions. 
The two things are entirely separate.

On Wednesday, April 3, 2013 12:45:55 PM UTC-7, Marko Topolnik wrote:

 I guess you mean the monadic bind operation, but - is not it. The only 
 conceptual connection between *bind* and - is that they are both some 
 kind of function composition operators.

 -marko

 On Wednesday, April 3, 2013 8:21:43 PM UTC+2, Plinio Balduino wrote:

 Hi there

 Is it correct to say that - operator is a kind of monad in Clojure?

 Thank you in advance.

 Plínio Balduino
  


-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Attempt at rethrow macro

2013-04-01 Thread Alan Malloy
On Monday, April 1, 2013 10:26:43 AM UTC-7, Alf wrote:

 I am guessing the problem is that the rethrow macro is expanded and passed 
 to the reader/compiler before the handle-ex macro is. And at that point the 
 compiler sees catch as a standalone-symbol, not as part of the try 
 special form. Macro-experts, please correct me :)

 Tried to quickly catch up with 
 http://www.infoq.com/presentations/Clojure-Macros, but infoq seems slow.

 On 1 April 2013 17:21, Bill Robertson billrob...@gmail.com 
 javascript:wrote:

 I was all excited when I was able to consolidate a lot of try/catch logic 
 behind a macro earlier this morning. All was good.

 I felt like I could do a better job of communicating my intentions in the 
 code though with a rethrow construct rather than writing 
 (catch FooException #f (throw #f))

 I would have liked to have been able to simply write
 (rethrow FooException)

 This failed. Poking around the docs a bit, I see that try/catch is a 
 special form. Which makes sense.

 user= (defmacro rethrow [ex-class] `(catch ~ex-class x# (throw x#)))
 #'user/rethrow
 user= (defmacro handle-ex [message  body] `(try ~@body (rethrow 
 IllegalArgumentException) (catch Exception x# (throw 
 (IllegalArgumentException. message)
 #'user/handle-ex
 user= (handle-ex no (throw (IllegalArgumentException. yes)))
 CompilerException java.lang.RuntimeException: Unable to resolve symbol: 
 catch in this context, compiling:(NO_SOURCE_PATH:1:1)

 It was a longshot, but I tried to qualify catch. That fails too, because 
 it's not really there...

 user= (defmacro rethrow [ex-class] `(clojure.core/catch ~ex-class x# 
 (throw x#)))
 #'user/rethrow
 user= (defmacro handle-ex [message  body] `(try ~@body (rethrow 
 IllegalArgumentException) (catch Exception x# (throw 
 (IllegalArgumentException. message)
 #'user/handle-ex
 user= (handle-ex no (throw (IllegalArgumentException. yes)))
 CompilerException java.lang.RuntimeException: No such var: 
 clojure.core/catch, compiling:(NO_SOURCE_PATH:1:1)

 Is this possible to do within the normal bounds of the language?

 Thanks!


  -- 
 -- 
 You received this message because you are subscribed to the Google
 Groups Clojure group.
 To post to this group, send email to clo...@googlegroups.comjavascript:
 Note that posts from new members are moderated - please be patient with 
 your first post.
 To unsubscribe from this group, send email to
 clojure+u...@googlegroups.com javascript:
 For more options, visit this group at
 http://groups.google.com/group/clojure?hl=en
 --- 
 You received this message because you are subscribed to the Google Groups 
 Clojure group.
 To unsubscribe from this group and stop receiving emails from it, send an 
 email to clojure+u...@googlegroups.com javascript:.
 For more options, visit https://groups.google.com/groups/opt_out.
  
  



That is the opposite of the problem: `try` searches for a `catch` without 
macroexpanding its body forms. You could come at the problem differently, 
by writing a macro that expands to an entire try+catch 
form: (try-rethrowing [IllegalArgumentException] (do a b c) (catch 
Exception e e) (finally (foo))) is a macro that you could successfully 
write.

-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Attempt at rethrow macro

2013-04-01 Thread Alan Malloy
This is how every macro and special form works. I know you like to 
complain, but the alternative is simply not possible: macros have complete 
control of expanding their bodies, and any macros therein are expanded 
later, not before. Try writing a macro system that goes the other way, and 
see how disastrous the result is.

On Monday, April 1, 2013 1:00:31 PM UTC-7, Cedric Greevey wrote:

 IMO, the real problem here is try not macroexpanding its body before 
 looking for its catches. IMO that's a bug, and indeed that the rethrow 
 macro doesn't work when the s-expression it expands to would work in its 
 place represents a violation, at least in spirit, of homoiconicity. There 
 are operators that are special and can't be supplied via macro. That's 
 wrong.
  

-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Floating point comparator issue?

2013-03-29 Thread Alan Malloy
Comparator.compare returns an int. (int 0.2) and (int -0.2) both
return 0. Thus, your comparator is returning 0, saying I don't care
what order these go in.

On Mar 29, 6:44 pm, JvJ kfjwhee...@gmail.com wrote:
 Alright check this out:

 ;; Normal subtraction as comparator sorts in ascending order
 (sort-by identity #(- %1 %2)   [1  -1])
 (-1 1)

 ;; Reverse subtraction as comparator sorts in descending order
 (sort-by identity #(- %2 %1)   [1  -1])
 (1 -1)

 ;;===
 ;; And now with values of -0.1, 0.1

 ;; Reverse subtraction as comparator sorts in descending order
 (sort-by identity #(- %2 %1)   [0.1  -0.1])
 (0.1 -0.1)

 ;; Normal subtraction STILL sorts in descending order??
 (sort-by identity #(- %1 %2)   [0.1  -0.1])
 (0.1 -0.1)

-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Working with a huge graph - how can I make Clojure performant?

2013-03-28 Thread Alan Malloy
Have you looked at https://github.com/jordanlewis/data.union-find ? 
Personally, I'd prefer it to Christophe's implementation, since his blog 
post seems to start with I dislike this algorithm; I also helped out a 
bit in writing this version.

On Monday, March 11, 2013 10:37:39 AM UTC-7, Balint Erdi wrote:

 Hey,


 I got an assignment to implement an algorithm to calculate strongly 
 connected components in a graph (
 http://en.wikipedia.org/wiki/Kosaraju's_algorithm). The graph is rather 
 big, it has ~900.000 vertices.


 In its first pass, it needs to do a depth-first search on the graph and 
 calculate the finishing time for each node (the finishing time for a node 
 is a number from 0…V-1 where V is the number of vertices). Potentially 
 several depth-first search need to be launched (done in the finishing-times 
 function below) to discover all components.


 The version I pasted below is the most performant. It discovers ~600.000 
 vertices (2/3 of all vertices). However, on subsequent 
 dfs-by-finishing-times it becomes extremely slow (exploring a handful of 
 additional nodes/second) and I'm not sure why.


 Here are a few things I tried to speed up the algorithm:


 * rewrite to a recursive function (not tail-recursive) and use lazy-seqs

 * define dfs-by-finishing-times in finishing-times so that the whole graph 
 (G) does not have to be passed at each call.

 * use persistent data structures everywhere instead of transients (I know 
 this would only slow things down but it did not hurt to try)

 * use a profiler (VisualVM) to learn where the bottlenecks are. I'm not 
 very proficient with profilers but I could not extract any valuable 
 information


 Here are the code snippets in question:

 (I also pasted it here: 
 https://www.refheap.com/paste/3840cc772cc3a5b1d9c4f1db3 for better 
 readability)

 (defn dfs-by-finishing-times

   ([G u]

  (dfs-by-finishing-times G u #{}))

   ([G u explored]

  (loop [[v  vs :as stack] (list u), explored (transient explored), 
 lhalf [], rhalf [],  iter-cnt 0]

  (if (seq stack)

   (let [neighbors (persistent!

(reduce

 (fn [c u] (if (explored u) c (conj! c u)))

 (transient [])

 (G v)))]

 (cond

  (explored v) (recur vs explored lhalf rhalf (inc iter-cnt))

  (empty? neighbors) (recur vs (conj! explored v) (conj lhalf 
 v) rhalf (inc iter-cnt))

  :else (recur (reduce (fn [stack e] (cons e stack)) vs 
 neighbors)

(conj! explored v)

lhalf

(cons v rhalf)

(inc iter-cnt

   (concat lhalf rhalf)))

  ))


 (defn finishing-times [G vertices]

   The first pass of Kosaraju's algorithm.

Scan the transpose graph of G, and mark the finishing time for each.

G should already be the transposed graph

   (loop [[u  vs :as stack] (seq vertices)

   explored #{},

   finished []]

  (if (nil? u)

finished

(let [path (dfs-by-finishing-times G u explored)

  new-explored (into explored path)]

  (recur (remove new-explored vs)

 new-explored

 (into finished path))

 Do you have any insights into what technique I could use to speed up my 
 algorithm? I'm pretty sure I'm missing a key point but I'm not sure 
 what. Presumably the whole algorithm runs under 10 seconds in C# on the 
 same graph so this is rather embarrassing :)

 Appreciate your help,

 Balint


-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Quirk with printing regexps

2013-03-28 Thread Alan Malloy
On Thursday, March 28, 2013 5:36:45 PM UTC-7, Andy Fingerhut wrote:


 I don't understand why (re-pattern a\\\nb) would match the same thing.  
 I would have guessed that it wouldn't, but it does indeed do so.  For all I 
 know that could be bug or weird dark corner case in the Java regex 
 library.  I would have expected such a regex to match the only the 
 4-character sequence a,backslash,newline,b.


That's a string with four characters: a, backslash, newline, b. When the 
regex engine compiles that, it sees the backslash-newline construct as 
unnecessary escaping of the newline character: since newline is neither a 
metacharacter nor alphabetic, backslash-newline just matches the single 
character newline.

The j.u.regex.Pattern javadoc, in explaining backslash-quoting, contains: 
It is an error to use a backslash prior to any alphabetic character that 
does not denote an escaped construct; these are reserved for future 
extensions to the regular-expression language. A backslash may be used 
prior to a non-alphabetic character regardless of whether that character is 
part of an unescaped construct.

-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Map destructuring variations in Pedestal

2013-03-20 Thread Alan Malloy
Yes. Apparently you can put whatever garbage you want into the `:or` map: 
each local is looked up in that map to see if it has a default, but nobody 
ever checks to see if there are unused keys in the defaults map. So `:or 
{::type :jety}` has no impact at all on the generated code: there is no 
local named `::jetty` (of course, since that would be an illegal name for a 
local).

On Tuesday, March 19, 2013 11:19:27 PM UTC-7, Sean Corfield wrote:

 Pretty sure it's just a typo / bug. I think it should read: 

{servlet ::servlet 
 type ::type 
 :or {type :jetty} 
 :as service-map} 

 On Tue, Mar 19, 2013 at 10:09 PM, Matching Socks 
 phill...@gmail.comjavascript: 
 wrote: 
  I'm puzzled by two :or syntaxes that are used in 
 io.pedestal.service.http, 
  from [io.pedestal/pedestal.service 0.1.1-SNAPSHOT], which is where 
  following along with the Getting Started got me. 
  
  In one place, it pairs :or with a map whose keys are symbols being bound 
 in 
  the outer form: 
  
   {routes ::routes 
  file-path ::file-path 
  resource-path ::resource-path 
  method-param-name ::method-param-name 
  :or {file-path nil 
   resource-path public 
   method-param-name :_method} 
  :as service-map} 
  
  A little farther down, it pairs :or with a map whose key is a key from 
 the 
  map being destructured: 
  
{servlet ::servlet 
  type ::type 
  :or {::type :jetty} 
  :as service-map} 
  
  In a tiny experiment, I don't see the second way working.  But the 
 compiler 
  does not emit any message.  Is there something subtle going on? 
  
  helloworld.server= (defn a [{x :X y :Y :or {y 3}}] (vector x y)) 
  #'helloworld.server/a 
  helloworld.server= (a {:X 7}) 
  [7 3] 
  helloworld.server= (defn a' [{x :X y :Y :or {:Y 3}}] (vector x y)) 
  #'helloworld.server/a' 
  helloworld.server= (a' {:X 7}) 
  [7 nil] 
  
  
  
  -- 
  -- 
  You received this message because you are subscribed to the Google 
  Groups Clojure group. 
  To post to this group, send email to clo...@googlegroups.comjavascript: 
  Note that posts from new members are moderated - please be patient with 
 your 
  first post. 
  To unsubscribe from this group, send email to 
  clojure+u...@googlegroups.com javascript: 
  For more options, visit this group at 
  http://groups.google.com/group/clojure?hl=en 
  --- 
  You received this message because you are subscribed to the Google 
 Groups 
  Clojure group. 
  To unsubscribe from this group and stop receiving emails from it, send 
 an 
  email to clojure+u...@googlegroups.com javascript:. 
  For more options, visit https://groups.google.com/groups/opt_out. 
  
  



 -- 
 Sean A Corfield -- (904) 302-SEAN 
 An Architect's View -- http://corfield.org/ 
 World Singles, LLC. -- http://worldsingles.com/ 

 Perfection is the enemy of the good. 
 -- Gustave Flaubert, French realist novelist (1821-1880) 


-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: set!

2013-03-13 Thread Alan Malloy
On Wednesday, March 13, 2013 2:46:06 PM UTC-7, puzzler wrote:

 On Wed, Mar 13, 2013 at 2:06 PM, Marko Topolnik 
 marko.t...@gmail.comjavascript:
  wrote:


 As far as I understand it, *set!* modifies the *thread-local* binding, 
 just like the *binding* macro, but doesn't delimit a definite scope of 
 validity for the binding. You can *set!* any dynamic var with the same 
 semantics.


 You can't just set! any dynamic var, you can only set! vars that are both 
 dynamic *and* have been bound again with the binding construct.

 = (def ^:dynamic a 2)
 #'user/a
 = (set! a 3)
 IllegalStateException Can't change/establish root binding of: a with set  
 clojure.lang.Var.set (Var.java:233)
 = (binding [a 1] (set! a 3))
 3


 This is why I'm puzzled about how things like (set! *unchecked-math* true) 
 are handled.  Clearly, in this special case you can use set! without first 
 calling binding.


Not really a special case, although I suppose you could argue it either 
way. These vars, too, must be bound before being set!. But the code that 
binds them is in the compiler: 
https://github.com/clojure/clojure/blob/master/src/jvm/clojure/lang/Compile.java#L72
 binds 
*unchecked-math*  *warn-on-reflection* before it starts compiling files. 
The only way you could make your own vars be set!able is to use them inside 
a context in which they've already been bound; for example, you could 
define a (let-me-set-stuff body) macro and evaluate the user's code in 
that context. That's basically the same as how the compiler and the repl 
work: they run all of your code in a context where bindings are 
established. 

-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Like if, but it composes functions

2013-02-20 Thread Alan Malloy
You can use fix to take some data that might not be right (say, an integer 
that might actually be a string) and fix it by applying read-string: (fix 
10 string? read-string). to-fix returns a function you can use to fix 
things.

On Wednesday, February 20, 2013 12:06:36 AM UTC-8, Laurent PETIT wrote:

 Hello, 

 Why the names fix / to-fix ? 

 2013/2/20 Alan Malloy al...@malloys.org javascript:: 
  Useful has functions that do this and more: fix or to-fix, according to 
  taste. Your iffn is just the three-argument case of to-fix: (def magnify 
  (to-fix pos? inc dec)). But fix and to-fix accept more or fewer 
 arguments as 
  well, so that (fix x pos? inc) is like (if (pos? x) (inc x) x), and 
 (to-fix 
  tall? shorten thin? fatten) is (fn [x] (cond (tall? x) (shorten x) 
 (thin? x) 
  (fatten x) :else x)). 
  
  Basically both of these functions look through their clause pairs and 
 apply 
  the first transform whose test matches. fix takes its focus argument 
  immediately, while to-fix returns a lambda that performs the requested 
  operation. 
  
  
  On Tuesday, February 19, 2013 9:53:57 PM UTC-8, James MacAulay wrote: 
  
  Sometimes I find myself writing code like this: 
  
  (defn magnify [n] (if (pos? n) (inc n) (dec n))) 
  
  ...and I want to get rid of all those ns. I've looked for a macro 
 like 
  this, but couldn't find it, so I wrote it: 
  
  https://gist.github.com/jamesmacaulay/4993062 
  
  Using that, I could re-write the above like this: 
  
  (def magnify (iffn pos? inc dec)) 
  
  I can imagine a condfn macro, too: 
  
  (def magnify2 (condfn pos? inc 
neg? dec 
:else identity) 
  
  Has this kind of conditional function composition been explored much? I 
  couldn't find anything like it in the standard library, but maybe I 
 wasn't 
  looking hard enough. 
  
  Cheers, 
  James 
  
  -- 
  -- 
  You received this message because you are subscribed to the Google 
  Groups Clojure group. 
  To post to this group, send email to clo...@googlegroups.comjavascript: 
  Note that posts from new members are moderated - please be patient with 
 your 
  first post. 
  To unsubscribe from this group, send email to 
  clojure+u...@googlegroups.com javascript: 
  For more options, visit this group at 
  http://groups.google.com/group/clojure?hl=en 
  --- 
  You received this message because you are subscribed to the Google 
 Groups 
  Clojure group. 
  To unsubscribe from this group and stop receiving emails from it, send 
 an 
  email to clojure+u...@googlegroups.com javascript:. 
  For more options, visit https://groups.google.com/groups/opt_out. 
  
  


-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Like if, but it composes functions

2013-02-19 Thread Alan Malloy
Useful has functions that do this and more: fix or to-fix, according to 
taste. Your iffn is just the three-argument case of to-fix: (def magnify 
(to-fix pos? inc dec)). But fix and to-fix accept more or fewer arguments 
as well, so that (fix x pos? inc) is like (if (pos? x) (inc x) x), and 
(to-fix tall? shorten thin? fatten) is (fn [x] (cond (tall? x) (shorten x) 
(thin? x) (fatten x) :else x)).

Basically both of these functions look through their clause pairs and apply 
the first transform whose test matches. fix takes its focus argument 
immediately, while to-fix returns a lambda that performs the requested 
operation.

On Tuesday, February 19, 2013 9:53:57 PM UTC-8, James MacAulay wrote:

 Sometimes I find myself writing code like this:

 (defn magnify [n] (if (pos? n) (inc n) (dec n)))

 ...and I want to get rid of all those ns. I've looked for a macro like 
 this, but couldn't find it, so I wrote it:

 https://gist.github.com/jamesmacaulay/4993062

 Using that, I could re-write the above like this:

 (def magnify (iffn pos? inc dec))

 I can imagine a condfn macro, too:

 (def magnify2 (condfn pos? inc
   neg? dec
   :else identity)

 Has this kind of conditional function composition been explored much? I 
 couldn't find anything like it in the standard library, but maybe I wasn't 
 looking hard enough.

 Cheers,
 James


-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: Like if, but it composes functions

2013-02-19 Thread Alan Malloy
Sorry, forgot to link to 
useful: 
https://github.com/flatland/useful/blob/develop/src/flatland/useful/fn.clj#L30

On Tuesday, February 19, 2013 9:53:57 PM UTC-8, James MacAulay wrote:

 Sometimes I find myself writing code like this:

 (defn magnify [n] (if (pos? n) (inc n) (dec n)))

 ...and I want to get rid of all those ns. I've looked for a macro like 
 this, but couldn't find it, so I wrote it:

 https://gist.github.com/jamesmacaulay/4993062

 Using that, I could re-write the above like this:

 (def magnify (iffn pos? inc dec))

 I can imagine a condfn macro, too:

 (def magnify2 (condfn pos? inc
   neg? dec
   :else identity)

 Has this kind of conditional function composition been explored much? I 
 couldn't find anything like it in the standard library, but maybe I wasn't 
 looking hard enough.

 Cheers,
 James


-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: What compiles into a method body?

2013-02-04 Thread Alan Malloy
Basically each lambda compiles into a method body, and the size of its 
lexical environment doesn't matter very much, only the amount of code 
inside the lambda's (fully macroexpanded) body. So in (fn a [x] (foo (letfn 
[(b [] (bar)) (c [] (baz))])), a only pays for foo, and b and c pay for 
bar and baz respectively. So the only cause of too-large methods is a 
single large lambda that doesn't delegate to other lambdas.

I checked out midje and tried macroexpanding the test that's giving you 
problems: it expands to 140KB of Clojure source! The culprit is indeed the 
creation of your metadata maps: the :midje/body-source and :midje/source 
keys are each around 40KB literals. I don't know the details of how quoted 
values get put into the bytecode, but it's possible that code is emitted to 
generate them at runtime; perhaps they go into a static initializer, but 
that probably has the same code size limits anyway.

On Monday, February 4, 2013 2:53:04 PM UTC-8, Brian Marick wrote:

 An individual Midje fact (test case, roughly) macroexpands into a form 
 like this: 

(record-fact-existence! 
  (letfn [(fun1 [] ...test code is here...) 
  (fun2 [] (with-meta fun1 {...metadata...}))] 
(fun2)) 
 
 Tabular facts in Midje are done via unification. A table with 8 rows turns 
 into 8 individual facts (each of that structure), surrounded by an outer 
 level fact that runs each of them. This is wasteful of space but allows 
 unusually expressive tests. 

 Something I've done recently seems to have pushed some tabular facts over 
 the Java method-length limit: 

  Caused by: java.lang.ClassFormatError: Invalid method Code length 81209 
 in class file midje/t_checkers$eval24254$this_function_here_24253__24497 

 (This is actually surprising, since I don't see what I've done today that 
 could push the size so *much* over 64K.) 

 I hope my two breaking tabular facts are atypically large, but I fear not. 
 So, some questions / thoughts: 

 1. Do mutually recursive `letfn` functions get compiled into a single 
 method? More generally, I hope that any nested function definitions turn 
 into separate methods. Do they? 

 2. The metadata is rather large - can it somehow end up increasing the 
 method bytecodes? What if it's constructed via merging literals, like this: 

   (clojure.core/merge 
'{:midje/body-source ((+ 1 1) = 2), ...} 
{:midje/top-level-fact? true})))] 

 The guts of assertion checking also involves merging maps: 

 (check-one (clojure.core/merge 
 {:position 
  :expected-result-form '2, 
  :expected-result 2, 
  :function-under-test (clojure.core/fn [] (+ 1 1))} 
 {:arrow '=, :call-form '1} 
 (hash-map-duplicates-ok :position (line-number-known 2 

 3. Midje goes to a lot of trouble to obey lexical scoping, so that you can 
 write, for example: 

 (let [a 2] 
   (fact 
 (let [b 2] 
   (+ a b) = (* a b))) 

 Do closed-over lexical environments contribute unduly to method size? 

 4. How can I get a look at what a big fact compiles into? (I suppose I 
 need to AOT-compile a test namespace, but I've never had much luck with 
 that.) 

  
 Looking for 1/2-time employment as a Clojure programmer 
 Latest book: /Functional Programming for the Object-Oriented Programmer/ 
 https://leanpub.com/fp-oo 



-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: How to solve Collatz Conjecture problem for huge numbers using clojure parallelism tricks?

2013-02-01 Thread Alan Malloy
(max-key :power mario luigi)

On Thursday, January 31, 2013 6:08:21 PM UTC-8, Leandro Moreira wrote:

 Running through this problem I also faced the weird situation, so:

 Given two maps
 (def mario {:color red :power 45})
 (def luigi {:color green :power 40})

 I want the max between both but based on :power key.
 It would be something like this.

 (max mario luigi)
 I expect max return not only 45 but the whole map Is there any built 
 in function for that?


-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: why did lein just download Clojure 1.5?

2013-01-29 Thread Alan Malloy
`lein deps :tree` will show you the tree of dependencies, and you can see 
which of your dependencies has a bad dependency specification overriding 
the one in your project.clj. Typically it turns out a dependency is saying 
something like I must have the very latest Clojure, whatever that is, 
whereas your project is saying I'd prefer 1.4, but if necessary to satisfy 
more stringent requirements from another project I'll try to work with 
anything.



On Tuesday, January 29, 2013 9:16:59 PM UTC-8, larry google groups wrote:

 Very strange. I just switched back to my home computer. I wanted to 
 get all the work I had done at work this last week, so I did git pull 
 origin master to pull it down from github. I have not used my home 
 computer in a week. Then I ran lein uberjar: 

 lein uberjar 
 Retrieving org/clojure/clojure/1.5.0-RC4/clojure-1.5.0-RC4.pom from 
 central 
 Compiling kiosks-clojure.core 
 Created /Users/lner/projects/timeout_planning_module/target/kiosks- 
 clojure-0.1.jar 
 Including kiosks-clojure-0.1.jar 
 Including jsr305-1.3.9.jar 
 ;; 
 ;; much more here 
 ;; 

 Why did lein just retrieve Clojure 1.5.0-RC4? My project.clj file 
 reads: 

   :dependencies [[org.clojure/clojure 1.4.0] 
 ;; plus much more 



-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
--- 
You received this message because you are subscribed to the Google Groups 
Clojure group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to clojure+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.




Re: special case in binding vector syntax for function definitions?

2013-01-25 Thread Alan Malloy
In (let [[x :as y] [1 2]]), there is already an object to make y point 
to: the vector [1 2]. in ((fn [x :as y]) 1 2), there is no such object.

On Friday, January 25, 2013 2:18:39 PM UTC-8, Ben wrote:

 Both of these work: 

 user (let [[x  y] [1 2]] [x y]) 
 [1 (2)] 
 user (let [[x :as y] [1 2]] [x y]) 
 [1 [1 2]] 

 And this works: 

 user ((fn [x  y] [x y]) 1 2) 
 [1 (2)] 

 But this gives an exception (unsupported binding form): 

 user ((fn [x :as y] [x y]) 1 2) 
 ; Evaluation aborted. 

 I would have expected this to work and return [1 [1 2]], with y bound 
 to the whole vector implicitly passed to the function (just as it's 
 bound to the tail of the whole vector implicitly passed in the third 
 case). 

 This seems to happen because (apparently) the internals of fn* handle 
 rest parameters already, so that clojure.core/maybe-destructured 
 doesn't actually need to do anything to top-level elements of the 
 binding vector: 

 clojure.core (maybe-destructured '[a b] ()) 
 ([a b]) 
 clojure.core (maybe-destructured '[a  b] ()) 
 ([a  b]) 
 clojure.core (maybe-destructured '[a [b  c]] ()) 
 ([a p__8059] (clojure.core/let [[b  c] p__8059])) 

 Since  is a symbol, it's just passed right through and left to fn* to 
 deal with. But :as is not a symbol, so we end up with this: 

 clojure.core (maybe-destructured '[a :as b] ()) 
 ([a p__8064 b] (clojure.core/let [:as p__8064])) 

 Is there a reason for this apparent irregularity? 

 -- 
 Ben Wolfson 
 Human kind has used its intelligence to vary the flavour of drinks, 
 which may be sweet, aromatic, fermented or spirit-based. ... Family 
 and social life also offer numerous other occasions to consume drinks 
 for pleasure. [Larousse, Drink entry] 


-- 
-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en




Re: Is keyword-params middleware safe?

2013-01-16 Thread Alan Malloy
Keywords are garbage-collected if no references to them exist. I think this 
is as of Clojure 1.3, but I'm not sure exactly; perhaps it's always been 
true. You can see it easily enough at 
https://github.com/clojure/clojure/blob/master/src/jvm/clojure/lang/Keyword.java#L32
 - 
there's a map from symbols to *references* to keywords, not keywords 
themselves. Those (weak) references make the keywords themselves eligible 
for GC.

On Wednesday, January 16, 2013 9:51:59 AM UTC-8, Tony Pitluga wrote:

 From what I have read about keywords in Clojure, it does not seem like 
 they are garbage collected. The keyword params middleware seems to convert 
 user input into keywords. Putting two and two together, it seems like you 
 could DoS any server using this middleware by sending large amounts of 
 random strings as params. Eventually exhausting the memory of the JVM.

 This is a common security vulnerability in the Ruby world with converting 
 user input strings to symbols. Am I missing something here?

 Thanks,
 Tony
  

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: CLJS: protocol interfaces don't seem to support variable args in the arglist, like [ opts]

2013-01-16 Thread Alan Malloy
On Wednesday, January 16, 2013 11:17:41 AM UTC-8, Aaron Cohen wrote:

 On Wed, Jan 16, 2013 at 12:53 PM, Frank Siebenlist 
 frank.si...@gmail.comjavascript:
  wrote:

 Thanks for the confirmation.

 I know that destructuring is supported in protocols as I'm using with 
 much pleasure - kind of assumed it would work as it wasn't documented not 
 to work ;-)


 I don't believe this is true. You may think it is working, but you 
 probably are just ending up with a function that has a parameter named .

 https://groups.google.com/forum/?fromgroups=#!topic/clojure/HyoSBEfEF4w


He said destructuring is working (which is true), not that varargs are 
working (which would not be true). 

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: replacing specific symbols in arbitrary expressions

2013-01-14 Thread Alan Malloy
(clojure.tools.macro/symbol-macrolet [P +, M -, T *]
  ...)

The tools.macro code-walker is much smarter and more careful than any that 
you or I will ever write.

On Monday, January 14, 2013 3:31:40 AM UTC-8, Jim foo.bar wrote:

 Hi everyone, I hope you're all well! 

 I recently faced a problem when i needed to receive some piece of code 
 and replace all the invalid symbols in it with the proper (existent) 
 ones. Imagine for example you have the following map from made-up 
 characters to real characters: 

 (def reserved-chars 
 (zipmap [\P \M \T] 
  [\+ \- \*]) ) 

 Now, I'm expecting code that includes the symbols P, M, T  but before 
 evaluating that code I need to replace these non-valid symbols with the 
 corresponding symbols Clojure knows about (+, -, * respectively). I 
 could get around that by def-ing  P, M  T to +, -  * so that Clojure 
 knows the symbols when the time comes to eval the fn. However, this 
 solution is not ideal when there are many such symbols. My second 
 thought was to create a macro that simply transforms the expressions 
 replacing all the 'bad' symbols with 'good' ones...This is what I came 
 up with: 


 (defmacro translate [ code] 
 `(let [code-string# (str '~@code) 
 fake-to-real# reserved-chars] 
   ;(eval 
(read-string ;;returns persistent-list 
 (reduce-kv 
   (fn [s# k# v#] 
 (.replaceAll ^String s# (str k#) (str v#))) 
   code-string# fake-to-real# 

 As you can probably gather, this macro treats the expression as a string 
 and not as data...Even though it runs perfectly fine and gives the 
 correct output , I was wondering if any of you macro-gurus has any 
 better suggestions or alternativesAlternatively, if you can think of 
 any cases that will break my little macro please share them... 

 thanks in advance... 

 Jim 


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: clojurescript gensym does not generate a unique symbol?!

2013-01-04 Thread Alan Malloy
Certainly it does work the same way in JVM-Clojure:

user= (gensym)
G__1278
user= (gensym)
G__1281
user= (gensym)
G__1284
user= (= 'G__1287 (gensym))
true

Whether that's a bug or a case of If it breaks when you do that, then 
don't do it isn't for me to say, but I would be pretty surprised to hear 
that Rich doesn't already know about this behavior.

On Thursday, January 3, 2013 4:44:34 PM UTC-8, David Little wrote:

 Open a fresh ClojureScript REPL and type:

  (def symbol1 'G__1)
 G__1
  (def symbol2 (gensym))
 G__1
  (= symbol1 symbol2)
 true

 Looks like a bug to me. It certainly doesn't work that way in Clojure 
 (though the ordering of these statements matters). I googled around but 
 didn't see any other reports of this.


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: inserting code into reify methods

2012-12-24 Thread Alan Malloy
You don't need any of the typehints in your reify body. The compiler infers 
argument and return types from the interface definition.

On Monday, December 24, 2012 5:35:35 AM UTC-8, nkonovalov wrote:

 Hi.

 I have a java interface.
 Something like this this.

 public interface ITest {
 void printHello();
 void printName(String name);
 }

 And i get an implementation using reify.

 (def impl (reify macrotest.ITest
   (^void printHello [this]
 (println Hello world!))
   (^void printName [this ^String name]
 (println (str Hello,  name
 )

 Also a have a validation method:
 (defn validate-state [] (println Some validation code here))

 So to add it into implementation i have to add int into every method 
 manually 

 (def impl (reify ITest
   (^void printHello [this]
 *(validate-state)*
 (println Hello world!))
   (^void printName [this ^String name]
* (validate-state)*
 (println (str Hello,  name
 )

 Is it possible to make a macros that would get the validation method and 
 insert this *(validate-state) *into the begining of each method in reify 
 automatically.

 Something like that?

 (def impl (reify-with-validation *validate-state* ITest
   (^void printHello [this]
 (println Hello world!))
   (^void printName [this ^String name]
 (println (str Hello,  name
 )

 Any thoughts on how to do this?



-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: zip-reduce

2012-12-24 Thread Alan Malloy
Probably better to write it more generally, by creating a seq from a zipper 
and then just using the ordinary reduce function on that zip:

(defn zip-seq [f acc z]
  (map node (tree-seq branch? children z)))

(reduce f acc (zip-seq some-zipper))

On Monday, December 24, 2012 6:27:00 PM UTC-8, JvJ wrote:

 The other day I wrote this as a utility function because I couldn't find 
 anything like it in the zipper libary.  Am I missing something?  Is 
 something like this implemented somewhere?

 (defn
   zip-reduce
   Reduce called on a zipper.
   [f acc z]
   (if (zip/end? z)
 acc
 (recur f (f acc z) (zip/next z


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: zip-reduce

2012-12-24 Thread Alan Malloy
Except of course zip-seq doesn't need the f, acc arguments. Sorry about 
that.

On Monday, December 24, 2012 7:18:17 PM UTC-8, Alan Malloy wrote:

 Probably better to write it more generally, by creating a seq from a 
 zipper and then just using the ordinary reduce function on that zip:

 (defn zip-seq [f acc z]
   (map node (tree-seq branch? children z)))

 (reduce f acc (zip-seq some-zipper))

 On Monday, December 24, 2012 6:27:00 PM UTC-8, JvJ wrote:

 The other day I wrote this as a utility function because I couldn't find 
 anything like it in the zipper libary.  Am I missing something?  Is 
 something like this implemented somewhere?

 (defn
   zip-reduce
   Reduce called on a zipper.
   [f acc z]
   (if (zip/end? z)
 acc
 (recur f (f acc z) (zip/next z



-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Confused about comp

2012-12-15 Thread Alan Malloy
Nonsense. Why would that be any faster? (join coll) is defined as (apply 
str coll).

On Saturday, December 15, 2012 12:21:45 PM UTC-8, Marek Šrank wrote:

 ...which should be also a lot faster :)

 On Saturday, December 15, 2012 5:44:01 PM UTC+1, Armando Blancas wrote:

 (comp (partial apply str) (partial filter #{\a}))


 Or, (comp join (partial filter #{\a}))
  



-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Strange behaviour: nested def in proxy method body

2012-12-13 Thread Alan Malloy
On Thursday, December 13, 2012 4:14:23 AM UTC-8, Marshall 
Bockrath-Vandegrift wrote:

 kristianlm kris...@adellica.com javascript: writes: 

  I'm enjoying testing Java code with Clojure and it's been a lot of fun 
  so far. Coming from Scheme, the transit is comfortable. However, I 
  encountered a big surprise when I nested def's and used them with a 
  proxy: 

 This is a common surprise for people with previous exposure to Scheme: 
 `def` in Clojure is always explicitly namespace-scoped.  What it does is 
 create a var with a name and intern it into the namespace with that 
 name, not introduce a name in the current lexical scope.  Nested `def`s 
 are thus very rarely going to be what one actually want, and the 
 behavior you’re seeing is exactly what one would expect. 


To further clarify: the mew* version doesn't *actually* behave just like 
new-let*, although it usually will have the same consequences. The issue is 
that there's a race condition if two different threads call mew* at the 
same time: they might both mutate i, then both read it, and thus end up 
with the same reference. Really, as Marhsall says, a nested def is (almost) 
never what you want. 

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Specific reduce function version

2012-12-09 Thread Alan Malloy
You seem to have written (reduce (fn [acc [a b]] ...) (partition 2 1 coll)).

On Sunday, December 9, 2012 7:39:21 AM UTC-8, Alexander Semenov wrote:

 Hi, folks.

 I'm wondering if Clojure library has 'reduce' function version which is 
 like (reduce f coll) - i.e. it applies function to coll elements without 
 the initial value but at the same time allows to use external accumulator 
 which is passed to f as well. Better look at the code:

 (defn reduce-with-acc
   Applies f to first two coll elements and acc producing new acc value for
   subsequent f calls. Returns acc. On singleton or empty collection returns
   acc immediately.
   [f acc coll]
   (loop [a (first coll) acc acc s (next coll)]
 (if (seq s)
   (let [b (first s)]
 (recur b (f a b acc) (next s)))
   acc)))

 Regards,
 Alexander.


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Sorted Sets With Duplicate Elements

2012-11-20 Thread Alan Malloy


On Tuesday, November 20, 2012 10:29:18 AM UTC-8, Andy Fingerhut wrote:


 On Nov 20, 2012, at 10:12 AM, Mark Engelberg wrote: 

  Clojure's sorted collections must be provided with a sorting function 
 where items tie if and only if they are equal. 
  
  (sorted-set-by #(compare [(second %) %] [(second %2) %2]) [:a 1] [:b 1] 
 [:c 1])) 

 Mark, I like the brevity of this way of writing comparison functions with 
 tie breakers, and see that it would extend well to multiple sort keys, and 
 ascending or descending order on each key can be chosen independently. 

 My question is perhaps of the 
 is-the-number-of-angels-that-can-dance-on-the-head-of-a-pin-finite-or-infinite
  
 kind. 

 Does Clojure promise anywhere in its documentation that it compares 
 vectors and sequences in lexicographic order? 


I hope not, because that's not what it does! Sequences don't implement 
Comparable at all, so unless you supply a comparator they can't be sorted. 
And vectors are compared first by length; only if they have the same length 
are their elements considered for a lexicographical comparison. 

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Difference between JVM and CLR when destructuring a lazy sequence

2012-11-15 Thread Alan Malloy
Binding to [ rst] must realize an element of the sequence, to determine if 
there are any left, and it promises to never bind (), only nil.

On Thursday, November 15, 2012 7:23:05 AM UTC-8, ffailla wrote:

 I believe I have discovered differing behavior between the JVM and CLR 
 implementations when running the following statement:

 user (let [foo (repeatedly (fn [] (let [r (rand)]
 (println in-repeat:  r)
 r)))
  [f  rst] foo]
  (println return:  f))

 When run on the JVM with clojure 1.4.0, I get the following output:

 in-repeat:  0.6929552277817549
 in-repeat:  0.7005322422752974
 return:  0.6929552277817549
 nil
 user 

 When run on the CLR with clojure-clr 1.4.0, the random number will be 
 printed from in-repeat infinitely, never to return.

 Is this difference between the JVM and CLR implementations when 
 destructuring a lazy sequence known?  

 Also, why was the random number printed twice on the JVM side.  I haven't 
 looked an the implementation, but I would guess this would be due to 
 chunking the sequence. Thanks.

 -Frank Failla 


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Proposed change to let- syntax

2012-11-15 Thread Alan Malloy
The primary point of let- is that you can insert it into an existing - 
pipeline. 

(- foo
(stuff)
(blah)
(let- foo-with-stuff
  (for [x foo-with-stuff]
(inc x)))

Your proposal breaks this.

On Thursday, November 15, 2012 10:35:59 AM UTC-8, Alex Nixon wrote:

 Hi all,

 I find the proposed function let- in Clojure 1.5 very useful, but a bit 
 ugly.  The arguments are backwards when compared to vanilla let, and it 
 doesn't support destructuring where it easily could (which I believe would 
 be helpful when threading 'state-like' maps, as I find let- very useful 
 for).

 I'd like to float an alternative implementation which improves on both 
 these issues.  Thoughts?

 (defmacro new-let-
   Establishes bindings as provided for let, evaluates the first form
in the lexical context of that binding, then re-establishes bindings
to that result, repeating for each successive form
   [bindings  forms]
   (assert (vector? bindings) binding must be a vector)
   (assert (= 2 (count bindings)) binding vector must contain exactly two 
 forms)
   `(let [~@bindings
  ~@(interleave (repeat (bindings 0)) (drop-last forms))]
  ~(last forms)))

 (new-let- [{:keys [foo bar] :as state} {:foo 1 :bar 2}] 
   (assoc state :foo (inc bar))
   (assoc state :bar (inc foo))) ; = {:foo 3, :bar 4}

 -- 
 *Alex Nixon*

 Software Engineer | SwiftKey

 *al...@swiftkey.net javascript:** | http://www.swiftkey.net/*

 ++
 WINNER - MOST INNOVATIVE MOBILE 
 APPhttp://www.swiftkey.net/swiftkey-wins-most-innovative-app-at-mwc
  - GSMA GLOBAL MOBILE AWARDS 2012

 Head office: 91-95 Southwark Bridge Road, London, SE1 0AX TouchType is a 
 limited company registered in England and Wales, number 06671487. 
 Registered office: 91-95 Southwark Bridge Road, London, SE1 0AX

  

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: How to get the namespace for an unqualified symbol?

2012-11-12 Thread Alan Malloy
Yikes! Try ((juxt (comp ns-name :ns) :name) (meta (resolve 'inc))) - name 
information is stored on the var's meta in a clojure-friendly way - no need 
to use undocumented behavior on the java internals.

On Monday, November 12, 2012 11:05:15 AM UTC-8, Ambrose Bonnaire-Sergeant 
wrote:

 Evil, but this is the solution I use:

 (let [v (resolve 'a)]
   (symbol (str (ns-name (.ns v))) (str (.sym v

 I'd love to know a better way.

 Thanks,
 Ambrose

 On Tue, Nov 13, 2012 at 1:46 AM, johnstok k.w.jo...@gmail.comjavascript:
  wrote:

 I was looking at combining the namespace and resolve functions:

 user= (def x 5)
 #'user/x
 user= (resolve 'x)
 #'user/x
 user= (namespace 'user/x)
 user
 user= (namespace 'x)
 nil
 user= (namespace (resolve 'x))
 ClassCastException clojure.lang.Var cannot be cast to clojure.lang.Named 
  clojure.core/namespace (core.clj:1497)

 In the final expression I was expecting to get the value user.

 Having read the doc's I understand that the return type from resolve is 
 not compatible with namespace:

 namespace: Returns the namespace String of a symbol or keyword, or nil 
 if not present.
 resolve:   Returns the var or Class to which a symbol will be resolved 
 in the current namespace else nil.

 Question: given a symbol 'x' how can I determine the 'fully qualified' 
 symbol (i.e. 'user/x')?

  -- 
 You received this message because you are subscribed to the Google
 Groups Clojure group.
 To post to this group, send email to clo...@googlegroups.comjavascript:
 Note that posts from new members are moderated - please be patient with 
 your first post.
 To unsubscribe from this group, send email to
 clojure+u...@googlegroups.com javascript:
 For more options, visit this group at
 http://groups.google.com/group/clojure?hl=en




-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Proposal/request: Give clojure.core/conj a unary implementation

2012-11-03 Thread Alan Malloy
There is never a reason to write (apply conj ...). Instead, use `into`, 
which does the same thing but faster and with fewer characters.

On Saturday, November 3, 2012 3:27:24 PM UTC-7, CGAT wrote:

 It would be nice if clojure.core/conj had a unary implementation
 
([coll] coll)

 The motivating use case is when one is conjoining sequences of
 items to a collection all at once:

(apply conj coll seqable)

 such as   (apply conj  #{1 2 3}  [2 4 6 8 10]). 
 Currently (1.4.0), this will raise an arity exception  
 if the seqable object is empty:

(apply conj #{1 2 3} [])

 necessitating an awkward empty? check when,
 for instance, the sequence is computed or passed in.

 It seems to me that making unary conj the identity is both
 a natural interpretation and essentially cost free, while
 making this use case much more convenient.
 Moreover, it is consistent with clojure.core/disj for sets
 which does act like this

   (apply disj #{1 2 3} []) -  #{1 2 3}

 and has an identity unary implementation.

 Comments?




-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: downcast

2012-10-24 Thread Alan Malloy
Clojure doesn't care about casting, so you can ignore this issue
entirely. But also, it's not an issue: the same code would fail in
Java, because Clojure's integer literals are Long, not Integer. (cast
Long (cast Number 1)) would work fine.

On Oct 24, 2:12 pm, Steffen Panning steffen.pann...@gmail.com wrote:
 Hello Group,

 the Java API I'm currently working with expects that an Interface is
 downcasted to a concrete class.

 As a quick test I toyed with this:

 (cast Integer (cast Number 1))
 ClassCastException Cannot cast java.lang.Long to java.lang.Integer
  java.lang.Class.cast (Class.java:3007)

 It seems the clojure cast does not work like the java cast.

 Is there a way to do this Clojure?
 A not so nice alternative is to write the cast stuff in java.

 TIA Steffen

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Replacing nested let statements with assignments

2012-10-18 Thread Alan Malloy
It's rare to get tired of this, because nobody does it: it's not
common because your interleaved statements are side-effecting only,
which is not encouraged in Clojure, and rarely needed. Certainly
sometimes it's the best way to do something, but not so often that I'd
become frustrated; if anything, having to write such irritating code
can serve as a good reminder that I shouldn't have so many
unrestrained side effects scattered through my logic.

On Oct 18, 9:01 am, JvJ kfjwhee...@gmail.com wrote:
 I'm not sure if anyone's done this before, but I'm fed up with writing code
 that looks like this:

 (let [a 1]
    (println this is a:  a)
    (let [b 2]
        (println this is b:  b)
        (let [c 3]
             (println this is c:  c)
             (+ a b c

 I'd rather do something more like this:
 (-:
    (:= a 1) ;; Assign a to 1
    (println this is a:  a)
    (:= b 2)
    (println this is b:  b)
    (:= c 3)
    (println this is c:  c)
    (+ a b c))

 I wrote a macro to do this, but I feel like it's such a simple thing that
 someone must have done it before, and it's probably better than mine.
 Does anyone know of anything like that?

 Here's the code for it in case anyone wants to use it:

 (ns cljutils.core)

 (defn- form-check
   Ensures the form represents an assignment.
 Such as (:= a 1)
   [form]
   (and
    (= 3 (count form))
    (= := (first form))
    (symbol? (second form

 (defn- iblk-fn
   Simulates imperative variable-assignments through nested
 let statements.
   [ forms]
   (let [form (first forms)
         rforms (rest forms)]
     (if-not form
       nil
       ;; Else
       `(do
          ~@(if (form-check form)
              `((let [~(second form) ~(nth form 2)]
                  ~(apply iblk-fn rforms)))
              (let [[f r] (split-with (comp not form-check) forms)]
                 (concat
                  f
                  (apply iblk-fn r

 (defmacro -:
   [ forms]
   (apply iblk-fn forms))

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Replacing nested let statements with assignments

2012-10-18 Thread Alan Malloy
On Oct 18, 12:02 pm, David Nolen dnolen.li...@gmail.com wrote:
 On Thu, Oct 18, 2012 at 2:55 PM, Alan Malloy a...@malloys.org wrote:
  It's rare to get tired of this, because nobody does it: it's not
  common because your interleaved statements are side-effecting only,
  which is not encouraged in Clojure, and rarely needed. Certainly
  sometimes it's the best way to do something, but not so often that I'd
  become frustrated; if anything, having to write such irritating code
  can serve as a good reminder that I shouldn't have so many
  unrestrained side effects scattered through my logic.

 I think from the examples debugging via print statements was the main (and
 reasonable) use case.

Indeed, but it's easy to add those in any number of ways other than
the code the OP was originally unhappy with. For example, by adding _
bindings for side effects, or by introducing a macro like:

(defmacro ? [form]
  `(let [x# ~form]
 (printf %s is %s '~form x#)
 x#))

(let [a (? 1)
  b (? (+ 3 a))]
  ...)

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Redubicle NIO

2012-10-18 Thread Alan Malloy
As a general-macro aside, you are multiply-evaluating the `f`
argument, by expanding it in-place inside the recursive clause. This
is almost certainly not what you want, and you could avoid it by
starting with (let [f# ~f] ...). Better still, ask why this is a macro
at all. This should really just be a function, because you don't
introduce any new syntax, and you don't delay evaluation of anything.

On Oct 18, 2:56 pm, Bruno França dos Reis bfr...@gmail.com wrote:
 Damn, just noticed a small mistake in the macro: I use the original buffer,
 not the duplicated one. Here's the correct version:

 (defmacro buffer-reduce [b f val]
   `(let [b# (.duplicate ~b)]
      (loop [remaining# (.remaining b#)
             result# ~val]
        (if (zero? remaining#)
          result#
          (recur (dec remaining#) (~f result# (.get b#)))

 (extend-protocol clojure.core.protocols/CollReduce
   java.nio.ByteBuffer
   (coll-reduce [b f] (coll-reduce b f (f)))
   (coll-reduce [b f val] (buffer-reduce b f val))

   java.nio.LongBuffer
   (coll-reduce [b f] (coll-reduce b f (f)))
   (coll-reduce [b f val] (buffer-reduce b f val))

   ; ... other kinds of buffer ...
 )

 Sorry for that.

 On Thursday, October 18, 2012 6:50:07 PM UTC-3, Bruno França dos Reis wrote:









  Hello!

  I've recently started playing with Clojure, and a couple of days ago I've
  been pointed to Reducers in Clojure 1.5 after a discussion on #clojure at
  Freenode.

  I've read Rich's posts announcing the Reducers library, and he says that
  there's a ***lack of reducible IO sources***. I'm working on a project
  that in which I analyze lots of data (from huge files on disk), and I'm
  frequently doing reduce operations on it. I began by writing a custom
  sequence, that after I transformed in a custom reducible collection. But
  I've just noticed that I could encapsulate it on a kind of reducible IO
  source.

  I'm writing this message to share the code I wrote relating to reducible
  IO sources, if anybody sees any use for it. The idea is to make the ***NIO
  Buffers reducible***, so that you can open huge files as **memory mapped
  files**, which are instances of `ByteBuffer`. You can then obtain
  instances of other buffers, say, `LongBuffer` (which is what I'm using on
  my current project), which are also reducible:

  (defmacro buffer-reduce [b f val]
    `(let [b# (.duplicate ~b)]
       (loop [remaining# (.remaining b#)
              result# ~val]
         (if (zero? remaining#)
           result#
           (recur (dec remaining#) (~f result# (.get ~b)))

  (extend-protocol clojure.core.protocols/CollReduce
    java.nio.ByteBuffer
    (coll-reduce [b f] (coll-reduce b f (f)))
    (coll-reduce [b f val] (buffer-reduce b f val))

    java.nio.LongBuffer
    (coll-reduce [b f] (coll-reduce b f (f)))
    (coll-reduce [b f val] (buffer-reduce b f val))

    ; ... other kinds of buffer ...
  )

  Hope this might be useful for someone.

  Bruno

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: trampoline not compatible with reducers?

2012-10-16 Thread Alan Malloy
Reducers don't enter into the picture at all: this code is just as
broken with clojure.core/reduce and clojure.core/map. The immediate
problem that Kevin is trying to draw your attention to is that you are
calling (reduce max (map my-fn coll)), where my-fn sometimes returns a
number, and sometimes a thunk. Obviously max can't be expected to
compare thunks for you, so that's no good. His suggestion is to make
sure to trampoline the results of (map my-fn coll) until you get out a
list of numbers, and then find the max.

But really I don't think trampoline is a very compelling problem-
solver here: the primary (only?) gain from trampoline is in reducing
stack depth, and I rather doubt that you can calculate minimax for
even a few hundred ply. So you're in no danger of a stackoverflow, but
are sacrificing readability and a smidge of performance to keep your
stack really small instead of not big enough to be a problem.

On Oct 16, 12:45 pm, Jim - FooBar(); jimpil1...@gmail.com wrote:
 'my-min' and 'my-max' simply wrap core/min core/max. You mean i have to
 trampoline these calls as well? return something like this? :

 #(r/reduce (trampoline my-max) ;;was my-max
                                     (r/map (fn [child] (minimize (:tree
 child) (dec d))) (:children tree)))

 Jim

 On 16/10/12 20:01, Kevin Downey wrote:







  if you look further down the stacktrace (where it refers to your code
  instead of clojure.lang.Numbers.lt) it will give you line numbers in
  your code to look at.

  you are calling these trampolined functions without trampoline.

  On Tue, Oct 16, 2012 at 11:24 AM, Jim - FooBar(); jimpil1...@gmail.com 
  wrote:
  On 16/10/12 19:15, Kevin Downey wrote:
  you are declaring the functions return doubles, but in fact returning
  functions or doubles
  yes you're right (my bad) but the same thing happens without the
  type-hinting - albeit in a different place and different originating
  function:

  ClassCastException Clondie24.lib.search$search$maximize__3081$fn__3082
  cannot be cast to java.lang.Number  clojure.lang.Numbers.lt
  (Numbers.java:219)

  Jim

  --
  You received this message because you are subscribed to the Google
  Groups Clojure group.
  To post to this group, send email to clojure@googlegroups.com
  Note that posts from new members are moderated - please be patient with 
  your
  first post.
  To unsubscribe from this group, send email to
  clojure+unsubscr...@googlegroups.com
  For more options, visit this group at
 http://groups.google.com/group/clojure?hl=en

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: parallel alpha-beta pruning possible?

2012-10-16 Thread Alan Malloy
You will get better results from a game-programming forum, or indeed
from a google search for parallel alpha beta than from a bunch of
clojure guys with no particular experience in your problem domain.

On Oct 16, 1:27 pm, Jim - FooBar(); jimpil1...@gmail.com wrote:
 After watching this presentation[1] by Brian Goetz, in which he
 discusses the fork-join framework and how it is intended to be used I
 was left with a major question. Around the end of the talk he said and I
 quote

 ...fork-join can be used for game-tree exploration...

 while the slides actually had
 -Move generation
 -Alpha-beta
 ...
 

 As soon as I saw/heard that I almost fell of my chair!!! He caught me
 completely by surprise simply because I've given this quite a bit of
 though myself... NOw, I'm not implying that I am nowhere near as smart
 or informed as he is but the 'objection' I have is pretty simple. I
 already have a parallel minimax (some of you have actually helped) so I
 know how that's done and it wasn't too hard because minimax is
 exhaustive search. No heuristics whatsoever...as long as you work with
 immutable data-structures God is on your side and all is well!

 HOWEVER, as soon as you introduce heuristics (even simplistic like
 alpha-beta pruning) you 've lost the ability to split the work in
 pieces. You've suddenly introduced coordination which only makes sense
 in a serial fashion. Since pruning a particular branch of the game-tree
 requires knowing how the previous branch did  how can you ever fork?
 What if these 2 branches are on separate threads? How can you ever do
 that without locking?

 I am very excited that someone like Brian Goetz is claiming something
 like this even though I don't understand how such an inherently serial
 process could be efficiently forked.

 Can anyone help?

   [1]http://www.infoq.com/presentations/brian-goetz-concurrent-parallel

 Jim

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Evaluating an anonymous function with closure

2012-10-15 Thread Alan Malloy
Evaluating function literals is not intended to work; that it works
for non-closure functions should be treated as a coincidence.

On Oct 15, 2:19 am, Gergely Szabó gergel...@gmail.com wrote:
 Hello,

 could someone please explain the behavior that is shown in the gist below?

 https://gist.github.com/3891587

 Regards,
 Gergely

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Evaluating an anonymous function with closure

2012-10-15 Thread Alan Malloy
Evaluating function literals is not intended to work; that it works
for non-closure functions should be treated as a coincidence.

On Oct 15, 2:19 am, Gergely Szabó gergel...@gmail.com wrote:
 Hello,

 could someone please explain the behavior that is shown in the gist below?

 https://gist.github.com/3891587

 Regards,
 Gergely

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Evaluating an anonymous function with closure

2012-10-15 Thread Alan Malloy
On Oct 15, 1:07 pm, Jim - FooBar(); jimpil1...@gmail.com wrote:
 On 15/10/12 19:42, Ben Smith-Mannschott wrote:

  If the distinction I'm trying to make is not clear to you, I'd suggest
  having a look athttp://www.infoq.com/presentations/Clojure-Macros (It
  does a good job exploring these kinds of distinctions as it's vital to
  have an accurate mental model of how Clojure is evaluated if one
  intends to write macros.)

 after watching this talk I tried this at a repl:

 (defmacro plus
 Perform addition at compile time.
   [numbers]
    (apply + (eval numbers)))

 user= (time (plus (vec (range 1
 Elapsed time: 0.015635 msecs ;;WOW
 49995000

 user= (time (apply + (vec (range 1
 Elapsed time: 16.732054 msecs ;;160 times slower
 49995000

 before jumping to any conclusions (and rushing to change some of my
 code) would you say timing is realistic? Is it expected to see such a
 dramatic speed increase? To be honest I'm a bit surprised...Regardless
 of when the actual calculation will be performed (compile vs run time),
 it will eventually be performed. why is at compile time so much faster?

You add the numbers at compile time, and then time how long it takes
to...do nothing to them, at runtime. You are comparing N to zero, not
to some smaller factor of N.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Intern a var from outside namespace

2012-10-11 Thread Alan Malloy


On Thursday, October 11, 2012 9:03:38 PM UTC-7, David Jacobs wrote:

 I would like to create function names programmatically. So far, I have 
 code that works: 
 ...
 Where am I going wrong?

 David


Sentence one. Don't do it that way: namespaces are not very good hashmaps, 
but hashmaps are excellent at that. You already have the data that you need 
to make this handler, and there's no need to scatter it into dozens of 
functions: use that data to create a single function that does the 
dispatching logic that you need, and put that into your ring routes or 
whatever.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: apply: increase performance by 60% for fixed length

2012-10-07 Thread Alan Malloy
This is nonsense. If s is fixed-size at compile-time, you would never use 
apply to begin with. Why bother with (applyn 10 + [1 2 3 4 5 6 7 8 9 10]) 
when you could just write (+ 1 2 3 4 5 6 7 8 9 10)?

On Sunday, October 7, 2012 2:15:28 PM UTC-7, Marc Dzaebel wrote:

 *apply *is slow. However you can increase performance by 60% with the 
 following macro, if you have a fixed length in S.

 (defmacro *applyn *[n f  s]
 (loop [curr `(list* ~@s), n n, vars[] vals[]]
 (if(pos? n)
(let[v(gensym)]
 (recur v (dec n) (conj(conj vars v) (if (seq vars) (list 
 'next curr) curr))
(conj vals(list 'first v
   `(let[~@vars] ~(cons f (seq vals))

 (let[t(fn[](*apply   *+ '(1 2 3 4 5 6 7 8 9 10)))] (time(dotimes [_ 
 100] (t ; ~680 msec
 (let[t(fn[](*applyn *10 + '(1 2 3 4 5 6 7 8 9 10)))] (time(dotimes [_ 
 100] (t ; ~220 msec

 So, if you have inner loops, that must be optimized for performance, you 
 might remember this possibility. Even other functions could be optimized 
 this way. However, *premature optimization* is the root of all evil. 
 Beside, the generated code is more space consuming.

 *Marc*


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: comp inside macro

2012-09-26 Thread Alan Malloy
(a) There's no reason for this to be a macro at all: you don't need to
prevent evaluation of anything, and you don't need to transform any
syntax. Just write a function: (defn asdf [ {:keys [a]}] (println
(comp (partial + 1) a)))

(b) To make this a macro, just be more careful about what you evaluate
at runtime vs compile-time: (defmacro asdf [ {:keys [a]}] `(println
(comp (partial + 1) ~a)))

On Sep 26, 2:14 am, sailormoo...@gmail.com sailormoo...@gmail.com
wrote:
 Hi :

   I would like to create a macro as follows.
 Note : the prinln function actually is something more sophisticated,
 but I would like to evaluate the composition of one predefined function and
 the other from the input argument.

   And I got some errors, why?
   Thanks

 user= (defmacro asdf [ {:keys [a]}]
   `(println ~(comp (partial + 1) a)))
 #'user/asdf
 user= (asdf :a (partial * 2))
 IllegalArgumentException No matching ctor found for class
 clojure.core$comp$fn__
 4034  clojure.lang.Reflector.invokeConstructor (Reflector.java:163)

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Nested functions on #() reader

2012-09-17 Thread Alan Malloy
Indeed, there's no need for anything to be a reader macro, except 
concision. You can write this as an ordinary macro, eg, (crazy-fn %a %%b 
%%%c). If you try that and find it's awesome, share it with others. If it's 
universally loved, perhaps someday it could be a reader macro.

On Monday, September 17, 2012 1:59:56 AM UTC-7, DAemon wrote:

 So you would introduce all of the functions first, then insert the body 
 into the inside? Major issue that I can see is that it's very powerful and 
 very useful only in very specific circumstances, but isn't extensible at 
 all. Looks cool, though. Maybe you could write a macro that does something 
 like this?

 - DAemon

 On Sun, Sep 16, 2012 at 2:16 PM, vhsmaia v...@viclib.com javascript:wrote:

 Hello. I'm new here, so, not sure if those were already posted. But why 
 is this not used? An example would be:
 #(%a %%b %%%c) would be the same as (fn [a] (fn [b] (fn [c] (a b c)))

 -- 
 You received this message because you are subscribed to the Google
 Groups Clojure group.
 To post to this group, send email to clo...@googlegroups.comjavascript:
 Note that posts from new members are moderated - please be patient with 
 your first post.
 To unsubscribe from this group, send email to
 clojure+u...@googlegroups.com javascript:
 For more options, visit this group at
 http://groups.google.com/group/clojure?hl=en




-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Sort and Java 1.7

2012-09-12 Thread Alan Malloy
Vote to close as not a real question. The signature of 
java.util.Collections/sort hasn't changed since 1.5, when generics were 
introduced, and it should still be basically compatible with what it was 
when it was introduced in 1.2.

On Wednesday, September 12, 2012 5:54:22 AM UTC-7, Canonical.Chris wrote:

 Clojure's sort just trampolines down to the Java sort implementation. 
 Between 1.6 and 1.7, the Java guys have really cracked down on the 
 interface that people must satisfy with their comparators. LISP is much 
 looser with its sorting requirements. I just wanted to know how people felt 
 about these changes.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: using take-while with pred function that has state

2012-09-03 Thread Alan Malloy
(map #(do %2 %1) c1 c2) is a neat trick I hadn't seen in this context; 
thanks for showing me!

On Sunday, September 2, 2012 10:26:07 PM UTC-7, Stephen Compall wrote:

 On Fri, 2012-08-31 at 05:08 -0700, shaobohou wrote: 
  I have written the following function using take-while and a pred 
  function with an atom to store the set of unique tokens. It works 

 Only because in the current implementation, take-while happens to be 
 called in coll order, which is not a guarantee of the API. 

  Will this be problem in my implementation if I am calling it from 
  multiple threads? 

 No. 

  And what would be the more idiomatic way of implementing this kind of 
  behaviour? 

 Consider this restructuring: 

 (- ss (map tok-fn), (reductions (partial apply merge) #{}), 
  (take-while #(...)), (map #(do %2 %1) ss), last) 

 Use of `atom' for this sort of thing is certainly an antipattern, so 
 consider any alternative that suits you. 

 -- 
 Stephen Compall 
 ^aCollection allSatisfy: [:each | aCondition]: less is better than 




-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: reporting function inputs as part of exceptions

2012-09-03 Thread Alan Malloy
Slingshot's throw+ generates an exception object that includes, among other 
things, all the locals in the context of your throw.

On Monday, September 3, 2012 9:03:42 PM UTC-7, Timothy Pratley wrote:

 I'm working on a project where it would be quite convenient to have the 
 input values to the function reported in any exceptions that get thrown. 
 I'm guessing the way to do this would be to create a replacement defn which 
 had a try catch and threw a new error with the inputs captured. Has anyone 
 tried this, know of a better way, or a library that helps in this way?

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Howto not reindent in (emacs) clojure-mode

2012-08-26 Thread Alan Malloy
I just use C-j instead of RET in the rare cases that I want to leave the 
previous line alone.

On Sunday, August 26, 2012 4:15:54 PM UTC-7, frye wrote:

 Hey all, 


 There'll probably be a quick solution to this. But I have emacs with 
 clojure-mode installed. And it has this very annoying behaviour of 
 re-indenting a bracket if I hit return on a line just abouve it. I took a 
 look around and thought this line ( 
 in ~/.emacs.d/elpa/install-dir/clojure-mode.el  ) might be the culprit. 
 But commenting it out didn't remove that behaviour. Is there another place 
 I can look to change this behaviour? 

 ... 
 (defvar clojure-mode-map
   (let ((map (make-sparse-keymap)))
 (set-keymap-parent map lisp-mode-shared-map)
 (define-key map \e\C-x 'lisp-eval-defun)
 (define-key map \C-x\C-e 'lisp-eval-last-sexp)
 (define-key map \C-c\C-e 'lisp-eval-last-sexp)
 (define-key map \C-c\C-l 'clojure-load-file)
 (define-key map \C-c\C-r 'lisp-eval-region)
 (define-key map \C-c\C-z 'run-lisp)
 *;;(define-key map (kbd RET) 'reindent-then-newline-and-indent) 
 *
 
 
 
   
 (define-key map (kbd C-c t) 'clojure-jump-to-test)
 map)
   Keymap for Clojure mode. Inherits from `lisp-mode-shared-map'.)
 ... 



 Thanks 

 Tim Washington 
 Interruptsoftware.ca 
 416.843.9060 

  

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: clojure.logic project.clj file

2012-08-15 Thread Alan Malloy
Blech. I've found having the project.clj helpful myself for the same reason 
David has: it's easy to start up lein (swank or repl) and hack around. I'm 
opposed to removing it unless there's someone it's actually hurting.

On Wednesday, August 15, 2012 3:00:27 PM UTC-7, Sean Corfield wrote:

 On Mon, Aug 13, 2012 at 1:38 PM, Brent Millare 
 brent@gmail.comjavascript: 
 wrote: 
  I think the :source-path line in project.clj should be :source-paths 
  [src/main/clojure]. Is :source-path still looked up in leiningen2? 

 My question would be: why is there a project.clj file in the 
 core.logic repository in the first place, given that Maven is used to 
 build contrib libraries? 

 I know David said he only uses it for interactive development but I 
 think it will cause confusion for others. Perhaps the best solution 
 would be to move it aside, delete it from Git, move it back and add it 
 to .gitignore? That way David can continue to use his local 
 project.clj file without confusing folks who clone the source. 

 The same comment / question applies to: 
 * core.cache/project.clj 
 * core.contracts/project.clj 
 * core.match/project.clj 
 * core.unify/project.clj 
 -- 
 Sean A Corfield -- (904) 302-SEAN 
 An Architect's View -- http://corfield.org/ 
 World Singles, LLC. -- http://worldsingles.com/ 

 Perfection is the enemy of the good. 
 -- Gustave Flaubert, French realist novelist (1821-1880) 


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Pattern of Succinctness

2012-08-12 Thread Alan Malloy
This doesn't work.

On Sunday, August 12, 2012 12:44:11 PM UTC-7, Pierre-Henry Perret wrote:

 I prefer  (filter (partial not nil?) coll)  as a HOF

 Le dimanche 12 août 2012 20:46:59 UTC+2, rmarianski a écrit :

 On Sun, Aug 12, 2012 at 11:22:55AM -0700, Takahiro Hozumi wrote: 
   (filter (partial not nil?) coll) 
  You mean (filter (comp not nil?) coll). 
  I'm not sure which is more readable, but thanks for Meikel and Alex, I 
 now 
  prefer (remove nil? coll). 

 remove is better in this case, but for posterity (comp not nil?) can be 
 spelled as (complement nil?) 

 Robert 



-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Writing code to get the source of a function

2012-08-08 Thread Alan Malloy
(println (with-out-str (foo))) is silly - it's the same as (do (foo) nil), 
which in many cases (eg, in this one) is the same as just (foo).

On Wednesday, August 8, 2012 6:25:35 AM UTC-7, Joshua Ballanco wrote:

 On Wed, Aug 08, 2012 at 09:19:15AM +, Samuel Lê wrote: 
  Dear all, 
  
  I am trying to write some code that would take a function name, get its 
  source code, and create a new function based on the source code. 
  Unfortunately, the function 'source' from clojure.repl doesn't seem to 
 be 
  working for the functions I define. 
  Here is my code: 
  
  (ns test-src.core 
(:require [clojure.repl])) 
  
  (defn my-function [x] 
(+ x 1)) 
  
  (defn print-src [] 
(println (clojure.repl/source my-function))) 
  

 Try: 

 (defn print-src [] 
   (println (with-out-str (clojure.repl/source my-function 

 The source method is designed for the REPL, and so dumps to *out* by 
 default (you can confirm this yourself, appropriately enough, by doing 
 (source source)) 

 Cheers, 

 Josh 



 -- 
 Joshua Ballanco 

 ELC Technologies™ 
 1771 NW Pettygrove Street, Suite 140 
 Portland, OR, 97209 
 jbal...@elctech.com javascript: 

 P +1 866.863.7365 
 F +1 877.658.6313 
 M +1 646.463.2673 
 T +90 533.085.5773 

 http://www.elctech.com 


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: serlization of map ---- Invalid token: :

2012-08-06 Thread Alan Malloy
You are attempting to serialize the empty keyword. The empty string, , is 
fine to store, but : is not. You will get the same error from (read-string 
:).

On Monday, August 6, 2012 4:55:23 AM UTC-7, 4m1r wrote:

 I am using Storm which is based on Clojure. while emitting a map which has 
 keywords as keys we get the following exception. When we have strings as 
 keys we dont get this exception. Sounds like serialization problem. I have 
 also checked the source of LispReader it should have : as a valid token.

 java.lang.RuntimeException: Invalid token: :
 at clojure.lang.Util.runtimeException(Util.java:170)
 at clojure.lang.LispReader.interpretToken(LispReader.java:321)
 at clojure.lang.LispReader.read(LispReader.java:206)
 at clojure.lang.RT.readString(RT.java:1707)
 at clojure.core$read_string.invoke(core.clj:3361)
 at carbonite.serializer$clj_read.invoke(serializer.clj:26)
 at carbonite.serializer$fn__45$fn__46.invoke(serializer.clj:34)
 at 
 carbonite.serializer.proxy$com.esotericsoftware.kryo.Serializer$0.readObjectData(Unknown
  
 Source)
 at com.esotericsoftware.kryo.Kryo.readClassAndObject(Kryo.java:566)
 at carbonite.serializer$read_map$fn__89.invoke(serializer.clj:84)
 at carbonite.serializer$read_map.invoke(serializer.clj:79)
 at 
 carbonite.serializer$clojure_map_serializer$fn__92.invoke(serializer.clj:91)
 at 
 carbonite.serializer.proxy$com.esotericsoftware.kryo.Serializer$0.readObjectData(Unknown
  
 Source)
 at com.esotericsoftware.kryo.Kryo.readClassAndObject(Kryo.java:566)
 at carbonite.serializer$read_map$fn__89.invoke(serializer.clj:84)
 at carbonite.serializer$read_map.invoke(serializer.clj:79)
 at 
 carbonite.serializer$clojure_map_serializer$fn__92.invoke(serializer.clj:91)
 at 
 carbonite.serializer.proxy$com.esotericsoftware.kryo.Serializer$0.readObjectData(Unknown
  
 Source)
 at com.esotericsoftware.kryo.Kryo.readClassAndObject(Kryo.java:566)
 at carbonite.serializer$read_map$fn__89.invoke(serializer.clj:84)
 at carbonite.serializer$read_map.invoke(serializer.clj:79)
 at 
 carbonite.serializer$clojure_map_serializer$fn__92.invoke(serializer.clj:91)
 at 
 carbonite.serializer.proxy$com.esotericsoftware.kryo.Serializer$0.readObjectData(Unknown
  
 Source)
 at com.esotericsoftware.kryo.Kryo.readClassAndObject(Kryo.java:566)
 at carbonite.serializer$read_map$fn__89.invoke(serializer.clj:84)
 at carbonite.serializer$read_map.invoke(serializer.clj:79)
 at 
 carbonite.serializer$clojure_map_serializer$fn__92.invoke(serializer.clj:91)
 at 
 carbonite.serializer.proxy$com.esotericsoftware.kryo.Serializer$0.readObjectData(Unknown
  
 Source)
 at com.esotericsoftware.kryo.Kryo.readClassAndObject(Kryo.java:566)
 at carbonite.serializer$read_map$fn__89.invoke(serializer.clj:84)
 at carbonite.serializer$read_map.invoke(serializer.clj:79)
 at 
 carbonite.serializer$clojure_map_serializer$fn__92.invoke(serializer.clj:91)
 at 
 carbonite.serializer.proxy$com.esotericsoftware.kryo.Serializer$0.readObjectData(Unknown
  
 Source)
 at com.esotericsoftware.kryo.Kryo.readClassAndObject(Kryo.java:566)
 at carbonite.serializer$read_map$fn__89.invoke(serializer.clj:84)
 at carbonite.serializer$read_map.invoke(serializer.clj:79)
 at 
 carbonite.serializer$clojure_map_serializer$fn__92.invoke(serializer.clj:91)
 at 
 carbonite.serializer.proxy$com.esotericsoftware.kryo.Serializer$0.readObjectData(Unknown
  
 Source)
 at com.esotericsoftware.kryo.Kryo.readClassAndObject(Kryo.java:566)
 at carbonite.serializer$read_map$fn__89.invoke(serializer.clj:84)
 at carbonite.serializer$read_map.invoke(serializer.clj:79)
 at 
 carbonite.serializer$clojure_map_serializer$fn__92.invoke(serializer.clj:91)
 at 
 carbonite.serializer.proxy$com.esotericsoftware.kryo.Serializer$0.readObjectData(Unknown
  
 Source)
 at com.esotericsoftware.kryo.Kryo.readClassAndObject(Kryo.java:566)
 at carbonite.serializer$read_map$fn__89.invoke(serializer.clj:84)
 at carbonite.serializer$read_map.invoke(serializer.clj:79)
 at 
 carbonite.serializer$clojure_map_serializer$fn__92.invoke(serializer.clj:91)
 at 
 carbonite.serializer.proxy$com.esotericsoftware.kryo.Serializer$0.readObjectData(Unknown
  
 Source)
 at com.esotericsoftware.kryo.Kryo.readClassAndObject(Kryo.java:566)
 at carbonite.serializer$read_map$fn__89.invoke(serializer.clj:84)
 at carbonite.serializer$read_map.invoke(serializer.clj:79)
 at 
 carbonite.serializer$clojure_map_serializer$fn__92.invoke(serializer.clj:91)
 at 
 carbonite.serializer.proxy$com.esotericsoftware.kryo.Serializer$0.readObjectData(Unknown
  
 Source)
 at 

Re: reduction to tail recursion

2012-07-24 Thread Alan Malloy
I don't see how the definition of primitive-recursive is relevant to this. 
You can transform primitive recursion to tail recursion if you allocate a 
stack of your own on the heap, and don't mind that it might grow without 
bound. Or you can transform to continuation-passing or trampolines 
(fundamentally the same, as I understand it); that approach is 
tail-recursive but can lead to functions with very large closures.

For example, here is a definition of the Ackermann function using only tail 
calls:

(defn ack
  ([m n] (ack m n identity))
  ([m n cont]
 (cond (zero? m) (cont (inc n))
   (zero? n) (ack (dec m) 1 cont)
   :else (ack m (dec n) #(ack (dec m) % cont)

And here's the same thing transformed to use only JVM-friendly 
self-tail-recursion:

(defn ack [m n]
  (loop [m m, n n, stack ()]
(cond (zero? m) (if (empty? stack)
  (inc n)
  (recur (peek stack), (inc n), (pop stack)))
  (zero? n) (recur (dec m) 1 stack)
  :else (recur m (dec n) (conj stack (dec m))

There is nothing magic about the stack; if you're wiling to manage the 
(infinite) memory yourself, you can compute any computable function with 
just tail calls.

On Monday, July 23, 2012 10:18:35 PM UTC-7, Christian Mueller wrote:

 No, not any recursion can be expressed as a  tail recursion. One example: 
 the Ackermann function (http://en.wikipedia.org/wiki/Ackermann_function)

 On Saturday, July 21, 2012 11:15:33 AM UTC+2, Mimmo Cosenza wrote:

 Hi,
 a very basic question. Any not tail recursion code can be reduced to 
 tail recursion code? 

 Thanks

 Mimmo



-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: s-expression levels and higher order functions

2012-07-19 Thread Alan Malloy
No, but it's pretty easy to write:

(defn map-depth [f coll depth]
  (if (zero? depth)
(map f coll)
(for [x coll]
  (map-depth f x (dec depth)

On Tuesday, July 17, 2012 7:17:19 PM UTC-7, Seth Chandler wrote:

 I'm new both to Clojure and to this group, so please be gentle.  I come to 
 Clojure mostly from a Mathematica background, which has a certain Lispyness 
 to it.  One of the things one can do in Mathematica is to map a function to 
 an s-expression but not at its top level, but rather at some user specified 
 level.  Thus Map[f, {{a,b},{c,d}},{2}] will (because of the {2} as the last 
 argument) evaluate to {{f[a],f[b]},{f[c],f[d]}} rather than 
 {f[{a,b}],f[{c,d}]}.  I have found this capability of having functions that 
 work at levels of an expression to be extremely valuable.  Is there work 
 already done that extends the higher order functions to permit something 
 like this.  And, yes, I am sure one could write a macro and perhaps that 
 has already been done, but I was curious as to what was out there.  My 
 Google search did not yield much on this topic, but perhaps I used the 
 wrong Clojure vocabulary.

 Thanks


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: atom and lock

2012-07-18 Thread Alan Malloy
Sorta off-topic from the main discussion, but in reference to the error you 
pointed out, one clever fix for this is to add a delay around the future:

(defn cache-image [icache url]
  (let [task (delay (future (download-image url)))]
(doto (swap! icache update-in [url] #(or % task))
  (- (get url) (force)

(defn wait-for-image [icache url]
  (deref (force (get icache url

As long as your swap! never overwrites an existing delay, only one will get 
added, and thus only one gets forced.

On Wednesday, July 18, 2012 4:48:17 AM UTC-7, tbc++ wrote:

 (def icache (atom {})) 

 (defn cache-image [url] 
(let [f (future (download-image url))] 
  (swap! icache assoc url f))) 

 I'll admit, we'll still try to download the image twice if two people 
 try to cache the same image at the exact same time but we could get 
 around that using promise or agents. So in general, your attitude when 
 using atoms, refs, or agents should be get in and get out. Don't do 
 your work inside of swap!, send or alter 


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Concatenating InputStreams (was: Re: Parsing SGML)

2012-07-13 Thread Alan Malloy
(defn coll-enumeration [coll]
  (clojure.lang.SeqEnumeration. coll))

On Friday, July 13, 2012 7:13:54 AM UTC-7, Meikel Brandmeyer (kotarak) 
wrote:

 Hi,

 I think you don't handle the switching of streams correctly. You have to 
 keep track with atoms. But then you run into thread-safety issues.

 (defn concat-input-stream
   Gets one or many input streams and returns a new input stream that
   concatenates the given streams.
   [is  streams]
   (let [is  (atom is)
 streams (atom streams)
 switch! (fn []
   (locking is
 (.close @is)
 (reset! is (first streams))
 (swap! streams rest)))
 do-read (fn
   ([is] (if is (.read is) -1))
   ([is arr] (if is (.read is arr) -1))
   ([is arr off len] (if is (.read is arr off len) -1)))]
 (proxy [java.io.InputStream] []
   (close
 []
 (when @is
   (.close @is)
   (doseq [s @streams] (.close s
   (read
 ([]
  (let [ch (do-read @is)]
(if (neg? ch)
  (do
(switch!)
(if @is
  (.read this)
  -1))
  ch)))
 ([arr]
  (let [n (do-read @is arr)]
(if (neg? n)
  (do
(switch!)
(if @is
  (.read this arr)
  -1))
  n)))
 ([arr off len]
  (let [n (do-read @is arr off len)]
(if (neg? n)
  (do
(switch!)
(if @is
  (.read this arr off len)
  -1))
  n)))

 You could also use java.io.SequenceInputStream with a small helper.

 (defn coll-enumeration
   [coll]
   (let [s (atom coll)]
 (reify [java.util.Enumeration] []
   (hasMoreElements [this]
 (boolean (swap! s seq)))
   (nextElement [this]
 (locking this
   (if-let [sq (seq @s)]
 (let [e (first sq)]
   (reset! s (rest sq))
   e)
 (throw (java.util.NoSuchElementException.

 (defn concat-input-stream
   Gets one or many input streams and returns a new input stream that
   concatenates the given streams.
   [is  streams]
   (java.io.SequenceInputStream. (coll-enumeration (cons is streams

 All code untested.

 Kind regards
 Meikel



-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Concatenating InputStreams (was: Re: Parsing SGML)

2012-07-13 Thread Alan Malloy
It's a public class in clojure.lang that is not used by any part of the 
Clojure runtime or standard libraries. I can't think what other reason it 
would be included for, if not to be used by you. Just like 
clojure.lang.PersistentQueue - there's no nice Clojure wrapper for it (why 
on Earth not?), but it's still intended to be used by Clojure code.

On Friday, July 13, 2012 12:40:07 PM UTC-7, Meikel Brandmeyer (kotarak) 
wrote:

 Hi, 

 Am 13.07.2012 um 19:25 schrieb Alan Malloy: 

  (defn coll-enumeration [coll] 
(clojure.lang.SeqEnumeration. coll)) 

 Ah. I knew there must be something. But it doesn't seem to be official, 
 public API. 

 Meikel

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: idempotency

2012-06-30 Thread Alan Malloy
That's really a stricter requirement than idempotence (ie, functional 
purity). I don't believe the compiler ever does this. The JVM might, if 
it's able to inline some particular method call and discover therein that 
no mutation happens, but that's probably pretty rare given the amount of 
indirection that goes on when calling everything through the IFn interface.

On Saturday, June 30, 2012 5:30:02 PM UTC-7, Brian Marick wrote:

 In its optimization, does the Clojure compiler ever assume idempotency? 
 That is, does it ever look at a function application `(f x y z)` and say to 
 itself I may freely substitute the result of the first application of `f` 
 to those particular arguments for any later call? 

 I could imagine it doing that for built-ins (or just primitives?), but not 
 for user-defined functions (given the existence of atoms, etc.) I can also 
 imagine it not bothering for any calls. 

 - 
 Brian Marick, Artisanal Labrador 
 Contract programming in Ruby and Clojure 
 Occasional consulting on Agile 




-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: aot compilation of clojure source code...

2012-06-21 Thread Alan Malloy
On Thursday, June 21, 2012 2:36:21 PM UTC-7, Phil Hagelberg wrote:

 Jim - FooBar(); jimpil1...@gmail.com writes: 

  Yes ok I do get that...but wouldn't you agree that is slightly easier 
  for plain Java than it is for clojure? Especially for someone that has 
  no idea how the clojure compiler works...for example if you decompile 
  a clojrue ns it just seems plain wrong!!! 
  
  x = null; 
  y= null; 
  //do something with x and y 
  
  This is just plain confusing for a a java person isn't it? 

 Sure, it always depends on how much someone wants to figure it out. If 
 they're determined I'm sure they can figure out how locals-clearing 
 works. Reconstructing something approximating the original Clojure 
 source from bytecode is probably very hard, but learning how the program 
 works is not necessarily. 


It's really not that hard - for any given function, reconstructing what it 
does from the bytecode is mostly a matter of tedium, not of genius. 
Closures are a little more complicated because you have to figure out what 
context they fit into, but it's not terribly difficult because the Clojure 
compiler is pretty regular about how it does things. 

  


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: How to do aynchrounous producer/consumer

2012-06-15 Thread Alan Malloy
(map consume (seque (produce-lazily)))

On Friday, June 15, 2012 6:44:39 PM UTC-7, Warren Lynn wrote:


 What I want to do is something I probably have done dozens of times in 
 C++: two threads, one thread putting items in a queue, another taking it 
 out (FIFO). How to do it in Clojure? I am at a loss. I thought about a few 
 options:

 1. watches, but it cannot change the queue itself (can only watch). 
 plus, I am not sure watch function will run in another thread
 2. agent, but how to notify the consumer thread when there is new item? 
 How to block the consumer thread when there is no items in the queue?
 3.  Ping-pong promises: so the producer delivers a promise to the 
 consumer, and the consumer immediately deliver another promise to the 
 producer to acknowledge the receipt so the producer can move on. But that 
 will prevent the producer to put the next item into the queue before the 
 consumer finish its processing, so not exactly concurrent.

 I cannot believe I am the first one to encounter this. Can anyone suggest 
 some idiomatic solution for the above? Thank you.





-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: so why it has to be so complicated / Longest Increasing Sub-Seq

2012-06-13 Thread Alan Malloy
useful https://github.com/flatland/useful has a partition 
functionhttps://github.com/flatland/useful/blob/develop/src/useful/seq.clj#L222powerful
 enough to make the find increasing subsequences part pretty easy:

(defn lis [coll]
  (or (- coll
   (partition-between (partial apply =))
   (sort-by (comp - count))
   (filter next)
   (first))
  []))

This isn't much shorter than your approach, but it makes every step easy to 
write and understand, and avoids doing any manual bookkeeping as in a 
reduce. It doesn't help for 4clojure, obviously, since you don't have 
partition-between available, but it underscores the importance of finding 
common patterns and lifting them out into their own functions with 
pluggable spots for the non-shared behavior.

On Tuesday, June 12, 2012 12:11:07 PM UTC-7, Andy C wrote:

 Hi, 

 First a quick disclaimer. Those are my first steps in Clojure so I am 
 not be super accustomed to the language entire landscape and might 
 miss some basics here. However I was able to solve my first 4clojure 
 hard problem https://www.4clojure.com/problem/53 and have some second 
 thoughts after looking up top contributor's solutions as well as mine. 
 Why it has to be so complicated??? 

 Conceptually, you just reduce the list to list of lists using a simple 
 condition  . Then you filter items longer then 1. And at the same 
 time you reduce the output to a first longest list. In this case, 
 stack for recursion is really not required, although I did use it in 
 my solution since I could figure out the reduction based way to 
 partition the source sequence. 

 It also seems that imperative solution would be quite straightforward 
 although maintaining at least 4 state variables is not compelling at 
 all. Bottom line, I want to have a idiomatic Clojure solution ... Any 
 insight  

 Thx, 
 Andy 


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: Using read-string and macros together

2012-06-13 Thread Alan Malloy
This can't work as a macro - Sean's suggestion is just as broken as yours, 
in that it needs the form supplied to be a compile-time literal, because 
macros are expanded at compile-time. You can do this at runtime with eval: 
something like (defn xr [s] (eval `(fn [] ~(read-string s, though of 
course as always the use of eval is discouraged.

It's not relevant that (= '(println hello) (read-string (println 
\hello\))), because macros do not evaluate their arguments. You are 
actually seeing that, quite reasonably, (not= '(println hello) 
'(read-string (println \hello\))).

On Wednesday, June 13, 2012 4:29:54 PM UTC-7, Rob Harrop wrote:

 Hi,

 I have a use case where I'd like to load small forms in String format from 
 a database and wrap them in functions. This is to support some basic 
 runtime customisation.

 I'm having problems getting read-string and macros to play nicely, a 
 problem which can be distilled as below:

 ; a simple macro to return a fn
 (defmacro xr [f]
   `(fn [] ~f))

 ; calling the macro normally
 (apply (xr (println hello)) []) ; nil (and prints hello)

 ; calling with the result of read string
 (apply (xr (read-string (println \hello\))) []) ; (println hello) 
 (and prints nothing)

 I'm sure I'm missing something very obvious here but I had assumed that 
 since (= '(println rob) (read-string (println \rob\))) that the above 
 example would work.

 Regards,

 Rob Harrop


-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en

Re: If a protocol creates a Java interface under the covers...

2012-06-12 Thread Alan Malloy
On Jun 12, 5:56 am, Jim - FooBar(); jimpil1...@gmail.com wrote:
 On 12/06/12 13:53, Jim - FooBar(); wrote:

  On 12/06/12 13:47, Meikel Brandmeyer (kotarak) wrote:
  If update-position is a protocol function just call it without the
  dot. Just like a normal function. Then any reflection will go away
  and no type hint is needed.

  WHAT??? Seriously??? I'll try it...

  Jim

 OMG! You were right Meikel... I cannot believe this! I don't recall
 reading about this anywhere...

It's not just less convenient, but genuinely incorrect to use dot-
notation for protocol functions. Not every class that satisfies the
protocol will be implementing the interface directly, and so dot-
notation will fail on them. The interface generated by defprotocol
exists primarily to allow the compiler to optimize certain cases, not
because it's an interface your application should be using.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: using - on a nested hash-map with string keywords.

2012-05-31 Thread Alan Malloy
Yes, but really to GET a value nested IN a series of maps, he should
just be using get-in, rather than threading anything at all.

On May 31, 7:59 am, Dave Ray dave...@gmail.com wrote:
 Keywords implement IFn meaning they can act as functions that look
 themselves up in a map. Strings are just strings. Replace b with
 (get b) and you'll get the behavior you're looking for.

 Dave

 On Thu, May 31, 2012 at 7:55 AM, Boris V. Schmid boris.sch...@gmail.com 
 wrote:







  Can someone tell me what I'm overlooking (clojure 1.4)

  (- (hash-map :b (hash-map :a 3)) :b :a)
  3
  user (- (hash-map b (hash-map :a 3)) b :a)
  ; Evaluation aborted: java.lang.String cannot be cast to clojure.lang.IFn

  I'm not sure why the first can work, and the second cannot. Is it a logical
  limitation of the language, or an oversight in how the macro - is build?

  --
  You received this message because you are subscribed to the Google
  Groups Clojure group.
  To post to this group, send email to clojure@googlegroups.com
  Note that posts from new members are moderated - please be patient with your
  first post.
  To unsubscribe from this group, send email to
  clojure+unsubscr...@googlegroups.com
  For more options, visit this group at
 http://groups.google.com/group/clojure?hl=en

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Recursive lets

2012-05-29 Thread Alan Malloy
On May 29, 9:54 am, nicolas.o...@gmail.com nicolas.o...@gmail.com
wrote:
 Is there a way to write something like:

 (let [x (foo1 (fn []  (bar y)))
       y  (foo2 x)]   )

 where the y on line 1 refers to y in line 2?

 I currently use an atom and an affectation to tie the loop...

I agree with the other commenters that letfn is good when you can use
it, but here you can't use it. Your general approach is really the
best you can do, though it's nicer to use promise/deliver than atom/
swap!, since these values are never going to change again.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Do you leave a Swank / nREPL in your production servers?

2012-05-25 Thread Alan Malloy
On May 25, 2:30 pm, Sean Corfield seancorfi...@gmail.com wrote:
 The :host specifies the IP (or hostname) to listen on so if you want
 external access you'll need to listen on an IP that is externally
 accessible. If you listen on 0.0.0.0 then it'll listen on any IP
 address so you can REPL in from outside as well as directly on server
 itself (on 127.0.0.1). Our servers have multiple IP addresses and this
 caught me out at first when working with our data center folks and
 setting up VPN/DMZ access to the host/port.

This may be good advice in some cases (eg when all network access to
your server is trusted), but on a lot of production servers it
strikes me as very dangerous to apply this suggestion carelessly.
Assuming you have SSH access to the machine, by far the safest way to
do it is to have swank only listen on localhost, and then use SSH port
forwarding to redirect the connection through the localhost interface.
For example:

akm@dev-machine $ ssh -NfL 4010:localhost:4005 production-machine

# from emacs on dev-machine
M-x slime-connect RET RET 4010 RET

This way the only people who can connect remotely are those who have
permission to get a local application (usually sshd) to forward the
traffic to the localhost interface on their behalf.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: NullPointerException

2012-05-17 Thread Alan Malloy
There's nothing wrong is a pretty strong statement. It works, but it
is definitely the wrong way to do things. Using a letfn, or external
helper functions, is a much better approach.

On May 17, 12:19 pm, Armando Blancas abm221...@gmail.com wrote:
 The redefinition of functions somehow is spooking the compiler. But if
 you're at the REPL you should be seeing these warnings (are you doing AOT
 compile?)
 WARNING: double already refers to: #'clojure.core/double in namespace:
 user, being replaced by: #'user/double
 WARNING: * already refers to: #'clojure.core/* in namespace: user, being
 replaced by: #'user/*

 Clojure 1.2 will compile regardless; later versions will produce the NPE.
 There's nothing wrong with your parens or your use of local functions. I
 just changed double to doubl and * to x and it all works fine. The
 stack trace isn't pretty but the warnings would've helped, so it's good to
 try things at the REPL.







 On Wednesday, May 16, 2012 3:25:20 PM UTC-7, Sargash wrote:

  Hi!

  I have a problem. With that code:

  ; ===
  ; ex 1.17 multiply
  (defn ex1_17 []
    (defn double [x] (+ x x))
    (defn halve [x] (/ x 2))

    (defn * [a b]
      (cond
        (= b 0) 0
        (even? b) (* (double a) (halve b))
        :else (+ a (* a (- b 1)

    (println (* 5 5))
  )
  (ex1_17 )

  I gave that exception:

  Exception in thread main java.lang.NullPointerException, compiling:
  (D:\workprivate\ll\1\src\first.clj:3)
          at clojure.lang.Compiler.analyzeSeq(Compiler.java:6462)
          at clojure.lang.Compiler.analyze(Compiler.java:6262)
          at clojure.lang.Compiler.analyzeSeq(Compiler.java:6443)
          at clojure.lang.Compiler.analyze(Compiler.java:6262)
          at clojure.lang.Compiler.access$100(Compiler.java:37)
          at clojure.lang.Compiler$DefExpr$Parser.parse(Compiler.java:518)
          at clojure.lang.Compiler.analyzeSeq(Compiler.java:6455)
          at clojure.lang.Compiler.analyze(Compiler.java:6262)
          at clojure.lang.Compiler.analyze(Compiler.java:6223)
          at clojure.lang.Compiler.eval(Compiler.java:6515)
          at clojure.lang.Compiler.load(Compiler.java:6952)
          at clojure.lang.Compiler.loadFile(Compiler.java:6912)
          at clojure.main$load_script.invoke(main.clj:283)
          at clojure.main$script_opt.invoke(main.clj:343)
          at clojure.main$main.doInvoke(main.clj:427)
          at clojure.lang.RestFn.invoke(RestFn.java:408)
          at clojure.lang.Var.invoke(Var.java:415)
          at clojure.lang.AFn.applyToHelper(AFn.java:161)
          at clojure.lang.Var.applyTo(Var.java:532)
          at clojure.main.main(main.java:37)
          at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
          at
  sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:
  39)
          at
  sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImp 
  l.java:

  25)
          at java.lang.reflect.Method.invoke(Method.java:597)
          at
  com.intellij.rt.execution.application.AppMain.main(AppMain.java:
  120)
  Caused by: java.lang.NullPointerException
          at clojure.lang.Compiler$ObjExpr.emitVar(Compiler.java:4774)
          at clojure.lang.Compiler$DefExpr.emit(Compiler.java:418)
          at clojure.lang.Compiler$BodyExpr.emit(Compiler.java:5659)
          at clojure.lang.Compiler$FnMethod.doEmit(Compiler.java:5215)
          at clojure.lang.Compiler$FnMethod.emit(Compiler.java:5069)
          at clojure.lang.Compiler$FnExpr.emitMethods(Compiler.java:3600)
          at clojure.lang.Compiler$ObjExpr.compile(Compiler.java:4233)
          at clojure.lang.Compiler$FnExpr.parse(Compiler.java:3732)
          at clojure.lang.Compiler.analyzeSeq(Compiler.java:6453)
          ... 24 more

  Could you tell me where I wrong?

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Idiomatic usage of partial

2012-05-17 Thread Alan Malloy
#() syntax can accept as many arguments as you like. For example, you
can define partial using #():

(defn partial [f  args]
  #(apply f (concat args %)))

On May 16, 7:13 pm, greg r gsra...@bellsouth.net wrote:
 The reader notation is limited to the arity of the number of arguments
 provided.  partial allows variable arity.
 Check out pages 67-68 of Clojure Programming.

 Regards,
 Greg







 On Wednesday, May 16, 2012 1:57:40 PM UTC-4, Murtaza Husain wrote:

  Hi,

  What is the idiomatic use of partial. I understand it helps create
  closures, however the reader notation also allows to the same. So when
  should partial be use dover other forms of creating functions.

  Thanks,
  Murtaza

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Idiomatic usage of partial

2012-05-16 Thread Alan Malloy
On May 16, 2:05 pm, Stuart Sierra the.stuart.sie...@gmail.com wrote:
 Every literal instance of `fn` or `#()` compiles to a new class definition.
 This is only at compile time: once the code is running, each execution of
 the `fn` expression merely creates an instance of that class.

 partial is implemented in terms of `fn`, so every usage of `partial` merely
 creates an instance of a class that already exists. So using `partial`
 instead of `fn` or `#()` saves a small amount of memory.

Note also that the tradeoff goes both ways - (partial f x) can't know
how many more args to expect, so it has to create a vararg function,
use apply, and all that jazz - a lambda can just accept exactly the
right number of args and use them directly. So there's some runtime
penalty for using partial.

Of course, in both cases the difference is miniscule - use whatever
makes your intent clearer.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Partitioning a list when the result of a predicate becomes a certain value.

2012-05-10 Thread Alan Malloy
https://github.com/flatland/useful/blob/develop/src/useful/seq.clj#L189
is a more general version of partition-by, which can easily handle
your requirements.

On May 10, 2:11 pm, Ant ant...@gmail.com wrote:
 Hi all,

 I am battering my head against the following problem which I'm sure is
 straightforward if only I knew how. I want to partition the following
 list:

 '(aa123 x y z bb123 ccq23 3 yg)

 into the following:

 ((aa123 x y z) (bb123) (ccq23 3 yg))

 The predicate is:

 #(re-matches #^(\w)\1.* %)

 partition-by doesn't work, since it splits the sequence when the
 result of applying the predicate changes. I want to partition when the
 predicate becomes a particular value.

 Any clues on how to accomplish this would be gratefully received!

 Thanks,

 Anthony.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Partitioning a list when the result of a predicate becomes a certain value.

2012-05-10 Thread Alan Malloy
On May 10, 3:19 pm, Jack Moffitt j...@metajack.im wrote:
     (when-let [s (seq coll)]
       (let [run (cons (first s) (take-while #(not= value (f %)) (next
  s)))]
        (cons run (partition-when f value (seq (drop (count run) s
       )
     )
   )
  )
 ...
  What test?

 (seq coll) is the test here. when-let (and if-let, etc) bind only when
 the right hand side is truthy.

 (when-let [x true]
   (println this prints))

 (when-let [x false]
   (println this does not print))

 It's a common shortcut for:

 (let [x (something-something)]
   (when x
      ))


Not quite true in the general case, though. Consider

(let [x 1]
  (if-let [x foo]
x   ;; should be foo
x)) ;; should be 1

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Reducers

2012-05-08 Thread Alan Malloy
My understanding is that reducers/map merely returns a new function
(or something like a function, maybe an instance of IReducible or
something), and all actual computation is done during the reduce. So
dynamic bindings around the scope of the map have no effect at all.

On May 8, 10:57 am, Mark Engelberg mark.engelb...@gmail.com wrote:
 Exciting!

 I'm having trouble visualizing at what points the computation is actually
 executed, and therefore, I'm not clear on how this feature interacts with
 dynamic binding.  If the reducers/map occurs in one dynamic binding
 context, and the fold occurs in another, what happens?

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: LinkedHashMap not well supported

2012-04-30 Thread Alan Malloy
On Apr 30, 7:53 pm, kurtharriger kurtharri...@gmail.com wrote:
 Sounds good. Ill submit a patch for walk. Im not real sure why apply hash-map 
 didnt work, but if figure it out Ill add that too.

For the same reason that (apply hash-map {1 2, 3 4}) doesn't work: the
maps seqs as ([1 2] [3 4]), not as (1 2 3 4).

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Typed Clojure 0.1-alpha2

2012-04-21 Thread Alan Malloy
He did say, compile-time error. These errors are at run-time - that
is, the following is just as obviously bad, but generates no warning
until bar is called:

(defn foo [x] 1)

(defn bar [y] (foo y 1)) ;; compiles fine

(bar 5) ;; throws runtime exception

On Apr 21, 5:14 pm, Softaddicts lprefonta...@softaddicts.ca wrote:
 

 user= (defn a [x y] x)
 #'user/a
 user= (a 1)
 java.lang.IllegalArgumentException: Wrong number of args passed to: user$a 
 (NO_SOURCE_FILE:0)
 user= (a 1 2)
 1
 user= (a 1 2 3)
 java.lang.IllegalArgumentException: Wrong number of args passed to: user$a 
 (NO_SOURCE_FILE:0)
 user=

 user= (defn b [x  ys] x)
 #'user/b
 user= (b 1)
 1
 user= (b 1 2)
 1
 user= (b)
 java.lang.IllegalArgumentException: Wrong number of args passed to: user$b 
 (NO_SOURCE_FILE:0)
 user=

 Where's the missing arity validation you are referring to ?

 Luc









  Looks interesting.

  Personally I always thought clojure's handling of function arity is a
  bit strange. I don't understand why calling a function like this

  (defn testfn [one two] ...)

  (test-fn 1)

  is not at least a compiler warning, possibly with a switch for the
  compiler for strict checking. I understand that it is not always
  possible to perform this check, but why not do it when possible? It
  would make clojure alot safer to use without a test suite covering
  every code path.

  On Apr 20, 8:50 pm, Ambrose Bonnaire-Sergeant
  abonnaireserge...@gmail.com wrote:
   Hi,

   I know there are a few people interested in trying Typed Clojure,
   so I've cut an early alpha release to give a taste.

   These are *very* early days, but looking through the readme will
   give you some hints as to what works in this release. Don't
   expect too much.

  https://github.com/frenchy64/typed-clojure

   Please give it a whirl, feedback welcome!

   Thanks,
   Ambrose

  --
  You received this message because you are subscribed to the Google
  Groups Clojure group.
  To post to this group, send email to clojure@googlegroups.com
  Note that posts from new members are moderated - please be patient with 
  your first post.
  To unsubscribe from this group, send email to
  clojure+unsubscr...@googlegroups.com
  For more options, visit this group at
 http://groups.google.com/group/clojure?hl=en

 --
 Softaddictslprefonta...@softaddicts.ca sent by ibisMail!

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Treatment of nil/null in a statically typed Clojure

2012-04-19 Thread Alan Malloy
On Apr 19, 4:06 pm, James Reeves jree...@weavejester.com wrote:
 On 19 April 2012 19:46, Ambrose Bonnaire-Sergeant

 abonnaireserge...@gmail.com wrote:
  I've been doing some thinking about the treatment of nil in a
  statically typed version of Clojure.

 Statically typed in what way? Java's type system doesn't seem
 particularly suited to a functional programming language like Clojure.

 - James

There's nothing about functional programming that precludes static
typing. Haskell, say, does a lovely job of static typing without
making you pound out a bunch of keyboard typing for every function
like Java would.

For example, the type signature for foldl (Haskell's reduce) is:
(a - b - a) - a - [b] - a

Reduce takes:
  - A function taking an A and a B and returning an A
  - An A to start with
  - A list of Bs
And returns an A.

This is sufficiently general for all applications of reduce, and if
you don't feel like typing it out the compiler can infer it for you
from the source.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: a convenience idea for test functions

2012-04-17 Thread Alan Malloy
IMO this is fairly absurd for a language default, but you can easily
do this yourself in a number of ways. For example:

(defmacro define-preds [ preds]
  (cons `do
(for [pred preds]
  `(defmacro ~(symbol (str pred +)) ~'[obj then else]
 (list '~'if (list '~pred ~'obj)
   ~'then ~'else)

(define-preds map? string?)

(map?+ {} 1 2) ;; 1

This would be quite a lot easier if we didn't care about the short-
circuiting behavior of 'if, since then a simple higher-order function
would do it, something like (defn as-switch [pred] (fn [obj then else]
(if (pred obj) then else))).

On Apr 17, 9:16 pm, Dmitri dmitri.sotni...@gmail.com wrote:
 Often times I find myself writing code like the following

 (if (map? foo) bar baz)

 would it make sense to make test functions variadic, so if only passed
 a single argument it would return true/false, but could also act as an
 if when passed 3 arguments, eg:

 (map? foo bar baz) would return bar if foo is a map and baz otherwise.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Should I better use a state monad (and how)?

2012-04-16 Thread Alan Malloy
On Apr 15, 8:25 pm, Nicolas Buduroi nbudu...@gmail.com wrote:
 I'm working on a turn-based game and I'm looking for a good way to manage
 states. In the game each turn is composed of multiple phases. I started by
 using atoms for the phases field (this is a sequence of functions) in a
 record and realized that it wouldn't be ideal to keep track of states in
 the case where I'd need to keep a snapshot of every phases. Here's the
 original code I had:

 (defrecord Game [phases]
   (next-phase [this]
     (stop-timer)
     (swap! phases #(conj (vec (rest %)) (first %)))
     (log :info change phase to %s (key (first @phases)))
     (start-phase this))

 I then started to think that this would be a good opportunity to use a
 state monad. I've tried to reimplement the above code using the algo.monads
 library but the result was less than satisfactory (probably due to my own
 shortcoming), here's the monadic version:

 (defrecord Game [phases]

   (next-phase [this]
     (-
      ((domonad state-m
         [_ (fn [s] (stop-timer) [s s])
          _ (update-state
             (fn [s]
               (update-in s [:phases]
                          #(conj (vec (rest %)) (first %)
          _ (fn [s]
              (log :info change phase to %s (key (first (:phases s [s 
 s])]
         nil)
       state)
      second
      start-phase))

 As my code probably doesn't need the full power of the state monad, I tried
 to write a lighter-weight version using the following macro:

 (defmacro  [ state-and-forms]
   (reduce #(list (if ('#{fn fn*} (first %2))
                    %2
                    `(fn [s#] ~%2 s#)) %)
           state-and-forms))

 Which let me write:

   (next-phase [state]
     ( state
      (stop-timer)
      (fn [s] (update-in s [:phases] #(conj (vec (rest %)) (first %
      #(do (log :info change phase to %s (key (first (:phases % %)
      #(start-phase %)))

 With some more helper macro this version looks promising. In the end I
 wonder if there's some Clojure feature I'm overlooking or if I should
 rethink the whole solution? Is there a better way to accomplish this?

 #(conj (vec (rest %)) (first %)) is a really awful way to implement a
queue. Just use clojure.lang.PersistentQueue, which works with the
conj/peek/pop functions in clojure.core.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: where do you put the docstring in a deftype declaration?

2012-04-12 Thread Alan Malloy
A deftype creates a java class, not a clojure var. Classes have no
slots to store a docstring. Just put a comment somewhere.

On Apr 12, 9:52 pm, Frank Siebenlist frank.siebenl...@gmail.com
wrote:
 Confusingly yours, FrankS.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: seeking a lazy way to interleave a constant

2012-04-10 Thread Alan Malloy
On Apr 10, 12:36 am, David Powell d...@djpowell.net wrote:
  As an aside.. I just looked at the source for this, what does the :static

 tag in the metadata do?

 From what I can make out... nothing.  I think it is left over from an
 experiment to improve var lookup times prior to dynamic binding being
 disabled by default.

Confirmed: all of the compiler's interactions with the :static key are
currently commented out.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: Advice on style implementation

2012-04-04 Thread Alan Malloy
On Apr 4, 6:50 am, David Jagoe davidja...@gmail.com wrote:
 Particularly I very often find myself doing

 (apply hash-map (flatten (for [[k v] some-map] ...)))

:( :( :( flatten is vile, never use it[1]. What if the value in the
map is a list, or the key is a vector? Now you've broken it. Instead
use into:

(into {}
  (for [[k v] some-map]
[k (f v)])) ;; or whatever k/v pair you want

I'm also very surprised to see (apply merge-with vector ...), because
this seems like it is rarely right. If you have three maps, {:a 1},
{:a 2}, and {:a 3}, do you really want the result to be {:a [[1 2]
3]}? You're probably better off converting to {:a [1]} {:a [2]} {:a
[3]} beforehand and using (apply merge-with into ...).

Your implementation of selected? is also strange - why are you
iterating through the keys, instead of using their fast lookup? I'd
write (selected? [coll] (contains? select coll)). But that brings up
another point: selected? and agg are just partial applications of
contains and get:

(let [selected? (partial contains? select)
  agg (partial get select)]
  ...)

Or, if you prefer never to repeat anything:

(let [[selected? agg] (for [f [contains? get]]
(partial f select))]
  ...)

[1] technically you want it sometimes, but I strongly suggest staying
away.


 Any pointers or advice on improving my style will be much appreciated!

 (defn aggregate
   Aggregate rows using the functions provided in select and after
    filtering the rows by where.

     E.g.

       (aggregate [{:a 1 :b 2} {:a 3 :b 4} {:a 5 :b 6}] :select {:a +}
 :where (fn [r] ( (:b r) 6))) -- {:a 4}

     [rows  {select :select where :where}]
     (letfn [(selected? [col] (some #{col} (keys select)))
              (agg [col] (get select col))]
       (apply hash-map
              (flatten
               (for [[k vs] (apply merge-with vector (filter where
 rows)) :when (selected? k)]
                 [k (apply (agg k) vs)])

 Thanks,

 --
 David Jagoe

 davidja...@gmail.com
 +447535268218

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


Re: What's the efficient functional way to computing the average of a sequence of numbers?

2012-03-29 Thread Alan Malloy
On Mar 29, 10:18 am, David Cabana drcab...@gmail.com wrote:
 On Thu, Mar 29, 2012 at 12:18 AM, simon.T simon.j@gmail.com wrote:
  The obvious way is like the following, which traverse the sequence 2 times.
  ...

 The obvious way does not necessarily traverse the sequence twice.  If
 a sequence S satisfies the 'counted?' predicate, (count S) takes
 constant time. In particular
 user= (counted? [:a :b :c])
 true

 user= (counted? '(:a :b :c))
 true

 user= (counted? {:a 1 :b 2 :c 3})
 true

 user= (counted? #{:a :b :c})
 true

 The examples are stolen 
 from:http://clojuredocs.org/clojure_core/clojure.core/counted_q

 So it is very likely that (/ (reduce + coll) (count coll)) will not
 traverse 'coll' twice, and the natural way is the preferred way.
 Insert standard warning about premature optimization./

Very likely strikes me as a huge overstatement here. Most sequences
that you want to average won't be source-code literals, they'll be
lazy sequences, and those aren't counted.

-- 
You received this message because you are subscribed to the Google
Groups Clojure group.
To post to this group, send email to clojure@googlegroups.com
Note that posts from new members are moderated - please be patient with your 
first post.
To unsubscribe from this group, send email to
clojure+unsubscr...@googlegroups.com
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en


  1   2   3   4   >