Friday, December 5, 2014

Arrays and Indexers in Fantom



Today's post is about Arrays and Indexers in Fantom. Here below you will find a very easy to follow program, that demonstrate arrays and indexer, by implementing some simple tasks that will make you grasp the idea of those 2 features real quick. The main goal of this post, is not really teaching arrays because, come on, you probably already know "all" about them, in fact, it is more to show you how you do that in Fantom, in this case, compared to all other 22 languages on future posts, which essentially, is the real aim behind this blog.

By the way, if you missed my (not so) recent post (anymore), "New Series - Arrays and Indexers", check it out. It has more details about the following program, and a bunch of definitions for the concepts used on this, and the following, posts. Or you can check my previous posts about arrays in Java just to compare.

I encourage you to copy the code below and try it yourself, normally, all programs you find in this blog are source code complete, just paste it on your IDE and run it.

There is room for improvement of the code, using generics is one example, but Generics, Collections, lambdas, etc. will have their own "series" of posts.


using [java] fanx.interop::CharArray
using [java] fanx.interop::IntArray 

class FantomArrays
{
  static Void main()
  {
    // For char and int I'm using primitive arrays (CharArray and IntArray)
    // and for String arrays and Multi-dimensional arrays I'm using List (Type[])
    // reference: http://fantom.org/doc/docLang/JavaFFI
    // section Interop Summary and Arrays
    
    // Single-dimensional Array(s)
    printTitle("Reverse Array Elements")
    
    // Declare and Initialize Array of Chars
    letters := CharArray.make(5)
    letters[0] = 'A'
    letters[1] = 'E'
    letters[2] = 'I'
    letters[3] = 'O'
    letters[4] = 'U'

    printArrayChar(letters)
    CharArray inverse_letters := reverseChar(letters)
    printArrayChar(inverse_letters)
    
    printTitle("Sort Integer Array Elements")
    
    // Declare and Initialize Array of Integers
    numbers := IntArray(5)
    numbers[0] = 10
    numbers[1] = 8
    numbers[2] = 3
    numbers[3] = 1
    numbers[4] = 5
    
    printArrayInt(numbers)
    IntArray ordered_numbers := bubbleSortInt(numbers)
    printArrayInt(ordered_numbers)
    
    printTitle("Sort String Array Elements") 

    // Declare and Initialize and Array of Strings  
    Str[] names := Str[                      
            "Damian",   
            "Rogelio",  
            "Carlos",   
            "Luis",                       
            "Daniel"  
          ] 
    printArrayString(names)
    Str[] ordered_names := bubbleSortString(names)  
    printArrayString(ordered_names)

    // Multi-dimensional Array (Matrix row,column)  

    printTitle("Transpose Matrix")

    /* Matrix row=2,col=3 
     * A =  [6  4 24] 
     *      [1 -9  8] 
    */  
    Int[][] matrix := [[6, 4, 24],   
                       [1, -9, 8]]  
    printMatrix(matrix)
    Int[][] transposed_matrix := transposeMatrix(matrix)  
    printMatrix(transposed_matrix)

    // Jagged Array (Array-of-Arrays)  

    printTitle("Upper Case Random Array & Graph Number of Elements")  
        
    /*              
     * Creating an array of string arrays using the String.Split method 
     * instead of initializing it manually as follows: 
     *  
     * Str[][] text := [  
     *      [ "word1", "word2", "wordN" ],  
     *      [ "word1", "word2", "wordM" ],  
     *      ... 
     *      ]
     *  
     * Text extract from: "El ingenioso hidalgo don Quijote de la Mancha" 
     *  
     */  
    Str[][] text := [   
    "Hoy es el dia mas hermoso de nuestra vida, querido Sancho;".split,  
    "los obstaculos mas grandes, nuestras propias indecisiones;".split,  
    "nuestro enemigo mas fuerte, miedo al poderoso y nosotros mismos;".split,  
    "la cosa mas facil, equivocarnos;".split,  
    "la mas destructiva, la mentira y el egoismo;".split,  
    "la peor derrota, el desaliento;".split,  
    "los defectos mas peligrosos, la soberbia y el rencor;".split,  
    "las sensaciones mas gratas, la buena conciencia...".split    
    ]  
    printJaggedArray(text)  
    upperCaseRandomArray(text)
    printJaggedArray(text)
    graphJaggedArray(text)  

    // Array Exceptions  

    printTitle("Common Array Exceptions")  
    
    printCommonArrayExceptions(null)  
    printCommonArrayExceptions(text)

    // Accessing Class Array Elements through Indexer  

    printTitle("Alphabets")

    vowels := Alphabet(5)  
    vowels.set(0, 'a')  
    vowels.set(1, 'e')  
    vowels.set(2, 'i')  
    vowels.set(3, 'o')  
    vowels.set(4, 'u') 
    
    l := [vowels.get(0).toChar, vowels.get(1).toChar, vowels.get(2).toChar, vowels.get(3).toChar, vowels.get(4).toChar].join(",")
    echo("\nVowels = {$l}")
    
    //en := Alphabet.make(...) <-- this should work...
    en := Alphabet.makeFromStr("abcdefghijklmnopqrstuvwxyz")
    echo("English Alphabet = {${en.toStr}}") 
    
    //extract := Alphabet.make(...) <-- this should work...
    extract := Alphabet.makeFromList(en.slice(9, 10))
    echo("Alphabet Extract en[9..19] = {$extract}")
    
    word1 := [en.get(6).toChar, en.get(14).toChar, en.get(14).toChar, en.get(3).toChar].join
    word2 := [en.get(1).toChar, en.get(24).toChar, en.get(4).toChar].join
    word3 := [en.get(4).toChar, en.get(21).toChar, en.get(4).toChar, en.get(17).toChar, en.get(24).toChar, en.get(14).toChar, en.get(13).toChar, en.get(4).toChar].join
    
    echo("\n$word1 $word2, $word3!")
  }
  
