
local reference(+Name, ?Init)

   Creates a named reference called Name with intial value Init.

Arguments
   Name                An atom.
   Init                A ground term, or an anonymous variable

Type
   Non-logical Variables, Arrays, Bags, Shelves and Stores

Description
   This creates a named reference with the atomic name Name and initial
   value Init.  Usually, this would be done in a directive.

   A named reference can be used to hold a reference to a term in the same
   way as a logical variable.  Unlike a non-logical variable, the value
   of a reference is not a copy, but identical to the original term it
   was set to.  This implies that the value behaves logically, i.e. 
   it disappears on backtracking, bindings to the variables inside it
   are undone on backtracking etc.  A typical example of its use is global
   state that a set of predicates wants to share without having to
   pass an argument pair through all the predicate invocations. 

   Changing the value of a reference is similar to changing an argument
   of a compound term using setarg/3.

   The initial value of the reference is Init, which must be a ground term
   or an anonymous variable (if it is an anonymous variable, the initial
   value of the reference is a different, unique variable).

   There are no arrays of references, but the same effect can be
   achieved by storing a structure in a reference and using the
   structure's arguments.  The arguments can then be accessed and
   modified using arg/3 and setarg/3 respectively. 

   Reference names are visible in the module where they are declared.
   Furthermore every ECLiPSe engine has its own reference store,
   meaning that the values are engine/thread-local and cannot be shared.

   Side note: When a reference is re-declared with a different Init value
   during execution, the effect only becomes visible once execution fails
   back to the reference's initial state.  A current value that is the
   result of a setref/2 is not affected.


Modes and Determinism
   reference(+, ++) is det
   reference(+, -) is det

Exceptions
     4 --- Name is not instantiated.
     4 --- Init is not a nonground compound term.
     5 --- Name is not an atom.

Examples
   
% declaring a reference

      :- local reference(a,0).
      yes.

% values of references are subject to backtracking:

      ?- ( getref(a, Old), setref(a, 27), getref(a, New)
	 ; getref(a, Then)
	 ).
      Old = 0
      New = 27
      Then = Then
      Yes (0.00s cpu, solution 1, maybe more) ? ;

      Old = Old
      New = New
      Then = 0
      Yes (0.00s cpu, solution 2)


% comparison between references and nonlogical variables.

      :- local reference(r), variable(v).
      yes.

% references are subject to backtracking, nonlogical variables survive:

      ?- ( setref(r, 27), fail
         ; getref(r, New)
	 ).
      New = 0
      Yes (0.00s cpu)

      ?- ( setval(v, 27), fail
         ; getval(v, New)
	 ).
      New = 27
      Yes (0.00s cpu)

% references refer to the original term, nonlogical variables to copies:

      ?- Term = p(X), setref(r, Term), getref(r, Y), Y == Term.
      X = X
      Y = p(X)
      Term = p(X)
      yes.

      ?- Term = p(X), setval(v, Term), getval(v, Y), Y == Term.
      no (more) solution.



See Also
   setref / 2, getref / 2, swapref / 3, setarg / 3, arg / 3
