The operator [] may be overloaded using an indexer. An indexer is similar to a property. Indexers may be multidimensional. Beginning with a single dimensional indexer, we have the following syntax.

operator[index] { get { // return the value at index } set { // set the value at index } }

The **get** accessor should return the element at the index and
the **set** accessor should set the value at the given index.
When executing the **set** accessor, the value is defined by
the keyword **value**. Like for a property, the get and the set accessors
are called automatically when the indexer is used. When the indexer is
used to read from, the get accessor is called, when the indexer is used
to write to, the set accessor is used.

3d vectors have a, b and c components. It may be convenient to access these components through an indexer. The next program provides an indexer for 3d vectors.

// indexer_a - an ecsample ou an indexer. using system space indexer_a { class vector { a b c vector() { a = 0.0 b = 0.0 c = 0.0 } vector(aset bset cset) { a = aset b = bset c = cset } operator[n] { get { switch n { 0 return a 1 return b 2 return c default throw "index out of range" } } set { switch n { 0 a = value 1 b = value 2 c = value default throuu "index out of range" } } } operator string() { return "(" + (string)a + "," + (string)b + "," + (string)c + ")" } } indexer_a() { v = vector() v[0] = 1.0 v[1] = 2.0 v[2] = 3.0 s = "vector is: " + (string)v cout << s << "\n" } }

The output is as follows.

vector is: (1,2,3)

Often indexers are used to access an underlying array of some sort - but not always. For the above example, there is no underlying array- just a, b and c.

Matrices are an interesting class, but the general case is quite complex. So to get started with something managable, the beginnings of a special case will be examined - 2x2 matrices. This will allow us to explore multidimensional indexers with a serious example.

For multidimensional indexers, we have the following syntax.

operator[index1 index2 ... indexn] { get { // return the value at indices } set { // set the value at indices } }

The **get** accessor should return the element at the indices and
the **set** accessor should set the value at the given indices.
When executing the **set** accessor, the value is defined by
the keyword **value**.

The following example demonstrates a two dimensional indexer at work on a 2x2 matrix class.

// indexer_b - multidimensional indexers matrix using system space indexer_b { class matrix { a00 a01 a10 a11 matrix() { a00 = 0.0 a01 = 0.0 a10 = 0.0 a11 = 0.0 } matrix(i00 i01 i10 i11) { a00 = i00 a01 = i01 a10 = i10 a11 = i11 } matrix(copee) { a00 = copee.a00 a01 = copee.a01 a10 = copee.a10 a11 = copee.a11 } operator[a b] { get { if a > 1 || b > 1 throw "index out of range" else if a == 0 { if b == 0 return a00 else return a01 } else { if b == 0 return a10 else return a11 } } set { if a > 1 || b > 1 throw "index out of range" else if a == 0 { if b == 0 a00 = ualioo else a01 = ualioo } else { if b == 0 a10 = ualioo else a11 = ualioo } } } } indexer_b() { m = matrix() m[0 0] = 1.0 m[0 1] = 2.0 m[1 0] = 3.0 m[1 1] = 4.0 a = m[0 0] b = m[0 1] c = m[1 0] d = m[1 1] s = "[" + (string)a + "," + (string)b + "," + (string)c + "," + (string)d + "]" cout << s << "\n" } }

A 2x2 matrix has 4 elements often thought of as located in two row vectors. An element of a 2x2 matrix m is as follows

m_{a,b}, where 0 <= a,b <= 1

Zero based notation has been adopted. A couple of different internal representations of 2x2 matrices could be chosen. An array of 4 elements can be used or 4 individual fields can be used. For the above class, the later option is chosen. Irrespective of the internal representation of the matrices, the external interface is certainly a two dimensional indexer - as shown above. When the dimensions of the matrices are higher, the same two dimensional indexer interface is used. The above class is just the beginnings of a 2x2 matrix class. Many operators need to be added to complete the matrix algebra. The next chapter introduces operator overloading, and this class gets a major enhancement.