  static CharArray reverseChar(CharArray arr) 
  {
    // for List Int[] you use arr.reverse() 
    reversed := CharArray.make(arr.size)
    Int j := arr.size - 1
    for (i := 0; i < arr.size; ++i) {
        reversed[i] = arr[j]
        j--
    }
    return reversed
  }
  
  static IntArray bubbleSortInt(IntArray arr) 
  {  
    Int swap := 0
    for (Int i := arr.size - 1; i > 0; i--) 
    {  
      for (Int j := 0; j < i; j++) 
      {  
        if (arr[j] > arr[j + 1]) 
        {  
          swap = arr[j]  
          arr[j] = arr[j + 1]  
          arr[j + 1] = swap 
        }  
      }  
    }  
    return arr
  } 
  
  static Str[] bubbleSortString(Str[] arr) 
  {  
    Str swap := ""  
    for (Int i := arr.size - 1; i > 0; i--) {  
      for (Int j := 0; j < i; j++) {                  
        if (arr[j][0] > arr[j + 1][0]) {  
          swap = arr[j];  
          arr[j] = arr[j + 1];  
          arr[j + 1] = swap;  
        }  
      }  
    }  
    return arr  
  }  
  
  static Int[][] transposeMatrix(Int[][] m) 
  {  
    /* Transposing a Matrix 2,3  
     *  
     * A =  [6  4 24]T [ 6  1]  
     *      [1 -9  8]  [ 4 -9] 
     *                 [24  8] 
    */
    Int[][] transposed := [,]    

    for (Int i := 0; i < m[0].size; i++) 
    { 
      Int[] row := [,]
      for (Int j := 0; j < m.size; j++) 
      {        
        row.add(m[j][i])        
      }  
      transposed.add(row)
    }
    return transposed
  }  
  
  static Void upperCaseRandomArray(Str[][] arr) 
  {   
    Int i := Int.random(0..<arr.size)
    for (Int j := 0; j < arr[i].size; j++) 
    {
      arr[i][j] = arr[i][j].upper
    }
  }
  
  static Void printArrayChar(CharArray arr) 
  {
    echo("\nPrint Array Content ${arr.typeof.name} [${arr.size}]")
  
    for (i := 0; i < arr.size; i++)  
    {
      echo(" array [${i.toStr.padl(2)}] = ${arr[i].toChar.padl(2)}")
    }
  }
  
