<?xml version="1.0" encoding="UTF-8"?>

<!-- ====================================================================== -->
<!-- = chapter-2.xml                                                      = -->
<!-- = afnix programmer's guide chapter 2                                 = -->
<!-- ====================================================================== -->
<!-- = This  program  is  free  software; you  can redistribute it and/or = -->
<!-- = modify it provided that this copyright notice is kept intact.      = -->
<!-- = 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. In no event = -->
<!-- = shall  the  copyright  holder be liable for any  direct, indirect, = -->
<!-- = incidental  or special  damages arising  in any way out of the use = -->
<!-- = of this software.                                                  = -->
<!-- ====================================================================== -->
<!-- = copyright (c) 2005-2007 - amaury darsch                            = -->
<!-- ====================================================================== -->

<chapter volume="1" number="2">
  <title>Numbers and strings</title>

  <p>
  This chapters covers in detail the builtin objects used to manipulate
  numbers and strings. First the integer, relatif and real numbers are
  described. <afnix/> offers a broad range of methods for these
  three objects to support numerical computation. As a second step,
  string and character objects are described. Many examples show the
  various operations which can be used as automatic conversion between
  one type and another. Finally, the boolean object is
  described. These objects belongs to the class of <em>literal
  objects</em>, that is objects that have a string representation.
  </p>

  <!-- integer number -->
  <section>
    <title>Integer number</title>

    <p>
    The fundamental number representation is the
    <code>Integer</code>. The integer is a 64 bits signed 2's
    complement number. Even when running with a 32 bits machine, the
    64 bits representation is used. If a larger representation is
    needed, the <code>Relatif</code> object might be more appropriate.
    </p>

    <!-- integer format -->
    <subsect>
      <title>Integer format</title>
      
      <p>
      The default literal format for an integer is the decimal
      notation. The minus sign (without blank) indicates a negative
      number. Hexadecimal and binary notations can also be used with
      prefix <code>0x</code> and <code>0b</code>. The underscore
      character can be used to make the notation more readable.
      </p>

      <example>
      const a  123
      trans b -255
      const h  0xff
      const b  0b1111_1111
      </example>

      <p>
      Integer number are constructed from the literal notation or by
      using an explicit integer instance. The <code>Integer</code>
      class offers standard constructors. The default constructor
      creates an integer object and initialize it to 0. The other
      constructors take either an integer, a real number, a character
      or a string.
      </p>

      <example>
      const a (Integer)
      const b (Integer 2000)
      const c (Integer "23")
      </example>

      <p>
      When the hexadecimal or binary notation is used, care should be
      taken to avoid a negative integer. For example,
      <code>0x_8000_0000_0000_0000</code> is the smallest negative 
      number.
      </p>
    </subsect>

    <!-- integer arithmetic -->
    <subsect>
      <title>Integer arithmetic</title>

      <p>
      Standard arithmetic operators are available as builtin
      operators. The usual addition <code>+</code>, multiplication
      <code>*</code> and division <code>/</code> operate with two
      arguments. The subtraction <code>-</code> operates with one or
      two arguments.
      </p>
      
      <example>
      + 3 4
      - 3 4
      - 3
      * 3 4
      / 4 2
      </example>

      <p>
      As a builtin object, the <code>Integer</code> object offers
      various methods for builtin arithmetic which directly operates
      on the object. The following example illustrates these methods.
      </p>

      <example>
      trans i 0
      i:++
      i:--
      i:+ 4
      i:= 4
      i:- 1
      i:* 2
      i:/ 2
      i:+= 1
      i:-= 1
      i:*= 2
      i:/= 2
      </example>

      <p>
      As a side effect, these methods allows a const symbol to be
      modified. Since the methods operates on an object, they do not
      modify the state of the symbol. Such methods are called
      <em>mutable methods</em>. 
      </p>
      
      <example>
      const i 0
      i:= 1
      </example>
    </subsect>

    <!-- integer comparision -->
    <subsect>
      <title>Integer comparison</title>

      <p>
      The comparison operators works the same. The only difference is
      that they always return a <code>Boolean</code> result. The
      comparison operators are namely equal <code>==</code>, not equal
      <code>!=</code>, less than <code>&lt;</code>, less equal
      <code>&lt;=</code>, greater <code>&gt;</code> and greater
      equal <code>&gt;=</code>. These operators take two arguments.
      </p>

      <example>
      == 0 1
      != 0 1
      </example>

      <p>
      Like the arithmetic methods, the comparison operators are
      supported as object methods. These methods return a
      <code>Boolean</code> object.
      </p>

      <example>
      i:=  1
      i:== 1
      i:!= 0
      </example>
    </subsect>

    <!-- integer calculus -->
    <subsect>
      <title>Integer calculus</title>
      
      <p>
      Armed with all these functions, it is possible to develop a
      battery of functions operating with numbers. As another example,
      we revisit the Fibonacci sequence as demonstrated in the
      introduction chapter. Such example was terribly slow, because of
      the double recursion. Another method suggested by Springer and
      Friedman uses two functions to perform the same job.
      </p>

      <example>
      const fib-it (gamma (n acc1 acc2) (
        if (== n 1) acc2 (fib-it (- n 1) acc2 (+ acc1 acc2))))

      const fiboi (gamma (n) (
        if (== n 0) 0 (fib-it n 0 1)))
      </example>

      <p>
      This later example is by far much faster, since it uses only one
      recursion. Although, it is no the fastest way to write it, but
      nobody is going to question the elegant aspect of recursion.
      </p>
    </subsect>

    <!-- other integer methods -->
    <subsect>
      <title>Other Integer methods</title>
      
      <p>
      The <code>Integer</code> class offers other convenient
      methods. The <code>odd-p</code> and <code>even-p</code> are
      predicates. The <code>mod</code> take one argument and returns
      the modulo between the calling integer and the argument. The
      <code>to-string</code> method returns a string representation of
      the integer. The <code>abs</code> methods returns the absolute
      value of the calling integer.
      </p>

      <example>
      i:even-p
      i:odd-p
      i:mod 2
      i:= -1
      i:abs
      i:to-string
      </example>
    </subsect>
  </section>

  <!-- relatif number -->
  <section>
    <title>Relatif number</title>

    <p>
    A <em>relatif or big-num</em> is an integer with infinite
    precision. The <code>Relatif</code> class is similar to the
    <code>Integer</code> class except that it works with infinitely
    long number. The relatif notation uses a <code>r</code> or
    <code>R</code> suffix to express a relatif number versus an
    integer one.
    </p>

    <example>
    const a  123R
    trans b -255R
    const c  0xffR
    const d  0b1111_1111R
    const e (Relatif)
    const f (Relatif 2000)
    const g (Relatif "23")
    </example>

    <!-- relatif operations -->
    <subsect>
      <title>Relatif operations</title>

      <p>
      Most of the <code>Intege</code> class operations are supported
      by the <code>Relatif</code> object. The only difference is that
      there is no limitation on the number size. This naturally comes
      with a computational price. An amazing example is to compute the
      biggest know prime Mersenne number. The world record exponent is
      6972593. The number is therefore:
      </p>

      <example>
      const i 1R
      const m (- (i:shl 6972593) 1)
      </example>

      <p>
      This number has 2098960 digits. You can use the
      <code>println</code> method if you wish, but you have been
      warned... 
      </p>
    </subsect>
  </section>

  <!-- real numbers -->
  <section>
    <title>Real number</title>

    <p>
    The <code>real</code> class implements the representation for
    floating point number. The internal representation is machine
    dependent, and generally follows the double representation with 64
    bits as specified by the IEEE 754-1985 standard for binary
    floating point arithmetic. All integer operations are supported
    for real numbers.
    </p>

    <!-- real format -->
    <subsect>
      <title>Real format</title>
      
      <p>
      The <afnix/> reader supports two types of literal representation
      for real number. The first representation is the <em>dotted
      decimal</em> notation. The second notation is the <em>scientific
      notation</em>.
      </p>

      <example>
      const a  123.0 # a positive real
      const b -255.5 # a negative real
      const c  2.0e3 # year 2000.0
      </example>

      <p>
      Real number are constructed from the literal notation or by
      using an explicit real instance. The <code>Real</code> class
      offers standard constructors. The default constructor creates a
      real number object and initialize it to 0.0. The other
      constructors takes either an integer, a real number, a character
      or a string.
      </p>
    </subsect>

    <!-- real arithmetic -->
    <subsect>
      <title>Real arithmetic</title>

      <p>
      The real arithmetic is similar to the integer one. When an
      integer is added to a real number, that number is automatically
      converted to a real and vice versa. Ultimately, a pure integer
      operation might generate a real result.
      </p>

      <example>
      + 1999.0 1   # 2000.0  
      + 1999.0 1.0 # 2000.0
      - 2000.0 1   # 1999.0  
      - 2000.0 1.0 # 1999.0
      * 1000 2.0   # 2000.0  
      * 1000.0 2.0 # 2000.0
      / 2000.0 2   # 1000.0  
      / 2000.0 2.0 # 1000.0
      </example>

      <p>
      Like the <code>Integer</code> object, the <code>Real</code>
      object has arithmetic builtin methods.
      </p>

      <example>
      trans  r 0.0 # 0.0  
      r:++       # 1.0 
      r:--       # 0.0  
      r:+ 4.0    # 4.0  
      r:= 4.0    # 4.0  
      r:- 1.0    # 3.0  
      r:* 2.0    # 8.0  
      r:/ 2.0    # 2.0  
      r:+= 1.0   # 5.0  
      r:-= 1.0   # 4.0  
      r:*= 2.0   # 8.0  
      r:/= 2.0   # 4.0
      </example>
    </subsect>

    <!-- real comparison -->
    <subsect>
      <title>Real comparison</title>

      <p>
      The comparison operators works as the integer one. As for the
      other operators, an implicit conversion between an integer to a
      real is done automatically.
      </p>

      <example>
      == 2000 2000   # true
      != 2000 1999   # true
      </example>

      <p>
      Comparison methods are also available for the <code>Real</code>
      object. These methods take either an integer or a real as
      argument.
      </p>

      <example>
      r:=  1.0 # 1.0
      r:== 1.0 # true  
      r:!= 0.0 # true
      </example>
    </subsect>

    <!-- a complex example -->
    <subsect>
      <title>A complex example</title>

      <p>
      One of the most interesting point with functional programming
      language is the ability to create complex computation
      function. For example, let's assume we wish to compute the value
      at a point <code>x</code> of the <em>Legendre polynomial of order
      n</em>. One of the solution is to encode the function given its
      order. Another solution is to compute the function and then
      compute the value. 
      </p>

      <example>
      # legendre polynomial order 0 and 1
      const lp-0 (gamma (x) 1)
      const lp-1 (gamma (x) x)

      # legendre polynom of order n
      const lp-n (gamma (n) (
        if (&gt; n 1) {
          const lp-n-1 (lp-n (- n 1))
          const lp-n-2 (lp-n (- n 2))
	  gamma (x) (n lp-n-1 lp-n-2) 
            (/ (- (* (* (- (* 2 n) 1) x) 
              (lp-n-1 x))
              (* (- n 1) (lp-n-2 x))) n)
        } (if (== n 1) lp-1 lp-0)
      ))

      # generate order 2 polynom
      const lp-2 (lp-n 2)

      # print lp-2 (2)
      println "lp2 (2) = " (lp-2 2)
      </example>

      <p>
      Note that the computation can be done either with integer or
      real numbers. With integers, you might get some strange results
      anyway, but it will work.  Note also how the closed variable
      mechanism is used. The recursion capture  each level of the
      polynom until it is constructed. As an exercise, try to use  a
      lambda expression instead of a gamma one, and compare the
      execution result  with large number of <code>n</code>. Note also
      that we have here a double recursion. 
      </p>
    </subsect>

    <!-- other real methods -->
    <subsect>
      <title>Other real methods</title>

      <p>
      The real numbers are delivered with a battery of functions. These
      include the trigonometric functions, the logarithm and couple
      others. Hyperbolic functions like <code>sinh</code>,
      <code>cosh</code>, <code>tanh</code>, <code>asinh</code>,
      <code>acosh</code> and <code>atanh</code> are also
      supported. The square root <code>sqrt</code> method return the
      square root of the calling real. The <code>floor</code> and
      <code>ceiling</code> returns respectively the floor and the
      ceiling of the calling real.
      </p>

      <example>
      const r0 0.0       # 0.0
      const r1 1.0       # 1.0
      const r2 2.0       # 2.0
      const rn -2.0      # -2.0
      const rq (r2:sqrt) # 1.414213
      const pi 3.1415926 # 3.141592

      rq:floor           # 1.0
      rq:ceiling         # 2.0
      rn:abs             # 2.0
      r1:log             # 0.0
      r0:exp             # 1.0
      r0:sin             # 0.0
      r0:cos             # 1.0
      r0:tan             # 0.0
      r0:asin            # 0.0
      pi:floor           # 3.0
      pi:ceiling         # 4.0
      </example>
    </subsect>

    <!-- accuracy and formatting -->
    <subsect>
      <title>Accuracy and formatting</title>

      <p>
      Real numbers are not necessarily accurate, nor precise. The
      accuracy and precision are highly dependent on the hardware as
      well as the nature of the operation being performed. In any
      case, never assume that a real value is an exact one. Most of
      the time, a real comparison will fail, even if the numbers are
      very close together. When comparing real numbers, it is
      preferable to use the <code>?=</code> operator. Such operator
      result is bounded by the internal precision representation and
      will generally return the desired value. The real precision is
      an interpreter value which is set with the
      <code>set-epsilon</code> method while the 
      <code>get-epsilon</code> returns the interpreter
      precision. Note also that the <code>Real</code> object bind the
      data member <code>EPSILON</code>, which can be use with the
      qualified name <code>Real:EPSILON</code>. By default, the
      precision is set to 0.00001.
      </p>

      <example>
      interp:set-epsilon 0.0001
      const r 2.0
      const s (r:sqrt) # 1.4142135
      (s:?= 1.4142)    # true
      </example>

      <p>
      Real number formatting is another story. The <code>format</code>
      method takes a <em>precision argument</em> which indicates
      the number of digits to print for the decimal part. Note that
      the format command might round the result as indicated in the
      example below.
      </p>

      <example>
      const pi 3.1415926535
      pi:format 3  # 3.142
      </example>

      <p>
      If additional formatting is needed, the <code>String</code>
      <code>fill-left</code> and <code>fill-right</code> methods can
      be used.
      </p>

      <example>
      const pi  3.1415926535  # 3.1415926535
      const val (pi:format 4) # 3.1416
      (val:fill-left '0' 9)   # 0003.1416
      </example>
    </subsect>
  </section>

  <!-- character -->
  <section>
    <title>Character</title>

    <p>
    The <code>Character</code> object is another builtin object of the
    <afnix/> engine. A character is internally represented by a quad
    by using a 31 bit representation as specified by the Unicode
    standard and ISO 10646.
    </p>

    <!-- character format -->
    <subsect> 
      <title>Character format</title>

      <p>
      The standard quote notation is used to represent a character. In
      that respect, <afnix/> differs substantially from other
      functional language where the quote protect a form.
      </p>

      <example>
      const LA01 'a' # the character a
      const ND10 '0' # the digit 0
      </example>

      <p>
      All characters from the <em>Unicode codeset</em> are
      supported by the <afnix/> engine. The characters are constructed
      from the literal notation or by using an explicit character
      instance. The <code>Character</code> class offers standard
      constructors. The default constructor creates a null
      character. The other constructors take either an integer, a
      character or a string. The string can be either a single quoted
      character or the literal notation based on the <code>U+</code>
      notation in hexadecimal. For example, <code>U+40</code> is the
      <em>@</em> character while <code>U+3A3</code> is the greek sigma
      capital letter <em>&#x3A3;</em>.
      </p>

      <example>
      const nilc (Character)        # null character
      const a    (Character 'a')    # a
      const 0    (Character 48)     # 0
      const mul  (Character "*")    # *
      const div  (Character "U+40") # @
      </example>
    </subsect>

    <!-- character arithmetic -->
    <subsect>
      <title>Character arithmetic</title>

      <p>
      A character is like an integer, except that it operates in the
      range 0 to 0x7FFFFFFF. The character arithmetic is simpler
      compared to the integer one and no overflow or underflow
      checking is done. Note that the arithmetic operations take an
      integer as an argument.
      </p>

      <example>
      + 'a' 1 # 'b' 
      - '9' 1 # '8'
      </example>

      <p>
      Several <code>Character</code> object methods are also provided
      for arithmetic operations in a way similar to the
      <code>Integer</code> class.
      </p>

      <example>
      trans  c 'a' # 'a'
      c:++         # 'b'
      trans  c '9' # '9'  
      c:--         # '8'
      c:+ 1        # '9'
      c:- 9        # '0'
      </example>
    </subsect>

    <!-- character comparison -->
    <subsect>
      <title>Character comparison</title>

      <p>
      Comparison operators are also working with the
      <code>Character</code> object. The standard operators are namely
      equal <code>==</code>, not equal <code>!=</code>, less than
      <code>&lt;</code>, less equal <code>&lt;=</code>, greater
      <code>&gt;</code> and greater equal
      <code>&gt;=</code>. These operators take two arguments.
      </p>

      <example>
      == 'a' 'b' # false  
      != '0' '1' # true
      </example>
    </subsect>

    <!-- other character method -->
    <subsect>
      <title>Other character methods</title>

      <p>
      The <code>Character</code> object comes with additional 
      methods. These are mostly conversion methods and predicates. The
      <code>to-string</code> method returns a string representation of
      the calling character. The <code>to-integer</code> method returns
      an integer representation the calling character. The predicates
      are <code>alpha-p</code>, <code>digit-p</code>,
      <code>blank-p</code>, <code>eol-p</code>, <code>eof-p</code> and
      <code>nil-p</code>.
      </p>

      <example>
      const LA01 'a'  # 'a'
      const ND10 '0'  # '0'
      LA01:to-string  # "a"
      LA01:to-integer # 97
      LA01:alpha-p    # true
      ND10:digit-p    # true
      </example>
    </subsect>
  </section>

  <!-- string object -->
  <section>
    <title>String</title>

    <p>
    The <code>String</code> object is one of the most important
    builtin object in the <afnix/> engine. Internally, a string is a
    vector of <em>Unicode characters</em>. Because a string operates
    with Unicode characters, care should be taken when using
    composing characters.
    </p>

    <!-- string format -->
    <subsect>
      <title>String format</title>

      <p>
      The standard double quote notation is used to represent
      literally a string. Standard escape sequences are also accepted
      to construct a string.
      </p>

      <example>
      const hello "hello"
      </example>

      <p>
      Any literal object can be used to construct a string. This means
      that integer, real, boolean or character objects are all valid
      to construct strings. The  default constructor creates a null
      string. The string constructor can also takes a string.
      </p>

      <example>
      const nils (String)      # ""
      const one  (String 1)    # "1"
      const a    (String 'a')  # "a"
      const b    (String true) # "true"
      </example>
    </subsect>

    <!-- string operation -->
    <subsect>
      <title>String operations</title>

      <p>
      With strings, numerous methods can be provided. We illustrate
      here the most common one.
      </p>

      <example>
      const h "hello"
      h:length       # 5
      h:get 0        # 'h'
      h:== "world"   # false
      h:!= "world"   # true
      h:+= " world"  # "hello world"
      </example>

      <p>
      The <code>sub-left</code> and <code>sub-right</code> methods
      return a sub-string, given the position index. For
      <code>sub-left</code>, the index is the terminating index, while 
      <code>sub-right</code> is the starting index, counting from 0.
      </p>

      <example>
      const msg "hello world"
      msg:sub-left  5 # "hello"
      msg:sub-right 6 # "world"
      </example>

      <p>
      The <code>strip</code>, <code>strip-left</code> and
      <code>strip-right</code> are methods used to strip blanks and
      tabs. The <code>strip</code> method combines both
      <code>strip-left</code> and <code>strip-right</code>.
      
      The <code>split</code> method returns a vector of strings by
      splitting the string according to a break sequence. By default,
      the break sequence is the blank, tab and newline characters. The
      break sequence can be one or more characters passed as one
      single argument to the method.
      </p>

      <example>
      const str "hello:world"
      const vec str:split ":" # "hello" "world"
      println (vec:length) # 2
      </example>

      <p>
      The <code>fill-left</code> and <code>fill-right</code> methods
      can be used to fill a string with a character up to a certain
      length. If the string is longer than the length, nothing
      happens.
      </p>

      <example>
      const pi  3.1415926535  # 3.1415926535
      const val (pi:format 4) # 3.1416
      val:fill-left '0' 9     # 0003.1416
      </example>
    </subsect>

    <!-- string hash value -->
    <subsect>
      <title>String hash value</title>

      <p>
      Computing the hash value of a string is an interesting
      problem. The algorithm used by the <afnix/> engine is shown as an
      example below. Note that the <code>hashid</code> method is
      built in the <code>String</code> object. The program shows both
      internal and computed values.
      </p>

      <example>
      # compute string hashid
      const hashid (s) {
        const len (s:length)
        trans cnt 0
        trans val 0
        trans sht 17
        do {
          # compute the hash value
 	 trans i (Integer (s:get cnt))
 	 val:= (val:xor (i:shl sht))
 	 # adjust shift index
 	 if (&lt; (sht:-= 7) 0) (sht:+= 24)
        } (&lt; (cnt:++) len)
        eval val
      }
      </example>

      <p>
      When run, <em>example 0203.als</em>, the following result is
      obtained.
      </p>

      <example>
      # test our favorite string
      const hello "hello world"
      hello:hashid # 1054055120
      hashid hello # 1054055120
      </example>

      <p>
      As a side note, it is recommended to print the shift amount in
      the program. One may notice, that the value remains bounded by
      24. Since we are "xoring" the final value, it does illustrate that
      the algorithm is design for a 32 bits machine. It will work as
      well with a 64 bits machine (and give the same result), but the
      full integer range is not used.
      </p>
    </subsect>
  </section>
</chapter>
