for FAQ: what are use/require/import/refer?

2008-12-20 Thread Stuart Sierra

This might make a good FAQ question:

On Dec 20, 11:25 am, chris cnuern...@gmail.com wrote:
 I am unclear as to the difference between refer, import use, and require.

Hi Chris,

require: Load a Clojure library from a file on classpath.  Use this
when you want to load a library, but leave it in its own namespace.

refer: Bring public symbols from one namespace into the current
namespace.  Use this when a library has already been loaded (example:
clojure.set) but you want to use its public symbols without a
namespace qualifier.

import: Copy Java class names into current namespace.  Use this when
you want to use a Java class without typing the full package name.

use: Combination of require and refer.  Use this when you want to load
a library AND use its symbols without a namespace qualifier.

All four are available as keyword arguments to ns, which is the
preferred way to use them:

(ns foo.bar
  (:use my.little.lib)
  (:require clojure.contrib.duck-streams)
  (:import (java.io File InputStream))
  (:refer clojure.set))

:require also allows aliasing, like this:
(ns foo.bar
  (:require [clojure.set :as set]))

Now you can write the symbol clojure.set/union as set/union.

-Stuart Sierra
--~--~-~--~~~---~--~~
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
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: for FAQ: what are use/require/import/refer?

2008-12-20 Thread Brian Doyle
This would make an excellent FAQ question and answer!

On Sat, Dec 20, 2008 at 9:53 AM, Stuart Sierra
the.stuart.sie...@gmail.comwrote:


 This might make a good FAQ question:

 On Dec 20, 11:25 am, chris cnuern...@gmail.com wrote:
  I am unclear as to the difference between refer, import use, and require.

 Hi Chris,

 require: Load a Clojure library from a file on classpath.  Use this
 when you want to load a library, but leave it in its own namespace.

 refer: Bring public symbols from one namespace into the current
 namespace.  Use this when a library has already been loaded (example:
 clojure.set) but you want to use its public symbols without a
 namespace qualifier.

 import: Copy Java class names into current namespace.  Use this when
 you want to use a Java class without typing the full package name.

 use: Combination of require and refer.  Use this when you want to load
 a library AND use its symbols without a namespace qualifier.

 All four are available as keyword arguments to ns, which is the
 preferred way to use them:

 (ns foo.bar
  (:use my.little.lib)
  (:require clojure.contrib.duck-streams)
  (:import (java.io File InputStream))
  (:refer clojure.set))

 :require also allows aliasing, like this:
 (ns foo.bar
  (:require [clojure.set :as set]))

 Now you can write the symbol clojure.set/union as set/union.

 -Stuart Sierra
 


--~--~-~--~~~---~--~~
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
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: for FAQ: what are use/require/import/refer?

2008-12-20 Thread chris

That really helped out a lot, thanks guys!

As long as we are on the subject of helping out newbs...

I like to program from the repl.

I have a namespace that maintains some state, mainly integration with
openGL.  It has some essentially static variables that can't get
initialized until openGL is initialized (like recording the version,
vendor, extensions, and the renderer).

I have put everything ui-related in one namespace called
lambinator.ui.  I have split this namespace up into two files, on for
variable definitions and another for function definitions.  The reason
is that I usually don't want my variables cleared when reloading the
file through load-file using the repl.

I am using simple def's to define the variables; the ones that may be
changed through opengl callbacks on other threads I am protecting with
refs.

So to be clear, I have:

main-ns-file - this contains defs and calls load on the function
file
function def file - this gets loaded all the time when I am working
in the repl.

1.  Is using defs the best way to go about this?  They are global
variables; they model static state of the system, essentially.  I
might associate them with the main window, however, instead of global
defs like they are now.
2.  How do defs handle updating when I reload a file in the repl and
then something in some other thread triggers a render?  Lets say I
change the render function which is called from the GLEventListener
object on display.  It is defined through a simple defn.  Does this
change propagate through to the other threads?  Are defs themselves
protected if they are at the module/file level?  I was thinking maybe
all the threads shared an environment which is itself a functional
datastructure protected by refs...
3.  If this is the case, do I need to protect my def'd variables with
refs?
4.  Is there some way to call load that ignores variable definitions
if it has already seen them but does update function definitions
regardless?
5.  Finally, in the function-def file I have an in-ns definition, not
a 'ns definition.  This means that I *have* to use (import and (use,
and I can't use :import or :use, correct?  The documentation for in-ns
didn't indicate that the keyword options were viable or I missed that
piece of info.  An answer to 4 would make 5 irrelevant.

