### 2.1 Getting started ¶

Currently, Blitz++ provides a single array class, called `Array<T_numtype,N_rank>`. This array class provides a dynamically allocated N-dimensional array, with reference counting, arbitrary storage ordering, subarrays and slicing, flexible expression handling, and many other useful features.

#### 2.1.1 Template parameters ¶

The `Array` class takes two template parameters:

- `T_numtype` is the numeric type to be stored in the array. `T_numtype` can be an integral type (`bool`, `char`, `unsigned char`, `short int`, `short unsigned int`, `int`, `unsigned int`, `long`, `unsigned long`), floating point type (`float`, `double`, `long double`), complex type (`complex<float>`, `complex<double>`, `complex<long double>`) or any user-defined type with appropriate numeric semantics.
- `N_rank` is the rank (or dimensionality) of the array. This should be a positive integer.

To use the `Array` class, include the header `<blitz/array.h>` and use the namespace `blitz`:

    #include <blitz/array.h>

    using namespace blitz;

    Array<int,1>    x;    // A one-dimensional array of int
    Array<double,2> y;    // A two-dimensional array of double
    .
    .
    Array<complex<float>, 12> z; // A twelve-dimensional array of complex<float>

When no constructor arguments are provided, the array is empty, and no memory is allocated. To create an array which contains some data, provide the size of the array as constructor arguments:

    Array<double,2> y(4,4);   // A 4x4 array of double

The contents of a newly-created array are garbage. To initialize the array, you can write:

    y = 0;

and all the elements of the array will be set to zero. If the contents of the array are known, you can initialize it using a comma-delimited list of values. For example, this code excerpt sets `y` equal to a 4x4 identity matrix:

    y = 1, 0, 0, 0,
        0, 1, 0, 0,
        0, 0, 1, 0,
        0, 0, 0, 1;

#### 2.1.2 Array types ¶

The `Array<T,N>` class supports a variety of arrays:

- Arrays of scalar types, such as `Array<int,1>` and `Array<float,3>`
- Complex arrays, such as `Array<complex<float>,2>`
- Arrays of user-defined types. If you have a class called `Polynomial`, then `Array<Polynomial,2>` is an array of `Polynomial` objects.
- Nested homogeneous arrays using `TinyVector` and `TinyMatrix`, in which each element is a fixed-size vector or array. For example, `Array<TinyVector<float,3>,3>` is a three-dimensional vector field.
- Nested heterogeneous arrays, such as `Array<Array<int,1>,1>`, in which each element is a variable-length array.

#### 2.1.3 A simple example ¶

Here’s an example program which creates two 3x3 arrays, initializes them, and adds them:

    #include <blitz/array.h>

    using namespace blitz;

    int main()
    {
        Array<float,2> A(3,3), B(3,3), C(3,3);

        A = 1, 0, 0,
            2, 2, 2,
            1, 0, 0;

        B = 0, 0, 7,
            0, 8, 0,
            9, 9, 9;

        C = A + B;

        cout << "A = " << A << endl
             << "B = " << B << endl
             << "C = " << C << endl;

        return 0;
    }

and the output:

    A = (0,2) x (0,2)
    [ 1 0 0
      2 2 2
      1 0 0 ]

    B = (0,2) x (0,2)
    [ 0 0 7
      0 8 0
      9 9 9 ]

    C = (0,2) x (0,2)
    [ 1 0 7
      2 10 2
      10 9 9 ]

#### 2.1.4 Storage orders ¶

Blitz++ is very flexible about the way arrays are stored in memory.

The default storage format is row-major, C-style arrays whose indices start at zero.

Fortran-style arrays can also be created. Fortran arrays are stored in column-major order, and have indices which start at one. To create a Fortran-style array, use this syntax: `Array<int,2> A(3, 3, fortranArray);` The last parameter, `fortranArray`, tells the `Array` constructor to use a fortran-style array format.

`fortranArray` is a global object which has an automatic conversion to type `GeneralArrayStorage<N>`. `GeneralArrayStorage<N>` encapsulates information about how an array is laid out in memory. By altering the contents of a `GeneralArrayStorage<N>` object, you can lay out your arrays any way you want: the dimensions can be ordered arbitrarily and stored in ascending or descending order, and the starting indices can be arbitrary.

Creating custom array storage formats is described in a later section (Array storage orders).