\input texinfo   @c -*-texinfo-*-
@c %**start of header
@setfilename sather-tutorial.info
@settitle Language Examples
@c %**end of header

@setchapternewpage odd

@ifinfo
Sather Eclectic Tutorial

Copyright (C) 1995 by International Computer Science Institute
This file is part of the GNU Sather package. It is free software; you may
redistribute  and/or modify it under the terms of the  GNU General Public
License (GPL)  as  published  by the  Free  Software  Foundation;  either
version 2 of the license, or (at your option) any later version.
This  program  is distributed  in the  hope that it will  be  useful, but
WITHOUT ANY WARRANTY without even the implied warranty of MERCHANTABILITY
or FITNESS FOR A PARTICULAR PURPOSE. See Doc/GPL for more details.
The license text is also available from:  Free Software Foundation, Inc.,
59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
----------->  Please email comments to <bug-sather@@gnu.org>  <-----------
@end ifinfo

@titlepage
@sp 5
@comment The title is printed in a large font.
@center @titlefont{Sather Eclectic Tutorial}
@sp 5
@center July 11, 1995
@sp 5
@center Benedict Gomes (gomes@@icsi.berkeley.edu) 
@sp 5
@center International Computer Science Institute
@center 1947 Center Street, Suite 600
@center Berkeley, California 94704

@c The following two commands start the copyright page.
@page
@vskip 0pt plus 1filll
Copyright @copyright{} 1995 by International Computer Science Institute

This file is part of the GNU Sather package. It is free software; you may
redistribute  and/or modify it under the terms of the  GNU General Public
License (GPL)  as  published  by the  Free  Software  Foundation;  either
version 2 of the license, or (at your option) any later version.

This  program  is distributed  in the  hope that it will  be  useful, but
WITHOUT ANY WARRANTY without even the implied warranty of MERCHANTABILITY
or FITNESS FOR A PARTICULAR PURPOSE. See Doc/GPL for more details.

The license text is also available from:  Free Software Foundation, Inc.,
59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
@end titlepage

@node Top, ,(dir),(dir)
@comment node-name, next, previous, up
@section Introduction
@cindex Introduction

This document introduces some of the trickier concepts in Sather,
particularly concepts that might not be familiar to a C++ or Smalltalk
programmer.  This document is between a tutorial and the language spec.
It is not a guided tour of the language; rather, it explains (with
examples) certain aspects of the language that might not be obvious from
reading the language spec.  Some portions of this may find their way
into the 1.1 document. Each section begins with a list of the points
that are illustrated. Contributions are welcome @dots{}

@menu
* Development Environment::     A brief description of the compiler and
                                development environment.
* Concrete Classes::            Using and defining concrete classes
                                (reference classes)
* Abstract Types::              Using and defining Abstract ($ classes)
* Value Classes::               @strong{Using and defining value types such as
                                INTs and FLTs.}
* Bound Routines::              @strong{Bound routine type definitions and usage.}
* Problems and Bugs::           (not yet) Some common problems and bugs
                                that you might encounter.
* Concept Index::               Index of the concepts in this document
@end menu

