Hi Phil,

At some point in time after a prolonged exposure to Clojure, my mind shifted,
I now think about my program flow as values, not containers being passed along.

I take the problem the reverse way to find out if there's a need for a var vs a 
fn and state
lifecyle.
Here's a short summary of my reasonning:

a) I just find out how long a value need to 'survive' to decide how to 
implement it's access
and its scope.

   Most of the time values are ephemeral so the answer is obvious, a local 
binding is enough
   if there's a need to name it.

b) If a value is required during the lifespan of the process then his scope is 
probably global
and a var is an obvious choice.

c) If a value reflects a state (as understood by clojure) that will change in 
time then an
atom or ref can be used. Then its scope determines if it will end up in a var
or not.

   I try to wrap a state lifecycle in a API. Most of the time leaking to the 
outside world involves
   too much refactoring, it may look simple at the beginning but you get caught 
in a
   forest fire at some point. 

d) I try to stay away from dynamic bindings except in rare cases (syntactic 
sugar for DSLs, ...).

e) I do not consider Java objects as values. Their internal mutation 
disqualifies them to me.

  They seldom make it in a var in my world except when there's no other choice
  (database connection pool, ...). I try to confine them at the edge of the 
code and wrap
  their access in a function.

  If possible I try to avoid leaking them to the outside world.

  I try to shorten their lifespan even if it means that they will get 
reallocated 
  more often.

  The main reason being that I want to avoid having to think about things like
  are they multithread safe ? To they have a finite lifecycle which prevents 
reuse ?

  They will get buried in a value as we know it in Clojure if they have to leak 
out.
  Makes it a bit harder to access them directly.

  If a Java object lifecycle has to leak, I wrap it in a API that relates to 
the application state,
  not to the object itself.

The net result is that my code has few vars aside from the functions themselves 
and less
state concerns.

I agree that it requires some brain cells rewiring. I went along that path the 
first year I
worked non-stop with Clojure.

Luc P.

> 
> Actually, I think that this is a real problem with Clojure, and with
> data access. It is very hard to change between accessing a var as a
> value and through calling a value.
> 
> I can give two concrete examples of this. First, in my library I used a
> var to store a factory object from a Java API. So I created one and
> stored it in a var. This worked well, in general, but when I integrated
> my library into an application, I realised that I need to get this
> factory object from elsewhere -- in short I needed a function call. So I
> had to change all of my `data-factory` calls to `(data-factory)`.
> 
> Another time the same issue hit me was with Clojure's :doc metadata.
> This is stored as a string, but I wanted to be able to subvert this by
> calculating the string from the object containing in the var. As far as
> I can tell, this is impossible in Clojure without changing all the
> client code that accesses the :doc metadata.
> 
> Java does not have this problem by common design patterns -- fields are
> declared private and always accessed through a function. If I understand
> things correctly, Scala avoids the problem in the same way, although it
> autocodes the accessors for you, so avoids the boilerplate.
> 
> In Clojure, it seems the only way to avoid this would to wrap up values
> in `constantly` and access everything as a function.
> 
> Phil
> 
> -- 
> 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.
> 
--
Luc Préfontaine<lprefonta...@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
--- 
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.

Reply via email to