Again, thanks to everyone for their replies!

Chris

On Dec 20, 9:53 am, Stuart Sierra the.stuart.sie...@gmail.com wrote:
 This might make a good FAQ question:

 On Dec 20, 11:25 am, chris cnuern...@gmail.com wrote:

  I am unclear as to the difference between refer, import use, and require.

 Hi Chris,

 require: Load a Clojure library from a file on classpath.  Use this
 when you want to load a library, but leave it in its own namespace.

 refer: Bring public symbols from one namespace into the current
 namespace.  Use this when a library has already been loaded (example:
 clojure.set) but you want to use its public symbols without a
 namespace qualifier.

 import: Copy Java class names into current namespace.  Use this when
 you want to use a Java class without typing the full package name.

 use: Combination of require and refer.  Use this when you want to load
 a library AND use its symbols without a namespace qualifier.

 All four are available as keyword arguments to ns, which is the
 preferred way to use them:

 (ns foo.bar
   (:use my.little.lib)
   (:require clojure.contrib.duck-streams)
   (:import (java.io File InputStream))
   (:refer clojure.set))

 :require also allows aliasing, like this:
 (ns foo.bar
   (:require [clojure.set :as set]))

 Now you can write the symbol clojure.set/union as set/union.

 -Stuart Sierra
--~--~-~--~~~---~--~~
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
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: for FAQ: what are use/require/import/refer?

2008-12-20 Thread Stuart Sierra

On Dec 20, 12:44 pm, chris cnuern...@gmail.com wrote:
 1.  Is using defs the best way to go about this?  They are global
 variables; they model static state of the system, essentially.  

Yes, global variables are probably best as Vars (which is what def
creates).

 2.  How do defs handle updating when I reload a file in the repl and
 then something in some other thread triggers a render?  

Re-evaluating a def changes the root binding of a Var, which affects
all threads but NOT in a protected, transactional way as with Refs.

 3.  If this is the case, do I need to protect my def'd variables with
 refs?

If you want Ref-style transaction semantics, then yes.  But if they
are static values that don't change, then no.

 4.  Is there some way to call load that ignores variable definitions
 if it has already seen them but does update function definitions
 regardless?

Yes, use defonce, which won't re-def things that already exist:
clojure.core/defonce
([name expr])
Macro
  defs name to have the root value of the expr iff the named var has
no root value,
  else expr is unevaluated

 5.  Finally, in the function-def file I have an in-ns definition, not
 a 'ns definition.  This means that I *have* to use (import and (use,
 and I can't use :import or :use, correct?  

Not exactly.  It's true, in-ns takes no other arguments.  But
typical usage would be something like this:

top-level file my/cool/lib.clj:
(ns my.cool.lib
  (:use ...) ; everything you need to use
  (:import ...)  ; everything you need to import
  (:load my/cool/lib/part1 my/cool/lib/part2))

second file my/cool/lib/part1.clj:
(in-ns 'my.cool.lib)


third file my/cool/lib/part2.clj:
(in-ns 'my.cool.lib)


The top-level ns contains all the imports/uses/requires you need for
the namespace, and the (:load ...) controls the order in which the
subsidiary files are loaded.  Each of the subsidiary files just does
(in-ns ...), giving them access to everything used/imported in the top-
level ns.

I forgot whether the arguments to (:load ...) need slashes at the
beginning.  Either way, they're inside CLASSPATH.

Ok, that was a lot; I hope some of it made sense.

-Stuart Sierra

--~--~-~--~~~---~--~~
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
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
-~--~~~~--~~--~--~---