BlitzMax/Language/Arrays

From Wikibooks, open books for an open world
Jump to navigation Jump to search

Arrays are used to store sequences of variables, or elements. An element within an array is accessed by indexing the array with an integer offset.

The general syntax for indexing an array is:

ArrayExpression [ index1 , index2 etc... ]

Creating Arrays[edit | edit source]

The most common way to create an array is when declaring a variable:

Local int_array[10]

This will initialize the int_array variable with a 10 element array. You can declare an 'empty' array by using []:

Local int_array[]

An empty array is identical to an array with 0 elements.

Comment: Something to remember is that, unlike in earlier versions of Blitz Basic, arrays are now zero based. That is, the first element of the array has an index of 0. So if you declare an array with 4 elements, they will be indexed from 0 to 3.

Arrays may also be created 'on the fly' using the syntax:

New [ Dimension1 , Dimension2 etc... ]

This returns an array of the specified dimension(s) with each element initialized to Null. For example:

Local int_array:Int[]
int_array=New Int[10]

'Auto arrays' may be created using the syntax:

[ Element1 , Element2 etc... ]

This returns a 1 dimensional array containing the specified elements, for example:

Local int_array[]=[1,2,3,4,5]

Each element of an auto array must have exactly the same type. If necessary, you can use type conversions to enforce this.

Arrays also provide the following methods:

Method Description
Sort( ascending=True ) Sort the array.
Dimensions:Int[]() Get array dimensions.

Arrays also provide a read-only length field that returns the total number of elements in the array.

Here are some examples of using array methods:

Strict

Local arr:String[]=["some","random","strings","in","a","string","array"]

arr.Sort        'sort ascending
Print "Array in ascending order..."
For Local t:String=EachIn arr
Print t
Next

arr.Sort False  'sort descending
Print "Array in descending order..."
For Local t:String=EachIn arr
Print t
Next

Local arr2[10,20,30,40]

'Dump array dimensions
For Local i=EachIn arr2.Dimensions()
Print i
Next

Arrays Tutorial[edit | edit source]

Arrays are really objects, so the following code does not copy the array. It only creates another variable that points to the same object.

Local arr:Int[] = [1,2,3]
Local arr2:Int[] = arr

To copy an array, you must use slices. The syntax for slicing is array[from..to].Both from and to may be omitted; they default to 0 and the last index, respectively. Copying the array is simple:

Local arr2:Int[] = arr[..]

Resizing an array using slices:

Local myArray[10] 'Create an array with 10 elements (0..9)
myArray = myArray[..20] 'Increase number of elements in the array to 20
myArray = myArray[..5] 'Take the first 5 elements

Note that you cannot use slices with multi-dimensional arrays.

Resizing an Array of Arrays[edit | edit source]

Note: this is a slightly advanced topic which may confuse beginners.

Although you cannot resize normal multi-dimensional arrays, you can resize an array of arrays (that being a 1D array where each element is a 1D array).

You first need to resize the main array and then loop through each element in it and resize the arrays that they contain.

Example:

Local x :Int[][] 'Create our array of arrays 

x = x[ .. 5 ] 'resize the main array to have 5 elements

'loop through each new element in this array 
'and resize the arrays that they contain
For l = 0 Until Len( X )
	x[ l ] = X[ l ][ .. 5 ]
Next

Multi-Dimensional Arrays[edit | edit source]

To create an array with more than one dimension, you can specify indexes separated by commas:

Local int_array1 : Int[4,4] 'create a 4x4 array
Local int_array2 : Int[3,3,3] 'create a 3x3x3 array

You can then refer to them like so:

int_array1[0,0] = 100
int_array2[2,1,0] = 1000

Multi-Dimensional Auto Arrays[edit | edit source]

Note: this is a slightly more advanced topic and as such, beginners may find it confusing.

It is not currently possible to create normal multi-dimensional arrays AND auto-initialize them. You can however cheat a little:

Local string_array:String[][] = [["Bob","Kate","Percy"],["Cecil","Edmund","Elizabeth"]] 

Print string_array[0][2] 'this will print Percy
Print string_array[1][0] 'this will print Cecil

What the above actually does is create an array of type String Array. If you were to attempt to refer to it in the conventional manner it would cause an error (Incorrect number of array dimensions).

Local string_array:String[][] = [["Bob","Kate","Percy"],["Cecil","Edmund","Elizabeth"]] 
Print string_array[0,0] 'this line would cause an error

Arrays in Types[edit | edit source]

If you wish to place an array in a type you must initialize them using New before you can use it. You cannot declare the size of the array on the line after Field. For now you actually can directly declare the size of a Field array. Could not do that for Type Globals though. ( So someone could perhaps sort out this article. Might do that myself should an opportunity rise. )

Type MyType
    Field arr:Int[]         ' Not initialized
End Type

Local a_type = New MyType
a_type.arr = New Int[32]    ' Initialize the array to 32 elements

To make things easier for yourself you can create the array inside the type's New method.

Type MyType
    Field arr:Int[]         ' Not initialized

    Method New()            ' This function is called when a new MyType is created with New
        arr = New Int[32]
    End Method
End Type

Local a_type = New MyType   ' No need to initialize the array

You can also do this to multi-dimensional arrays. Just put commas between the brackets.

Type MyType
    Field arr:Int[,,]       ' Not initialized

    Method New()            ' This function is called when a new MyType is created with New
        arr = New Int[10,10,10]
    End Method
End Type

Local a_type = New MyType   ' No need to initialize the array

Array Methods[edit | edit source]

Arrays provide a Sort method, a Dimensions method and a read-only length field. In addition, there are three internal methods which you may find of some use.

Sort

Takes an optional ascending parameter that defaults to true. Here is an example of sorting an array:

Strict
Local arr:String[]=["some","random","strings","in","a","string","array"]
arr.Sort        'sort ascending
Print "Array in ascending order..."
For Local t:String=EachIn arr
       Print t
Next
arr.Sort False  'sort descending
Print "Array in descending order..."
For Local t:String=EachIn arr
       Print t
Next
Dimensions

Returns an int array with array dimensions. So for example Int[10,5].Dimensions() would return Int[2] equal to the auto array [10,5].

numberOfDimensions

Returns an Int value indicating the number of dimensions in the array.

elementTypeEncoding

Byte Ptr to a value representing the data type of the array elements.

Type encoding will return one of the following: TYPE_BYTE, TYPE_SHORT, TYPE_INT, TYPE_FLOAT, TYPE_LONG, TYPE_DOUBLE, TYPE_STRING, TYPE_OBJECT, TYPE_ARRAY, TYPE_POINTER.

sizeMinusHeader

Returns an Int value, the number of elements * 4.

Example:

Local a:Int[2,2,2]
Print a.numberOfDimensions 'Prints 3 
Print a.elementTypeEncoding[0] 'Prints 105 if Int, 102 if Float, 36 if String
Print a.sizeMinusHeader

Iterating through Array Elements[edit | edit source]

If you want to loop through each element of an array you can use a For-EachIn loop:

'create a 10 element array and pre-initialize the values
Global myArray:Int[] = [0,1,2,3,4,5,6,7,8,9]

For Local i:Int = EachIn myArray
	'print the int contained in each array element
	Print i
Next

This is all very well, but what if you want to only loop through a portion of them? Say for instance, the last five. Well for that, you need a slice like so:

'create a 10 element array and pre-initialize the values
Global myArray:Int[] = [0,1,2,3,4,5,6,7,8,9]

'loop through each element starting with the sixth element (0 based array index)
For Local i:Int = EachIn myArray[5..]
	'print the int contained in each array element
	Print i
Next