'Welcome to the Commodore Computer Wiki!'

DIM (dimension)

Keyword Token Version Category(s)
DIM $86 1.0 Command and Statement

Syntax

DIM var_name( size_1 [,size_2] … [,size_n] ) [,var_name( size_1 [,size_2] … [,size_n] ) ]…

Purpose

Declare and initialize one or more arrays.

Notes

var_name must not be a reserved variable or an existing array of the same type, but otherwise any name meeting the criteria for a variable name is valid. This means, for example, you can have a scalar called X (floating point), an array called X (also floating point), and an array called X$ (string).

Note that using an array in an expression (for example PRINT X(7)) without a previous DIM will implicitly create an array of 11 elements (index 0 to 10).

If var_name is an existing array of the same type (declared explicitly with a previous DIM or implicitly as described above) then a REDIM'D ARRAY error will be generated.

Although an array may be DIM'd only once, the size argument(s) may be variables or expressions. If the array size is not constant, the program should calculate the maximum size it will need (because it can not be changed later).

Multiple arrays may be created with one DIM statement by seperating each array name by a comma.

The array will have one or more dimensions. The size of the first dimension is size_1+1 elements, the size of the second dimension (if present) is size_2+1 elements, and so on up to dimension n which has size_n+1 elements. The +1 is because elements are numbered starting with zero instead of one.

1-Dimensional Example

The most common type of array. A pictorial represesntation of DIM X(5):

X 0 1 2 3 4 5
0.0 0.0 0.0 0.0 0.0 0.0

Notice there are six elements, and all have been initialized with zero (string types are initialized with an empty string).

Executing a statement such as X(2) = 9 would change the array as such:

X 0 1 2 3 4 5
0.0 0.0 9.0 0.0 0.0 0.0

2-Dimensional Example

The next most common type of array. A pictorial represesntation of DIM X(5,3):

X 0 1 2 3 4 5
0 0.0 0.0 0.0 0.0 0.0 0.0
1 0.0 0.0 0.0 0.0 0.0 0.0
2 0.0 0.0 0.0 0.0 0.0 0.0
3 0.0 0.0 0.0 0.0 0.0 0.0

Notice there are six elements per row and four rows. (This representation is arbitrary; the same DIM X(5,3) could represent four elements per row and six rows.)

Executing a statement such as X(2,3) = 9 would change the array as such:

X 0 1 2 3 4 5
0 0.0 0.0 0.0 0.0 0.0 0.0
1 0.0 0.0 0.0 0.0 0.0 0.0
2 0.0 0.0 0.0 0.0 0.0 0.0
3 0.0 0.0 9.0 0.0 0.0 0.0

Higher Dimensions

The concept can be extended to 3 or more dimensions. In practice few programs use 3 let alone larger values. The theoretical maximum number of dimensions is 255, but a BASIC line is too short to write a DIM statement that long.

Memory Usage

One innocent looking statment like DIM X(10,10) can generate an array with more elements than all other variables in the program! On the 8-bit Commodore machines, careful consideration should be given to memory requirements of any array with more than 1 dimension (or if a single dimension has more than, say, 500 elements)… this is critically important on computers with low memory like a VIC-20 or C16.

Each element in an array is allocated a number of bytes based on its type:

type bytes/element
integer 2
float 5
string 3*

*string type only considers the length and pointer generated for each string element; when a value is assigned to the element an additional amount of memory equal to the length of the string (+2 on the C128) may be used. On machines with more than 64K, additional memory is always used, however on other machines it will not be needed if the assignment is to a constant in the program (for example, D$(1)=“MONDAY”).

The number of elements plus one in each dimension are multiplied together, that product is multiplied by the size from the table above, two bytes for each n dimensions are added, and a final 6 bytes are added for the array declaration. In symbols:

bytes = (size_1 + 1) * (size_2 + 1) * … * (size_n + 1) * type + n * 2 + 6

So for example, DIM X(10,10) which would be type floating-point (5 bytes / element) would work out as:

(10+1) * (10+1) * 5 + 2 * 2 + 6 = 615 bytes

Not too bad. If it were a string (3 bytes/element) it would work out as

(10+1) * (10+1) * 3 + 2 * 2 + 6 = 373 bytes

That sounds fantastic, until you realize that each string can be up to 255 chars (257 on the C128 including hidden “back pointer”). If all elements (121 of them) used the maximum string size (and they were not constants in the program), you would need an additional 30,885 bytes! (31,097 bytes on the C128.) In other words, the string data itself will likely use more memory than the array structure. This is true if your average string length is greater than 3 (or on the C128, if the average string is greater than 1) character in length (again, assuming the string data is not a constant).

Looking at DIM X%(10,10), an integer array (2 bytes/element), we have

(10+1) * (10+1) * 2 + 2 * 2 + 6 = 252 bytes

Sweet! Only about half the size of the floating-point array (and for larger arrays, the size gets noticably less than half… approaching 40%). Of course there is a cost to reduced memory use: slower speed. Typical for computers! This is because BASIC operates natively with floating-point numbers and must make conversions back-and-forth when reading and writing an integer variable.

Finally, lets expand the last example to see how things can ballon real quickly. DIM X%(10,10,10) works out as

(10+1) * (10+1) * (10+1) * 2 + 3 * 2 + 6 = 2674 bytes

Adding 1 extra dimension increased memory usage by about 1100% in this case! The increase is a factor of very nearly the number of elements of the added dimension (a factor of 10+1 in this case).

See also LET, DEF


This page is a member of Commodore BASIC