@example
@strong{<A href="http://www.icsi.berkeley.edu/~gomes/sather-top.html">Who's working on what?</A>}
@end example

An unofficial directory of people working on various library classes.

@example
@strong{<A href="http://www.icsi.berkeley.edu/Sather">The Sather Home Page</A>}
@end example

@subsubsection Acknowledgements
@cindex Acknowledgements

This document incorporates ideas and feedback from David Stoutamire,
David Bailey, Jerome Feldman, Michael Philippsen and others. Portions of
this document will become a part of the 1.1 manual.  This is a texinfo
document, and will eventually be available as on-line GNU info files, as
well as in textual and html form.

@subsection What is Sather?
@cindex What is Sather?

This document has grown long enough that some introduction of the topic
seems obligatory.  This section is largely from the manual and will
eventually be changed to reflect what is actually in this document.

Sather is an object-oriented language that supports highly efficient
computation, powerful abstractions for encapsulation and code reuse, a
flexible development environment, and constructs for improving code
correctness. It has statically-checked strong typing, multiple
inheritance, explicit subtyping which is independent of implementation
inheritance, parameterized types, dynamic dispatch, iteration
abstraction, higher-order routines and iters, garbage collection,
exception handling, assertions, pre-conditions, postconditions, and
class invariants.

@cindex Concrete Classes
Data structures in Sather are constructed from objects, each of which
has a specific concrete type that determines the operations that may be
performed on it. The implementation of concrete types is defined by
textual units called classes.

@cindex Abstract types
Abstract types specify a set of operations without providing an
implementation and correspond to sets of concrete types.  Sather
programs consist of classes and abstract type specifications.  Each
Sather variable has a declared type which determines the types of
objects it may hold.

@cindex Features 
Classes define the following features: object attributes which make up
the internal state of objects, shared and constant attributes which are
shared by all objects of a type, routines which perform operations on
objects, and iters which encapsulate iteration. Features may be declared
private to allow only the class in which they appear to access
them. Accessor routines are automatically defined for reading object,
shared, and constant attributes and for writing object and shared
attributes. The set of non-private routines and iters in a class define
the interface of the corresponding type. Abstract types directly specify
their interfaces. Routine and iter definitions consist of statements and
these are constructed from expressions. There are special literal
expressions for boolean, character, string, integer, and floating point
objects.

@node Development Environment, Concrete Classes, Top, Top
@section Development Environment
@cindex Development Environment

This section illustrates

@itemize @bullet
@item
Using the compiler, module files.

@item
How to over-ride an erroneous library class.

@item
Debugging sather code.

@item
Pointers to Emacs mode, browser and compiler documentation.
@end itemize

The development environment consists of an incremental Sather-to-C
compiler (written in Sather), emacs and gdb support and a tcl-based code
browser.  A fair number of libraries are available, as well as
interfaces to other systems such as Tcl. A native compiler for a variant
of Sather 1.0, Sather-K is also available from Karlsruhe in Germany.
        
For a how-to introduction to writing your first program, please see
Philippsen's tutorial which is available with the sather distribution
and is also pointed to by:

@example
@strong{<A href="http://www.icsi.berkeley.edu/~gomes/Sather/sather-top.html">http://icsi.berkeley.edu/~gomes/Sather/sather-top.html</A>}
@end example

@noindent
in HTML form.

The compiler has been designed to permit the relatively easy development
of a Sather interpreter. The compiler spits out virtual machine
instructions which are translated into C; an interpreter for Sather must
provide an interpreter for this abstract machine language.  Resource
constraints have not permitted its development.  There is an unsupported
interpreter for a subset of the language which does things differently
(it does not make use of the abstract machine form); it is available in
the distribution. If you are interested in working on the interpreter
please contact sather-bugs or davids, both @@icsi.berkeley.edu

@menu
* The 1.0 Compiler::    Using the 1.0 compiler - pointers to documentation
* Module Files::        How to group compiler commands
* Debugging Sather::    The use of gdb with sather
* The Sather Emacs Mode:: Pointers to the emacs mode and it's documentation
* The Browser::         Pointers to browser documentation
@end menu

@node   The 1.0 Compiler, Module Files, Development Environment, Development Environment
@subsection The 1.0 Compiler
@cindex The 1.0 Compiler

The 1.0 compiler is available by anonymous ftp from
@code{ftp://icsi.berkeley.edu/pub/sather/}, as are binaries for various
platforms. The Sather-K compiler is also available from this site.  For
information about the platforms to which the compiler has been ported,
the FAQ etc., please see the main sather page:

@example
@strong{<A href="http://www.icsi.berkeley.edu/Sather">http://icsi.berkeley.edu/Sather</A>}
@end example

The compiler options are documented in a man page under the Doc
subdirectory of the distribution.  There is also a document that
describes the internal structure of the compiler available from

@example
@strong{<A href="http://www.icsi.berkeley.edu/Sather/ps/compiler.ps.gz">http://icsi.berkeley.edu/Sather/ps/compiler.ps.gz</A>}
@end example

@node Module Files, Debugging Sather, The 1.0 Compiler, Development Environment
@subsection Module Files
@cindex Module Files

The compiler options (documented in the man page for the compiler:
@code{man sacomp}) allow the user to specify a list of sather, C, "module"
files and other compiler flags.  Files of different types are
distinguished by their suffixes (@file{.sa}, @file{.c}, @file{.module},
etc.).  @strong{Module files are collections of compiler options which
behave exactly if they were typed in on the command line. Module files
have no futher semantic meaning}.  This permits the usage of a single
uniform, unix-like syntax whether specifying options on the command line
or in a module file.

Module files are used to partition and organize the Sather library.
Associated with each subdirectory of the Sather library is a module
file, which just lists the sather and C files in that directory, as well
as any modules contained within that directory.  For instance, the
System module lists the files in the system subdirectory and
@file{Socket.module}. @file{Socket.module}, in turn, lists the files in
the socket sub-directory. Note that path-names in a module file are
relative to the location of the module file.

The current convention is that all related files should be placed in a
single directory and provided with a module file. Using the code from
those classes should then just be a matter of mentioning it's module
file.  The Sather compiler automatically includes the top-most module of
the library, @file{Library.module}, which is found in the Library
subdirectory of the distribution.  This module in turn includes the rest
of the sather library.  If you do not wish to use the standard
Library.module, you will need to change the value of the environmental
variable @code{SATHER_LIBRARY} to point to a different module.

@example
setenv SATHER_LIBRARY "/u/gomes/Sather1/SatherCopy/Browser/mylibrary.module"
@end example

You can use this method to avoid loading the standard Sather libraries,
but don't forget to define the built-in classes (@code{INT},
@code{BOOL}, @code{MUTEX} etc.) or the compiler will complain.

@subsubsection Has clauses
@cindex Has clauses
In order to expedite parsing, the compiler permits the specification of
which classes are defined in each file.  For instance,

@example
my_math.sa -has my_math.sa MY_MATH_CLASS_FOO MY_MATH_CLASS_BAR 
@end example

@noindent
"has" clauses are not required by the compiler.

@subsubsection Comments
@cindex Comments
You can put comments in a module file by using the standard Sather
syntax "--". Module files also accept an extended comment syntax of the
form

@example
(*  my multi
 line 
comment
*) 
@end example

Since the module file is displayed by the browser, these comments can be
used to describe the nature of a particular module in the Library.

@subsubsection Module files with different suffixes
@cindex Module files with different suffixes

Module files which do not have the suffix @code{.module} must be
specified with the compiler option @code{-com <command file name>}. This
permits the use of the older style of @file{.com} files, which may still
be necessary on some systems with file name restrictions.


@subsubsection Over-riding library files
@cindex Over-riding library files

It is not particularly easy to over-ride just a single file in the
library.  The straightforward way to do it is to copy over the entire
library and modify the file. However, as a byproduct of the current
behaviour of the compiler (having to do with @code{-has} clauses), it
sometimes suffices to just copy the one file you want to fix and then
mention this amended file explicitly during your compile (without a -has
clause).  The compiler may find your version.  This is clearly a hacky
solution, but it often works and can save you some trouble.  If it does
work, it will work correctly (i.e. it will either choose your version or
complain that there were two definitions - it will never silently ignore
your explicitly specified version).

@node Debugging Sather, The Sather Emacs Mode, Module Files, Development Environment
@subsection Debugging Sather
@cindex Debugging Sather

You can basically use @code{gdb} for symbolic debugging.  David took a
great deal of trouble to make sure that the generated C names look as
much like the sather names as possible.  Classes turn into structs with
obvious feature mappings. You can usually use the "info" command
(eg. @code{info locals}) to get the actual names, and the mapping is
usually quite clear, since gdb under emacs will take you to the right
source location (if you compile with the @code{-debug} flag).

Furthermore, I find that programming in Sather is a very different
experience from programming in C. Far fewer bugs make it through the
compilation phase, and with checking turned on, those bugs are easily
detected - very often just void references, or array bounds checks which
you can locate by running @code{gdb} (even without the debug flag) and
looking at the stack trace at the point where the error occurs.  The
@code{gdb} command "where" will give you the stack trace.
       
I believe that @code{gdb} has a facility for name unmangling, given some
table, which C++ may use. If so, it might not be too much work to hook
into it. If you are interested in undertaking this task, please contact
@code{sather-bugs@@icsi.berkeley.edu}.  Since Sather stores type
information along with each object, there is the potential for a far
more sophisticated debugging environment/object browser than would be
possible with C++.

One more point to note: if, for some reason, you do have to debug the
generated C, do not turn on the debug flag. Instead, use: @code{-C_flag
-g}.
        

@node The Sather Emacs Mode, The Browser, Debugging Sather, Development Environment
@subsection The Sather Emacs Mode
@cindex The Sather Emacs Mode

There is an emacs editing mode available for Sather (started by Steve
Omohundro, but largely written and currently maintained by Kevin
K. Lewis, lewikk@@aud.alcatel.com), under the Emacs directory of the
distribution.  The @file{.elc} files are byte-compiled, faster versions
of the @file{.el} files. The documentation for the emacs mode is
available at the beginning of the file @file{sather.el}.  Effective use
of code highlighting requires you to set up some variables as described
in the beginning of @file{sather.el}.


@node The Browser, , The Sather Emacs Mode, Development Environment
@subsection The Browser
@cindex The Browser

Documentation for the sather browser (which is written in tcl and
distributed under the Browser subdirectory of the distribution) is
available at

@example
@strong{<A href="http://icsi.berkeley.edu/~gomes/Sather/bs.html">http://icsi.berkeley.edu/~gomes/Sather/bs.html</A>}
@end example

@noindent
This documentation includes recent bug-fixes and coming attractions.
        
@node Concrete Classes, Abstract Types, Development Environment, Top
@section Concrete Classes
@cindex Concrete Classes

This section illustrates

@itemize @bullet
@item
Declaring a concrete class

@item
Attributes with various degrees of privacy

@item
The (implicit) routines that implement attributes

@item
Creation routines and the @code{#} sugar for creation

@item
Type inference and @code{::=}
@end itemize

An example of a how a simple class @code{FOO} may be defined.
Attributes with varying degrees of privacy are illustrated, along with a
create routine that creates a new instance of this class.

@example
class @b{FOO} is
   -- A concrete class i.e. a class whose features are
   -- all implemented

   attr a: INT;
      -- This is implemented by the two implicit routines
      -- a: INT   [the public reader routine]
      -- a(new_value: INT)   [the public assignment routine]
      -- Since assignment is syntactic sugar for a call to a function of
      -- one variable
      --   foo.a := b is syntactic sugar for foo.a(b),

   private attr b: FLT;
      -- This is implemented by the two implicit routines
      -- private b: FLT   [the private reader routine]
      -- private a(new_value: FLT)   [the private assignment routine]

   readonly attr c: CHAR;
      -- This is implemented by the two implicit routines
      -- c: CHAR   [the public reader routine]
      -- private c(new_value: CHAR)   [the private assignmnet routine]

   readonly attr g: INT;

   create: SAME is
      -- Create routine, invoked by calling #FOO (# is syntactic
      -- sugar for create routines)
      -- SAME, the returned type, refers to the current class i.e. FOO
      res ::= @strong{new};  -- The @strong{::=} is used to combine 
                             -- the declaration of "res" with its assignment

      -- Set the attributes to various literal values.
      res.a := 5;
      res.b := 3.2;
      res.c := 'd';
      res.g := 42;
      res.e := "abcd";
      return(res);
   end;

   create(a_value: INT): SAME is
     -- Another create routine that takes an integer argument.
     -- We can overload routines, provided that they differ either in
     -- the number of arguments, presence or absence of return types
     -- or the concrete type of the arguments (i.e. we can't overload
     -- a routine that takes two abstract types)
     res ::= #;  -- This calls the create routine above. Recall that
                 -- the @strong{#} sign is syntactic sugar for the 
                 -- @strong{create}  routine.
                 -- Since we are in FOO, we don't have to specify the class
                 -- Otherwise, we would have to say #FOO
                 -- The @strong{::=} is used to combine the 
                -- declaration of "res" with its assignment
     res.a := a_value;  -- Set the a attribute to the correct value
     return(res);
   end;
end;

class TEST_FOO is
   
   main is
        p: FOO := #FOO;   -- Create an instance of foo
                          -- Equivalent to calling the first create routine
        q  ::= #FOO(3);   -- Another instance is created, using
                          -- the second create routine which takes the 
                          -- argument 3.
                          -- The type of the variable "q" is inferred from 
                          -- the rhs. The ::= is used to combine declaration
                          --  and assignment
        #OUT+p.a+"\n";    -- Will print out 5
        #OUT+q.a+"\n";    -- Will print out 3 (the value we set it to)
        #OUT+q.g+"\n";    -- Will print out 42
        -- #OUT+q.b+"\n"; ILLEGAL! the compiler will complain 
                          -- The attribute b is private

        q.a := 9.0;       -- Set the value of the attribute "a" in FOO
        --    q.g := 53;  ILLEGAL! q.g is readonly.  This
                          -- means that the writer routine for g is private.
      
   end;
end;
@end example

Each attribute declaration really traslates into two routines.

@example
  attr a: INT;
@end example

@noindent
is sugar for
@example
  a: INT;                   -- Used to get the value of a

  a(value: INT);            -- Used to set the value of "a"
@end example        

If access is restricted the underlying routines are typed accordingly.

@example
  private attr a: INT;
@end example

@noindent
is syntactic sugar for

@example
  private a: INT;          -- Used to get the value of a within FOO

  private a(value: INT);   -- Used to set the value of "a" within FOO
@end example

@noindent
And @dots{}

@example
  readonly attr a: INT;
@end example

@noindent
is syntactic sugar for

@example
  a: INT;                  -- Publicly used to get the value of a

  private a(value: INT);   -- Used to set the value of "a" within FOO
@end example

The @code{:=} sign is just syntactic sugar for the second function.  In
fact, you can call any routine with one argument using the @code{:=}
syntactic sugar, though it almost never makes sense except for attribute
access.

@node    Abstract Types, Value Classes, Concrete Classes, Top
@section Abstract Types
@cindex Abstract Types

This section illustrates

@itemize @bullet
@item
Definition of an abstract class

@item
A concrete class that subtypes and conforms to an abstract class

@item
Parametrized abstract types

@item
Type bounds on parameters

@item
Subtyping relations between different parametrizations
@end itemize        

@code{$MY_ABSTRACT_TYPE} illustrates an abstract type.  @code{FOO} and
@code{BAR} are subtypes. Below, we will illustrate how the abstract type
may be used.

@example
type @b{$MY_ABSTRACT_TYPE} is
   -- Definition of an abstract type.  Any concrete class that subtypes
   -- from this abstract class must provide the two routines
   -- ukridge and mulliner

    ukridge: INT;

    mulliner: CHAR;

end;

class @b{FOO} < $MY_ABSTRACT_TYPE is
    -- A concrete class, which supports the $MY_ABSTRACT_TYPE interface.
    -- It is said to subtype from $MY_ABSTRACT_TYPE

   attr ukridge: INT;
    -- This generates 
    -- ukridge: INT      [reader routine]
    -- ukridge(val: INT)  [assignment routine]
    -- It is the reader routine that implements the "ukridge"
    -- feature that that is required by $MY_ABSTRACT_TYPE

   private attr b: FLT;

   readonly attr mulliner: CHAR;

   create: SAME is
     -- Create routine, invoked by calling #FOO (# is syntactic
     -- sugar for the create routine)
     -- SAME, the returned type, refers to the current class i.e. FOO
      res ::= new;
      res.ukridge := 5;
      res.b := 3.2;
      res.mulliner := 'd';
      res.e := "abcd";
      return(res);
   end;

   create(ukridge_value: INT): SAME is
     -- We can overload routines, provided that they differ either in
     -- the number of arguments, presence or absence of return types
     -- or the concrete type of the arguments (i.e. we can't overload
     -- a routine that takes two abstract types)
     res ::= #;  -- This calls the create routine above. Recall that
                 -- the # sign is syntactic sugar for create.  The class is
                 -- assumed to be the current class. The type of res is inferred
     res.ukridge := ukridge_value; 
                 -- Set the "ukridge" attribute to the current class value
     return(res);
   end;

end;
@end example

@subsection Parametrized Abstract Types
@cindex Parametrized Abstract Types

All Sather classes may be parametrized by any number of type parameters.
Each type parameter may have an optional type bound; this forces any
actual parameter to be a subtype of the corresponding type bound.  Given
the following definitions,

@example
abstract class $A@{T < $BAR@} is
  foo(b:T): T;
end;

type $BAR is

end;

class BAR < $BAR is

end;
@end example

@noindent
we may then instantiate an abstract variable @code{a:$A@{BAR@}}.
@code{BAR} instantiates the parameter @code{T} and hence must be under
the type bound for @code{T}, namely @code{$BAR}.  If a type-bound is not
specified then a type bound of @code{$OB} is assumed.

@subsubsection Why have typebounds?
@cindex Why have typebounds?

The purpose of the type bound is to permit type checking of a
parametrized class @strong{over all possible instantiations}.  Note that
the current compiler does not do this, thus permitting some possibly
illegal code to go unchecked until an instantiation is attempted.

@subsubsection How are different parametrizations related?
@cindex How are different parametrizations related?

It is sometimes natural to want a @code{$LIST@{MY_FOO@} <
$LIST@{$MY_FOO@}}.  Sather, however, specifies no subtyping relationship
between various parametrizations.  The reason is contravariance.
Consider the case where the parameter type is used to specify an
argument type in a routine

@example
abstract $LIST@{T@} is
   append(element: T);
end;

abstract class $POLYNOMIAL is 

end;

abstract class $SQUARE < $POLYNOMIAL is

end;
a: $LIST@{$POLYNOMIAL@};
b: $LIST@{$SQUARE@};
@end example

We may wish to have @code{a < b}, so that we can pass a list of squares
to any routine that can deal with a list of polynomials.  However,
contravariance would not permit @code{$LIST@{$SQUARE@} <
$LIST@{$POLYNOMIAL@}}, since @code{append(element: $SQUARE)} cannot be
under @code{append(element: $POLYNOMIAL)} due to contravariance.

@node   Value Classes, Bound Routines, Abstract Types, Top
@section Value Classes
@cindex Value Classes

This section illustrates

@itemize @bullet
@item
What are value types?

@item
The benefits of value classes

@item
When might you use them?

@item
How to declare value classes. A simple version of @code{CPX}

@item
The strange value class attribute assignment syntax and why it must be
so.

@item
The create routine of a value class.

@item
Problems with void and value classes - the reason for nil.

@item
Getting equivalent behaviour from an "immutable" reference class.

@item
An immutable version of @code{CPX}.

@item
An immutable reference class, @code{STR}.

@item
It's more efficient cousin, @code{FSTR}.

@item
Aliasing problems with using @code{FSTR} (and many of the other ``F''
classes, which use amortized doubling).
@end itemize

Sather distinguishes between reference objects and value objects.
Experienced C programmers immediately catch the difference when told
about the internal representation: Value types are similar to C structs
and reference types are similar to pointers to struct's.  Because of
that difference, reference objects can be referred to from more than one
variable (aliased).  Value objects can not.  The basic types mentioned
(except arrays) are value classes. Reference objects must be explicitly
allocated with @code{new}. Variables have the value @code{void} until an
object is assigned to them. Void for reference objects is similar to a
void pointer in C. Void for value objects means that a predefined value
is assigned (@code{0} for @code{INT}, @code{`\0`} for @code{CHAR},
@code{false} for @code{BOOL}, and @code{0.0} for @code{FLT}).  Accessing
a void value object will always work. Accessing a void reference object
usually will be a fatal error.

At a more fundamental level: @strong{value classes define objects which,
once created, never change their value}.  A variable of a value type may
only be changed by re-assigning to that variable.  When we wish to only
modify some portion of a value class (one attribute, say), we are
compelled to @strong{reassign the whole object}. Hence, an attribute
@code{attr a: INT} of a value class has a setting routine called
@code{a(new_a_value: INT): SAME}, which returns a new value object in
which the attribute @code{a} has the value @code{new_a_value}.  This
contrasts with a reference class, in which the setting routine for a
similar attribute would have the signature @code{a(new_a_value: INT)}.
This aspect of value classes causes much confusion when one is first
introduced to Sather; a chief goal of this section is to help dispell
this confusion.

@menu
* Value Class Example::         A basic example, the @code{CPX} (complex number) class
* Value Class Usage::           Why would you want to use a value class
* Nil and void::                The difference between @code{nil} and @code{void} -
                                Extends the @code{CPX} example with an abstract
                                type (@code{$CPX}) and value (@code{VAL_CPX}) and reference
                                (@code{REF_CPX}) implementations.
* Immutable Reference Classes:: Defining reference classes with value semantics
* Value Class History::         A brief history of value classes.
@end menu

@node   Value Class Example, Value Class Usage, Value Classes, Value Classes
@subsection Value Class Example
@cindex Value Class Example

We illustrate the use of value classes through a commonly used example:
the complex class @code{CPX}.  The version shown here is a much
simplified version of the library class @code{CPX@{T@}}.  The key point
to note is the manner in which attributes values are set in the create
routine.
        
@cartouche
@example
value class @b{CPX}  is
   -- Complex numbers.

   readonly attr real,imag: FLT;
        -- Real and imaginary parts.
   
   create(re,im:FLT):SAME is 
      -- Create a new value type
      -- The following whole routine can be concisely written as:
      -- return(real(re).imag(im));  
      -- For the sake of clarity, we expand the steps involved
      res: SAME;         
         -- Declare a new CPX variable, 
         -- initialized with re, im = 0.0
      res := res.real(re);  
         -- The attribute setting routine for 
         -- real is real(FLT): SAME which takes an argument
         -- of type FLT and returns (conceptually) a new CPX number
         -- i.e. res now holds a new value.
      res := res.imag(im);   
         -- The new "res" has the correct value
         -- for the real part.  Now we set the imaginary part and re
         -- assign to res
       return(res);        
         -- Return the result
    end;
   
   is_eq(c: SAME): BOOL is 
      -- Return true if this object is equal to "c"
      return (real=c.real and imag=c.imag)
   end;

   plus(c:SAME):SAME is
      -- The sum of self and `c'.
      -- res is a new CPX object 
      -- # is syntactic sugar for the create routine shown above
      -- We create a new complex number whose real part is the sum
      -- of self' real part and c's real part and likewise with the
      -- imaginary part
      res ::= #(real+c.real,imag+c.imag); 
      -- We could also write res: CPX := #CPX(real+c.real+imag+c.imag);
      -- However, # refers to the create in this context i.e. CPX::create
      -- The return value of create is a CPX, therefore the type of res is
      -- also CPX. Type inference magic!
      return(res);
    end;

   str:STR is
      -- A string representation of self of the form "1.02+3.23i".
      buf:STR;
      if imag >= 0.0 then 
         buf:= real.str + ("+") + imag.str + "i";
      else buf:= real.str + ("-") + (-imag).str + "i" end;
      return buf 
    end;

end;
@end example
@end cartouche

The complex class may then be used in the following manner.

@example
        b: CPX := #(2.0,3.0);
        d: CPX := #(4.0,5.0);
        c: CPX := b+d;
@end example

The key point to note is the assignment of the attributes of the value
class. The attribute @code{imag} can be viewed as syntactic sugar for
the two routines

@example
        imag(new_imag_value: FLT): SAME
                -- Setting attribute routine
        image: FLT
                -- Getting attribute routine
@end example

The reason that the setting routine returns @code{SAME} is that we
cannot really modify a value object.  Rather, changing an attribute
generates a new value; the setting routine, @code{imag(FLT):SAME},
returns this new value.

If @code{CPX} were a regular reference class, the attribute access
routines would be

@example
        imag(new_imag_value: FLT);
                -- Setting attribute routine
        image: FLT
                -- Getting attribute routine
@end example

For a more elaborate example, please consult the section on @code{nil}
and @code{void} (@pxref{Nil and void}).

@node   Value Class Usage, Nil and void, Value Class Example, Value Classes
@subsection Value Class Usage
@cindex Value Class Usage

Value classes have several advantages.  One virtue is their immutable
semantics, which makes aliasing bugs impossible.  You can also get the
same effect by creating an immutable reference class (for example, look
at the @code{STR} class) in which every modification makes a new
copy. Value classes have no heap management overhead, they don't use
space to store a tag, and the absence of aliasing makes more C compiler
optimizations possible.  Furthermore, since value objects are stored on
the stack, they do not need to be garbage collected. For a small class
like @code{CPX}, all these factors combine to give a significant win
over a reference class implementation.  Balanced against these positive
factors in using a value class is the overhead that some C compilers
introduce in passing the entire object on the stack.  This problem is
worse in value classes with many attributes.

Unfortunately the efficiency of a value class appears directly tied to
how smart the C compiler is; ``gcc'' is not very bright in this respect.

@subsubsection My rules of thumb for creating value classes
@cindex My rules of thumb for creating value classes

@itemize @bullet
@item
You want the class to have value semantics. You could still consider an
immutable reference class (@pxref{Immutable Reference Classes}).

@item 
The class is small - I don't know what the speed trade-offs actually
are, but value classes have so far been used when there are only a
handful of attributes.

@item
There are going to be a large number of objects of that class.  This
goes along with the previous point. For instance, if you are going to
have large arrays of complex numbers, then the space that would be
required for an object pointer and an object tag may be considerable.
@end itemize

@node Nil and void, Immutable Reference Classes, Value Class Usage, Value Classes
@subsection Nil and void
@cindex Nil and void

One complexity in using value classes is the meaning of @code{void},
which is usually used to indicate a non-existent object.  @code{void} is
perfectly clear in the case of reference objects, where it is
implemented by the @code{NULL} pointer.  However, a value object exists
as soon as it is declared (initialized to all zero values), and is never
non-existent. Sather's solution is to say that a value object is
@code{void} if it has this initial, all zero value.  This introduces its
own problems, since we may well want to use the all-zero value as a
legitimate value (for instance, we frequently want to make use of
@code{INT}s and @code{FLT}s with values of zero!).

To illustrate this discussion, we start with a simple example. The same
class @code{CPX} used above is re-implemented, this time with an
abstract type @code{$CPX}, below which are a reference implementation
@code{REF_CPX} and a value implementation @code{VAL_CPX}.

@example 
        type @b{$CPX} is
           -- For the purposes of illustration, we have an abstract
           -- class that might be implemented as either a value or 
           -- reference class
           real: FLT;
           imag: FLT;
           plus(arg: $CPX): $CPX;
        end;

        class @b{REF_CPX} < $CPX is
          readonly attr real: FLT;  -- Make the reader publicly available
          readonly attr imag: FLT;

          create(r,i: FLT): SAME is
            res ::= new;
            res.real := r; 
            res.imag := i;      
            return(res);
          end;

          plus(arg: $CPX): REF_CPX is
            -- By the @strong{contravariant rule}:
            -- The argument(s) of plus must either be of @strong{same type}
            -- as $CPX or some @strong{supertype} of $CPX. 
            -- Using a supertype is very rarely useful.
            -- The return value can be either of type $CPX or some 
            -- @strong{subtype} of $CPX.
            new_real: FLT := real+arg.real;
            new_imag: FLT := imag+arg.imag;
            res: REF_CPX := #REF_CPX(new_real,new_imag);
            return(res);
          end;
        end;

        value class @b{VAL_CPX} < $CPX is
             -- Same as the CPX class mentioned previously 
          readonly attr real,imag: FLT;

          create(re,im:FLT):SAME is 
              -- More concise version of earlier create
             return(real(re).imag(im));
          end;
   
          plus(c:$CPX): VAL_CPX is
             res: VAL_CPX := #(real+c.real,imag+c.imag); 
             return(res);
          end;
        end;
@end example

As you can see, there are only subtle differences
in the way the value and the reference classes are created.
However, what if we want to perform the void test on the
variables below?

@example        
        a: VAL_CPX;
        b: REF_CPX;
        #OUT+void(a);    -- "true"
        #OUT+void(b);    -- "true"
@end example

We would like both calls to generate void, since neither variable has
been properly initialized, and Sather's definition of void achieves
exactly this.  However, problematic situations can arise, since there
will doubtless be occassions when you want to use a zero valued complex
number!

@example
        a: VAL_CPX := #VAL_CPX(0.0,0.0);
        b: REF_CPX := #REF_CPX(0.0,0.0);
        #OUT+void(a);   -- Returns "true"!
        #OUT+void(b);   -- Returns "false"
@end example

@noindent
will generate @code{void} for the @code{a} and non-@code{void} for the
call @code{b}, because @code{a} happened to be set to our void value!
The reference class has no such confusion.

@subsubsection The birth of nil
@cindex The birth of nil

To get around this problem, we can provide a user-defined @code{nil}
value for the value class - @code{nil} will be an unused value which
will signify a non-existent value object.  In the case of the @code{FLT}
class, a good @code{nil} value is ``NaN''.

@example
        value class @b{VAL_CPX} < $NIL@{VAL_CPX@}, $CPX is

           is_nil: BOOL is
                -- A complex number is nil if both real
                -- and imaginary parts are nil
               return(imag.is_nil and real.is_nil);
           end;

           nil: VAL_CPX is
             -- Return the "nil" value, which consists of 
             -- a complex number with two nil FLT components
             return(#(FLT::nil,FLT::nil))
           end;
        end;
@end example

In this case, we make use of @code{nil} @code{FLT} values to signify a
@code{nil} complex number.  The @code{FLT} class itself uses ``NaN''
(not a number) to signify a nil value.  We subtype from the class
@code{$NIL} to indicate that @code{VAL_CPX} provides the two routines
@code{is_nil} and @code{nil}.

@example
     type @b{IS_NIL} is
        is_nil: BOOL; -- Return true if this object is nil
     end;
     type @b{$NIL@{T@}} < $IS_NIL is
        nil: T;    -- The actual nil value
     end;
@end example

Hence, when checking to see whether an object is non-existent we can now
do the following:

@example
         object_does_not_exist(a: $CPX): BOOL is
            -- Returns true if "a" is a non-existent object.
           typecase a
           when $IS_NIL then return(a.is_nil);
                -- When a is a subtype of $IS_NIL
           else return(void(a)) end;
        end;
@end example

This is a fairly standard idiom; you will find code similar to this,
particularly in parametrized classes such as @code{FMAP} etc, where the
@code{nil} value is used to indicate empty spots in the hash table.

@example
        a: VAL_CPX := VAL_CPX::nil;
        b: REF_CPX;
        #OUT+object_does_not_exist(a);   -- Returns "true"
        #OUT+object_does_not_exist(b);   -- Returns "true"
        
        c: VAL_CPX := #VAL_CPX(0.0,0.0);
        d: REF_CPX := #REF_CPX(0.0,0.0);
        #OUT+object_does_not_exist(c);   -- Returns "false"
        #OUT+object_does_not_exist(d);   -- Returns "false"
@end example

We now need to always initialize value classes when we declare them to
the nil value (it would be nice if the language did this automatically,
but this introduces other complications).  This solution suffers from
another problem; for some classes such as @code{INT}, there is no single
value that can be set aside to signal @code{nil}, since we would then
not be able to use that value.

Please note that the @code{IS_NIL} class does not yet exist, but will
shortly.

@node  Immutable Reference Classes, Value Class History, Nil and void, Value Classes
@subsection Immutable Reference Classes
@cindex Immutable Reference Classes

It is possible to get the same semantics as a value class by defining an
@emph{immutable} reference class.  Immutable reference objects return a
copy of the object whenever an operation might modify the object.  An
immutable class is not a Sather construct. Rather, it is a property of a
reference class interface.

@menu
* Immutable CPX::       Mutable and immutable REF_CPX.
* STR and FSTR::        An immutable reference class and its efficient cousin.
* Using FSTR::          A couple of simple rules that will prevent all
                        aliasing bugs when using FSTR.
@end menu


@node Immutable CPX, STR and FSTR, Immutable Reference Classes, Immutable Reference Classes
@subsubsection Immutable CPX
@cindex Immutable CPX

Value semantics can be achieved for reference classes my making them
immutable. All operations that might be most naturally defined to modify
the original object, instead return a new object with the appropriate
modification.

We can imagine defining a ``square'' operation in @code{REF_CPX} as follows:

@example
        square is
            r ::= real*real-imag*imag;
            i ::= 2*real*imag;
            real := r;
            imag := i;
          end;
@end example

However, our complex numbers would then behave unexpectedly.

@example
       a: REF_CPX := #REF_CPX(3.0,4.0);
       c: REF_CPX := a;                -- c is (3.0,4.0)
       a.square;                       -- c's value has also changed to (-7,24)
@end example

The resulting value of @code{a} is as we expect (-7.0,24.0).  The value
of @code{c}, however, has changed to be (-7.0,24.0).  The reason, of
course, is that @code{c} points to the @code{a} object.

The @code{REF_CPX} class we defined above was immutable. Square would
return a copy of the class instead of modifying the original.

@example
        square: REF_CPX is
            r := real*real-imag*imag;
            i := 2*real*imag;
            return(#REF_CPX(r,i));
        end;

@end example

@example
       a: REF_CPX := #REF_CPX(3.0,4.0);
       c: REF_CPX := a;                 -- c is (3.0,4.0)
       a := a.square;                   -- c's value is still (3.0,4.0);
@end example

@node STR and FSTR, Using FSTR, Immutable CPX, Immutable Reference Classes
@subsubsection STR and FSTR
@cindex STR and FSTR

The class STR is an example of such an immutable reference class in the
library - a reference class with value semantics.  We generally expect
value semantics for strings i.e.

@example
        a: STR := "Beetle ";
        b: STR := a;
        a := a+"dung";
@end example

At the end of this example, we would like a to hold "Beetle dung" and b
to hold "Beetle". However, were STR a reference class with aliasing, b
might well be modified along with a.  There are two possible solutions.
The obvious one is to make STR a value class. However, strings can be
extremely large (in the complier, whole files are held in strings), and
should definitely not be passed on the stack, which is the current
implementation.  The other choice is to make an immutable reference
class, where every modification generates a copy.  However, this copying
is inefficient.  So we have two types of strings.  The basic class STR,
which is an immutable reference class and the type of the string
literal.  We also have the more efficient class FSTR, which is
@emph{not} immutable.  Using FSTR can therefore result in aliasing bugs.

To explain this futher we consider the plus operation in FSTR and in STR
(this version is simplified to explain the point. The library version is
more general and efficient).

@example
        
@dots{} From @strong{STR}

    plus(s: STR):SAME is
        -- A new string obtained by appending `s' to self.
        -- This routine is actually from  STR::append(STR) in the library.

        -- If either self or sarg is void, return the other
        if void(self) then return s; end;
        if void(s) then return self; end;
        selfsize::=asize;            -- Determine the size of self 
        ssize::=s.asize;             -- and sarg strings
        r::=new(selfsize+ssize);     -- Allocate a @strong{new} string for result
        r.acopy(self);               -- Copy self 
        r.acopy(selfsize,s);         -- and the argument into the new string
        return r;                    -- return the new string
    end;

        
@dots{} From @strong{FSTR}

    plus(s:SAME):SAME is
    -- Append the string `s' to self and return it. 
        -- r will hold the result
        r:SAME;
        l ::= s.length;
        -- If the argument would fit into our left over space,
        -- then let the result be @strong{self}
        if (loc + l < asize) then
            @strong{r:=self;}
        else
        -- Otherwise, make the result be a new string
        -- that is twice the (length of self+length of argument)
        -- (this is the technique of @strong{amortized doubling} which
        -- reduces the total number of allocations necessary 
        -- to incrementally build up an object to a particular
        -- size)
            @strong{r :=new(2*(asize+l));}
            -- Set the end pointer of the string
            -- Then copy 
            if (~void(self)) then
              -- If self is not void, copy it into the new string
              r.loc := loc;
              r.acopy(self);      
               -- Mark the old string as @strong{destroyed}.
               -- This helps prevent aliasing bugs - if someone
               -- tries to access the old string and destroy
               -- checking is on, then an error will occur.
               -- We do this because we still would like to 
               -- avoid aliasing behaviour for strings.
              SYS::destroy(self);   -- The old one should never be used now.
            end;
        end;
        -- "r" now holds the original string 
        --  and space enough to copy the argument into it.
        -- If the argumnet string has a size of 0, just return return
        -- current result
        if (l = 0) then return r; end;
        -- Set the new location
        r.loc := r.loc + l;
        -- Copy the argument into the result
        r.acopy(r.loc-l,s);
        return r;
    end;

@end example

Both STRs and FSTRs are meant to behave in roughly the same manner, but
FSTRs can exhibit aliasing bugs as shown below.

@example
        a: STR := #STR;         -- A new string
        a := a+"Beetle";        -- Append the string "Beetle" to a
        b: STR := a;            -- "b" now points to "a"
        c: STR := a+" Dung";
        #OUT+c;                 -- Outputs "Beetle Dung"
        #OUT+b;                 -- Outputs "Beetle"  
                                -- "b" has not been modified by aliasing
                                -- because the append operation returned 
                                -- a @strong{new} string.

        -- To avoid seeing the effect of amortized doubling, we
        -- first create a large amount of space for "a"
        a: FSTR := #FSTR;     -- Create an empty FSTR, which starts out with 
                              -- space for 16 chars
        a := a+"Beetle";      
        b: FSTR := a;         
        c: FSTR := a+" Dung";
        #OUT+c;               -- Outputs "Beetle Dung"
        #OUT+b;               -- Outputs "Beetle Dung"  
                              -- "b" has been modified
                              -- because the append operation modified the
                              -- the @strong{original} string.
        
@end example

@subsubsection Amortized Doubling further complicates matters
@cindex Amortized Doubling further complicates matters

The presence of such unexpected side effects can be even more tricky in
reality, since it is usually not obvious to the user when exactly a new
string will be allocated (due to the amortized doubling).  It is
possible for a program that works fine with "n" characters to break when
we add or delete a few characters.

@example
        a: FSTR := #FSTR("A test");     -- 6 chars
        a := a+" of";                   -- Amortized doubling kicks in
                                        -- "a" now has space for 18 characters
        b: FSTR := a;                   -- "b" is aliased to "a"
        a := a+"123456789012"           -- Add on another 12 characters - this 
                                        -- won't fit into "a"'s 18 chars and 
                                        -- so a new string will be 
                                        -- allocated and returned.
        #OUT+a;                         -- "A test of12345678901"
        #OUT+b;                         -- "A test of";   
                                        -- The original "b" is left unchanged.

@end example

However, if we change this program slightly, aliasing suddenly rears its
ugly head!

@example
        @dots{} First 3 lines are the same @dots{}
        a := a+"123456"                -- Add on another 6 characters - this 
                                       -- now fits into the space "a" has 
                                       -- left over.
                                       -- We just modify the @strong{original}
                                       -- string.
        #OUT+a;                        -- "A test of123456"
        #OUT+b;                        -- "A test of123456";  
                                        -- b is changed due to aliasing!
@end example

The @strong{destroy} check allows us to catch some of these problems.
If destroy checking is on, reading or modifying "b" should generate a
run-time error.

@node   Using FSTR, , STR and FSTR, Immutable Reference Classes
@subsubsection Using FSTR
@cindex Using FSTR

While the preceeding discussion may make FSTRs seem dangerous,
in practice a couple of simple rules will prevent any problems.

@itemize @bullet
@item        
Set only one variable to hold the FSTR and always reassign back to that
variable when a modification takes place.

@item
Avoid letting an FSTR be part of a class interface. If possible confine
FSTR usage to local variables.

@item
In general, only use FSTR when efficiency is an issue; this is usually
the case when building up a string in small bits, possibly from parsing
or user input.
@end itemize
        
        
@node   Value Class History, , Immutable Reference Classes, Value Classes
@subsection Value Class History
@cindex Value Class History

Value classes were initially proposed to generalize the notion of basic
types such as INT's and FLT's. They were particularly relevant to the
use of Sather on machines which had special arithmetic types (FLTs with
differing precisions etc.).  Later, however, the value semantics came to
be emphasized, they acquired attributes and were allowed to be under
abstract types.


@node Bound Routines, Problems and Bugs, Value Classes, Top
@section Bound Routines
@cindex Bound Routines

This section illustrates

@itemize @bullet
@item
What are bound routines?

@item
How to declare a simple bound routines.

@item
Binding various arguments to a bound routine.

@item
Leaving self unbound.

@item
Applications of bound routines - menu structures, applicative
programming, higher order functions.
@end itemize

Bound routines are Sather's equivalent of function pointers.  Like
everything else in Sather, they must be strongly typed. The type of a
bound routine most closely represents the type ofa parametrized class,
with the possible addition of a return type.

@menu
* Basic Bound Routine Example:: A very simple example of a bound routine.
* Binding Some Arguments::      An example that illustrates how some
                                arguments to a bound routine may be preset.
* Leaving Self Unbound::        Illustrates the case when the "self"
                                object is not preset.
* Bound Routine Usage::         When might you use bound routines?
                                Examples from applicative programming,
                                the "menu" paradigm and higher order
                                functions.
@end menu

@node Basic Bound Routine Example, Binding Some Arguments, Bound Routines, Bound Routines
@subsection A Simple Example
@cindex A Simple Example

In the following example, we define a bound routine that takes an INT as
an argument and returns an INT.

@example
class @b{BAR} is

  create: SAME is return(new) end;

  foo(a: INT): INT is
     return(a+5) 
  end;

end;

   main is
      a: BAR := #BAR;
      br: ROUT@{INT@}:INT := #ROUT(a.foo(_));
      result_of_calling_br: INT := br.call(9);
      #OUT+result_of_calling_br;
   end;

@end example

The variable "br" is typed as a bound routine which takes an integer as
argument and returns an integer. The routine foo, which is of the
appropriate type, is then assigned to "br".  The routine associated with
"br" may then be invoked by the built in function "call".  Just as we
would when calling the routine "foo", we must supply the integer
argument to the bound routine.

@example
        result_of_calling_br: INT := br.call(9)
@end example

@noindent
is equivalent to:

@example
        result_of_calling_br:INT := foo(9);
@end example

@noindent
which returns the value 14.

@node Binding Some Arguments, Leaving Self Unbound, Basic Bound Routine Example, Bound Routines
@subsection Binding some arguments
@cindex Binding some arguments

When a bound routine is created, it can preset some of the values of the
arguments.  For example:

@example
class @b{BAR} is

  create: SAME is return(new) end;
    -- A trivial create routine - just returns a new instance.

  foo(a: INT,b: INT): INT is
     return(a+b) 
  end;

end;

class TEST_BR is

   main is
        a: BAR := #BAR;  -- Call the create routine of BAR. 
        -- Using type inference, we could also write a ::= #BAR
        -- No preset arguments
        br1: ROUT@{INT,INT@}: INT := #ROUT(a.foo(_,_));
        br1_res: INT := br1.call(11,15);

        -- Preset the first argument of foo to 53
        br2: ROUT@{INT@}:INT := #ROUT(a.foo(53,_));
        br2_res: INT := br2.call(9);

        #OUT+br1_res+","+br2_res;
   end;
end;

@end example

In the example above, br2 binds the first argument of foo to 53 and the
second argument is left unbound.  This second argument will have to be
supplied by the caller of the bound routine.  br1 binds neither argument
and hence when it is called, it must supply both arguments. The result
of calling br1 should be 26 and the result of calling br2 should be 62.

@node Leaving Self Unbound, Bound Routine Usage, Binding Some Arguments, Bound Routines
@subsection Leaving self unbound 
@cindex Leaving self unbound 

Bound routines are often used to apply a function to arbitrary objects
of a particular class. For this usage, we need the "self" argument to be
unbound. In the following example we will make use of the "plus" routine
from the INT class.


@example
@dots{} from the INT class @dots{}
   plus(arg: INT): INT is 
      @dots{} definition of plus 
   end;
@dots{}

   main is
       -- Leaving self and the argument unbound
        plusbr1: ROUT@{INT,INT@}:INT := #ROUT(_:INT.plus(_));
        br1res: INT := plusbr1.call(9,10); -- 19

        -- Binding self, but leaving the argument unbound
        plusbr2: ROUT@{INT@}:INT := #ROUT(3.plus(_));
        br2res: INT := plusbr2.call(15);   -- 18

        -- Binding the argument but leaving self unbound
        plusbr3: ROUT@{INT@}:INT := #ROUT(_.plus(9));
        br3res: INT := plusbr3.call(11);   -- 20
        #OUT+br1res+","+br2res+","+br3res; -- 19,18,20
   end;

@end example

In the above example, plusbr1 leaves both self and the argument to plus
unbound.  Note that we must specify the type of self when creating the
bound routine, otherwise the compiler cannot know which class the
routine belongs to (the type could also be an abstract type that defines
that feature in its interface).  plusbr2 binds self to 3, so that the
only argument that need be supplied at call time is the argument to the
plus.  plusbr3 binds the argument to plus to 15, so that the only
argument that need be supplied at call time is self for the routine.

@node Bound Routine Usage, , Leaving Self Unbound, Bound Routines
@subsection Bound Routine Usage
@cindex Bound Routine Usage

Just as is the case in C, there will be programmers who find bound
routines indispensible and others who will hardly ever touch them.
Since Sather's bound routines are strongly typed, much of the insecurity
associated with function pointers (that I felt when using C, at least!)
disappears.

@menu 
* Applicative Bound Routines::  The use of bound routines in 
                                the applicative style
* Menu Structures::             A menu-like control structure, useful in user
                                interfaces and elsewhere.
* Higher Order Functions::      Bound routines may be composed to form
                                higher order bound routines
@end menu

@node Applicative Bound Routines, Menu Structures, Bound Routine Usage, Bound Routine Usage
@subsubsection Applicative Bound Routines
@cindex Applicative Bound Routines

They are generally useful when you want to write "apply" like routines
in a container class, which will work on a collection of data items.  A
good set of useful bound routines may be found in the ARRAY@{T@} class,
some examples of which are shown below.  As usual, the "elt!" iter
returns consecutive elements of the container.

@example
from @b{ARRAY@{T@}} @dots{}
     some(test:ROUT@{T@}:BOOL):BOOL is
        -- True if some element of self satisfies `test'. 
        -- Self may be void.
        loop if test.call(elt!) then return true end end;
        return false 
      end;

    every(test:ROUT@{T@}:BOOL):BOOL is
        -- True if every element of self satisfies `test'.
        -- Self may be void.
        loop if ~test.call(elt!) then return false end end; 
        return true 
    end;

These routines may be used thus:

     class MAIN is

        main is
          a ::= #ARRAY(|0.0,1.0,3.0,5.0|);
          br ::= #ROUT(gt_four);
          #OUT+a.every(br);  -- Returns false, all elements are not
                -- greater than four
          #OUT+a.some(br);  -- Returns true, one element is > 4.0
        end;

        gt_four(arg: FLT): BOOL  is return(arg > 4.0) end;
          -- Return true if the argument is greater than four
@end example

@node Menu Structures, Higher Order Functions, Applicative Bound Routines, Bound Routine Usage
@subsubsection Menu Structures
@cindex Menu Structures

Another, common use of function pointers is in the construction of a set
of choices.  They may be used to, for instance, create a MENU class
which associates various menu entries with bound routines.  (This
corresponds to the COMMAND pattern from the gang-of-four text called
@emph{Design Patterns}).

@example
class @b{MENU} is
   
   private attr menu_choices: FMAP@{STR,ROUT@};
      -- Hash table mapping from strings to bound routines
   create: SAME is return(new) end;
   
   add_menu_item(name: STR, function: ROUT) is 
      -- Add a menu item to the hash table, indexed by it's name
      menu_choices := menu_choices.insert(name,function);
   end;

   private user_selects(m: STR) is
      -- Perform an action when the user selects a particular menu item
      -- Look up the bound routine in the hash table, and call it.
      routine: ROUT := menu_choices.get(m);
      routine.call;
   end;
   
   run is
      -- In a loop, get user input, if it is not the word "done"
      -- then call the user_selects routine.
      loop
         #OUT+">";
         val ::= IN::get_line.str;
         if (val = "done") then
            break!
         else user_selects(val); end;
      end;
   end;

end;

class @b{MAIN} is
   
   main is
      m: MENU := #MENU;
      m.add_menu_item("hello",#ROUT(print_hello));
      m.add_menu_item("why",#ROUT(print_why));
      m.run;
   end;
   
   print_hello is  #OUT+"Hello there yourself!\n" end;
   
   print_why is #OUT+"My existance is a cosmic mystery\n" end;
   
end;

This generates the following session:
ttyp0 icsib78:~/tmp>a.out
>hello
Hello there yourself!
>why
My existance is a cosmic mystery
>hello
Hello there yourself!
>done
ttyp0 icsib78:~/tmp>
@end example

A very similar usage may be found in the GET_OPT class which may be
found Contrib/gomes/get_opt.sa of the sather distribution. GET_OPT is
capable of parsing a set of command line options in the standard unix
form -<keyword1> text -<keyword2> text2.  The class associates a bound
routine with each keyword, and calls that bound routine with "text" as
its argument.  If the bound routine expects an argument of a different
type (one of INT, FLT or BOOL), it tries to convert the string to a
value of the appropriate type.

@node Higher Order Functions, , Menu Structures, Bound Routine Usage
@subsubsection Higher Order Functions
@cindex Higher Order Functions

Bound routines may also be composed to form higher order functions.  Our
example takes two bound routine predicates (bound routines that return a
boolean value) as arguments and returns another bound routine which is
the result of ORing the results of the two predicates.

@example
class @b{MY_TEST} is
    -- Include the class definition just for clarity

   make_or(bp1: ROUT@{INT@}:BOOL, bp2: ROUT@{INT@}:BOOL): ROUT@{INT@}:BOOL is
      -- bp1 and bp2 are bound routine predicates that take ints as 
      -- arguments and return bools
      res: ROUT@{INT@}: BOOL;
      res := #ROUT(stub_for_or(_,bp1,bp2));
   end;

   stub_for_or(arg: INT, bp1,bp2: ROUT@{INT@}:BOOL): BOOL is
      bp1_res: BOOL := bp1.call(arg);
      bp2_res: BOOL := bp2.call(arg);
      return(bp1_res.or(bp2_res));
   end;
        
-- A higher order function may then be developed as follows.
-- Suppose we have the two predicates,
   gt_four(a: INT): BOOL is return(a > 4) end;

   lt_two(a: INT): BOOL is return(a < 2) end;

-- which have been assigned to bound routines
   main is
      bp1: ROUT@{INT@}:BOOL := #ROUT(gt_four(_));
      bp2: ROUT@{INT@}:BOOL := #ROUT(lt_two(_));
      or_bp: ROUT@{INT@}:BOOL := make_or(bp1,bp2));
      #OUT+bp1.call(5);  -- Output is "true"
      #OUT+bp2.call(3);  -- "false"
      #OUT+or_bp(1);     -- "true"
      #OUT+or_bp(5);     --  "true"
      #OUT+or_bp(3);     --  "false"
      -- The predicates may also be directly defined using the INT class
      -- bp1: ROUT@{INT@}: BOOL :=  #ROUT(_:INT.gt(4));
      -- bp2: ROUT@{INT@}: BOOL :=  #ROUT(_:INT.lt(2));
   end;
   
end;
      
@end example

Using bound routines, we have created a test for whether a number is
either greater than 4 or less than two.

@node   Problems and Bugs, Concept Index, Bound Routines, Top
@section Problems and Bugs
@cindex Problems and Bugs

This section is about some common problems and bugs.  This is from
Doc/Bugs of the distribution, with some added comments.

Send comments to "sather-bugs@@icsi.berkeley.edu".

Major functionality omissions:

@itemize @bullet
@item
Bound iters and dispatching over iters aren't implemented.  Bound iters
will probably never be implemented and have been taken out of the 1.1
spec. Dispatched iters might be available as early as 1.0.7

@item
The supertype operator ">" may be broken.  Use "<" instead.

@item
There is a problem passing Sather arrays to external classes that have
been put in bound routines.
@end itemize

Bugs of libraries and library support:

@itemize @bullet
@item
FLTX and FLTDX aren't implemented; it's difficult when most C compilers
don't support them, either.

@item
IEEE "-0.0" literals become positive, because RATs are used internally
to represent the mantissas and those don't have signed zero.  You can
get the correct effect with 0.0.negate.

@item
Built-in INT operations such as "plus" don't work when you change asize
in a descendent.  AVAL@{BOOL@} and AREF@{BOOL@} use bytes insteadof bits
for storage except in built-in classes.
@end itemize

Bugs affecting checking:
@itemize @bullet
@item
IEEE exception handling isn't implemented.

@item
Static checks on classes with type bounds are not performed.  This never
affects the correctness of compiled code, but means that for the moment
it is possible for a new instantiation of parameters to cause a type
problem that wasn't recognized until that instantiation.

@item
Programs with infinite numbers of classes, for instance

@example
        class BUG@{T@} is a:BUG@{SAME@} is end; end;
@end example

@noindent
aren't caught properly; the compiler infinite loops.  

@item
Cycles of value types where each type has an object attribute whose type
is the next in the cycle are also not caught.  So, don't write programs
like this.

@item
Stack overflows are reported as void accesses under some circumstances,
because they are just trapped seg faults.
@end itemize

Bugs affecting invocation/environment:

@itemize @bullet
@item
Symbolic info generated by -debug or -g may occasionally point to a C
file instead of Sather, but these should be ignored (it only happens if
there isn't an appropriate Sather line that corresponds to the C
statements, such as during automatic boxing of dispatched value types).
@end itemize

Known pSather bugs:

@itemize @bullet
@item
Threads waiting for locks cannot be cleared.
@end itemize

@node Concept Index, , Problems and Bugs, Top
@unnumbered Concept Index
@printindex cp
@summarycontents

@contents
@bye