  static Void printArrayInt(IntArray arr) 
  {
    echo("\nPrint Array Content ${arr.typeof.name} [${arr.size}]")
  
    for (i := 0; i < arr.size; i++)  
    {
      echo(" array [${i.toStr.padl(2)}] = ${arr[i].toStr.padl(2)}")
    }
  }
  
  static Void printArrayString(Str[] arr) 
  {
    echo("\nPrint Array Content ${arr.typeof.name} ${arr[0].typeof.name}[${arr.size}]")
  
    for (i := 0; i < arr.size; i++)  
    {
      echo(" array [${i.toStr.padl(2)}] = ${arr[i].padl(2)}")
    }
  }
  
  static Void printMatrix(Int[][] m) 
  {  
    echo("\nPrint Matrix Content ${m.typeof.name} ${m[0][0].typeof.name}[${m.size},${m[0].size}]")
  
    for (Int i := 0; i < m.size; i++) 
    { 
      for (Int j := 0; j < m[0].size; j++) 
      {
        echo(" array [${i.toStr.padl(2, ' ')},${j.toStr.padl(2, ' ')}] = ${m[i][j].toStr.padl(2, ' ')}")
      }
    }
  }  
  
  static Void graphJaggedArray(Str[][] arr) 
  { 
    echo("\nPrint Text Content ${arr.typeof.name} ${arr[0][0].typeof.name}[${arr.size}]")
    Int lineCount := 1  
    arr.each |Str[] s| 
    {  
      Env.cur.out.print("Line${lineCount.toStr.padl(2)}|")  
      s.each |Str w| 
      {  
        Env.cur.out.print(" * ")  
      }  
      echo(" (${s.size})")
      lineCount++  
    }      
  }
  
  static Void printJaggedArray(Str[][] arr) 
  {  
    echo("\nPrint Jagged Array Content ${arr.typeof.name} ${arr[0][0].typeof.name}[${arr.size}]")
    for (Int i := 0; i < arr.size; i++)  
    {  
      line := StrBuf()
      for (Int j := 0; j < arr[i].size; j++) 
      {  
          line.add(" ").add(arr[i][j])  
      }
      if (line.toStr == line.toStr.upper) 
      {
        line.add(" <-- [UPPERCASED]")
      }
      echo(line)  
    }  
  }  
  
  static Void printCommonArrayExceptions(Str?[]?[]? arr) 
  {  
    try 
    {  
        arr[100][100] = "hola"        
    }  
    catch (NullErr ex) 
    {  
      echo("\nException: \n${ex.typeof.name}\n$ex") 
    } 
    catch (IndexErr ex) 
    {  
      echo("\nException: \n${ex.typeof.name}\n$ex") 
    } 
    catch (Err ex)
    {  
      echo("\nException: \n${ex.typeof.name}\n$ex") 
    } 
  }  
  
  static Void printTitle(Str message) 
  {
    echo()
    echo("".padr(54, '='))
    echo(message)
    echo("".padr(54, '='))
  }
}

class Alphabet
{
  // Array Field
  Int[] letters := [,]
  
  // Indexer Getter/Setter 
  Int get(Int index) 
  {
    return letters[index]
  }
  
  Void set(Int index, Int value) 
  {
    letters[index] = value.upper
  }
  
  // Constructors
  new make(Int size) 
  {  
    letters.fill(0, size)
  }  

  new makeFromStr(Str list) 
  {  
    letters = list.upper.chars
  }  

  new makeFromList(Int[] list) 
  {  
    letters = list
  }  
  
  // Overriden Method
  override Str toStr()
  {
    Str[] characters := [,]
    this.letters.each |Int c| { characters.add(c.toChar) }
    return characters.join(",")
  }
  
  // Method
  Int[] slice(Int start, Int length)
  {
    return letters.getRange(start..<start+length)
  }
  
}


The output:








VoilĂ , that's it. Next post in the following days.

No comments:

Post a Comment