
 Usage

There are three classes of indexing expressions available in
FreeMat: (), {}, and . Each is explained below in some
detail, and with its own example section.


 Indexing

We start with array indexing (), which is the most general
indexing expression, and can be used on any array. There are
two general forms for the indexing expression - the N-
dimensional form, for which the general syntax is

    variable(index_1,index_2,...,index_n)

and the vector form, for which the general syntax is

    variable(index)

Here each index expression is either a scalar, a range of
integer values, or the special token :, which is shorthand
for 1:end. The keyword end, when included in an indexing
expression, is assigned the length of the array in that
dimension. The concept is easier to demonstrate than
explain. Consider the following examples:

  --> A = zeros(4)

  A =
   0 0 0 0
   0 0 0 0
   0 0 0 0
   0 0 0 0

  --> B = float(randn(2))

  B =
     -0.1688    0.5183
      0.9485   -0.6864

  --> A(2:3,2:3) = B

  A =
           0         0         0         0
           0   -0.1688    0.5183         0
           0    0.9485   -0.6864         0
           0         0         0         0

Here the array indexing was used on the left hand side only.
It can also be used for right hand side indexing, as in

  --> C = A(2:3,1:end)

  C =
           0   -0.1688    0.5183         0
           0    0.9485   -0.6864         0

Note that we used the end keyword to avoid having to know
that A has 4 columns. Of course, we could also use the :
token instead:

  --> C = A(2:3,:)

  C =
           0   -0.1688    0.5183         0
           0    0.9485   -0.6864         0

An extremely useful example of : with array indexing is for
slicing. Suppose we have a 3-D array, that is 2 x 2 x 3, and
we want to set the middle slice:

  --> D = zeros(2,2,3)

  D =

  (:,:,1) =
   0 0
   0 0

  (:,:,2) =
   0 0
   0 0

  (:,:,3) =
   0 0
   0 0

  --> D(:,:,2) = int32(10*rand(2,2))

  D =

  (:,:,1) =
    0  0
    0  0

  (:,:,2) =
    9 10
    5  8

  (:,:,3) =
    0  0
    0  0

In another level of nuance, the assignment expression will
automatically fill in the indexed rectangle on the left
using data from the right hand side, as long as the lengths
match. So we can take a vector and roll it into a matrix
using this approach:

  --> A = zeros(4)

  A =
   0 0 0 0
   0 0 0 0
   0 0 0 0
   0 0 0 0

  --> v = [1;2;3;4]

  v =
   1
   2
   3
   4

  --> A(2:3,2:3) = v

  A =
   0 0 0 0
   0 1 3 0
   0 2 4 0
   0 0 0 0

The N-dimensional form of the variable index is limited to
accessing only (hyper-) rectangular regions of the array.
You cannot, for example, use it to access only the diagonal
elements of the array. To do that, you use the second form
of the array access (or a loop). The vector form treats an
arbitrary N-dimensional array as though it were a column
vector. You can then access arbitrary subsets of the arrays
elements (for example, through a find expression)
efficiently. Note that in vector form, the end keyword takes
the meaning of the total length of the array (defined as the
product of its dimensions), as opposed to the size along the
first dimension.


 Indexing

The second form of indexing operates, to a large extent, in
the same manner as the array indexing, but it is by no means
interchangable. As the name implies, cell-indexing applies
only to cell arrays. For those familiar with C, cell-
indexing is equivalent to pointer derefencing in C. First,
the syntax:

    variable{index_1,index_2,...,index_n}

and the vector form, for which the general syntax is

    variable{index}

The rules and interpretation for N-dimensional and vector
indexing are identical to (), so we will describe only the
differences. In simple terms, applying () to a cell-array
returns another cell array that is a subset of the original
array. On the other hand, applying {} to a cell-array
returns the contents of that cell array. A simple example
makes the difference quite clear:

  --> A = {1, 'hello', [1:4]}

  A =
   [1] [hello] [1x4 double array]

  --> A(1:2)

  ans =
   [1] [hello]

  --> A{1:2}

  ans =

  1 of 2:
   1


  2 of 2:
  hello

You may be surprised by the response to the last line. The
output is multiple assignments to ans!. The output of a
cell-array dereference can be used anywhere a list of
expressions is required. This includes arguments and returns
for function calls, matrix construction, etc. Here is an
example of using cell-arrays to pass parameters to a
function:

  --> A = {[1,3,0],[5,2,7]}

  A =
   [1x3 double array] [1x3 double array]

  --> max(A{1:end})

  ans =
   5 3 7

And here, cell-arrays are used to capture the return.

  --> [K{1:2}] = max(randn(1,4))
  K =
   [0.779398] [4]

Here, cell-arrays are used in the matrix construction
process:

  --> C = [A{1};A{2}]

  C =
   1 3 0
   5 2 7

Note that this form of indexing is used to implement
variable length arguments to function. See varargin and
varargout for more details.


 Indexing

The third form of indexing is structure indexing. It can
only be applied to structure arrays, and has the general
syntax

    variable.fieldname

where fieldname is one of the fields on the structure. Note
that in FreeMat, fields are allocated dynamically, so if you
reference a field that does not exist in an assignment, it
is created automatically for you. If variable is an array,
then the result of the . reference is an expression list,
exactly like the {} operator. Hence, we can use structure
indexing in a simple fashion:

  --> clear A
  --> A.color = 'blue'

  A =
      color: blue
  --> B = A.color

  B =
  blue

Or in more complicated ways using expression lists for
function arguments

  --> clear A
  --> A(1).maxargs = [1,6,7,3]

  A =
      maxargs: 1x4 double array
  --> A(2).maxargs = [5,2,9,0]

  A =
  1x2 struct array with fields:
      maxargs
  --> max(A.maxargs)

  ans =
   5 6 9 3

or to store function outputs

  --> clear A
  --> A(1).maxreturn = [];
  --> A(2).maxreturn = [];
  --> [A.maxreturn] = max(randn(1,4))
  A =
  1x2 struct array with fields:
      maxreturn

FreeMat now also supports the so called dynamic-field
indexing expressions. In this mode, the fieldname is
supplied through an expression instead of being explicitly
provided. For example, suppose we have a set of structure
indexed by color,

  --> x.red = 430;
  --> x.green = 240;
  --> x.blue = 53;
  --> x.yello = 105

  x =
      red: 430
      green: 240
      blue: 53
      yello: 105

Then we can index into the structure x using a dynamic field
reference:

  --> y = 'green'

  y =
  green
  --> a = x.(y)

  a =
   240

Note that the indexing expression has to resolve to a string
for dynamic field indexing to work.


 Indexing

The indexing expressions described above can be freely
combined to affect complicated indexing expressions. Here is
an example that exercises all three indexing expressions in
one assignment.

  --> Z{3}.foo(2) = pi

  Z =
   [0] [0] [1x1 struct array]

From this statement, FreeMat infers that Z is a cell-array
of length 3, that the third element is a structure array
(with one element), and that this structure array contains a
field named 'foo' with two double elements, the second of
which is assigned a value of pi.

* FreeMat_Documentation
* Variables_and_Arrays
* Generated on Thu Jul 25 2013 17:18:30 for FreeMat by
  doxygen_ 1.8.1.1

