My program doesn't have bugs. It just develops random features.
Dynamic arrays
Dynamic arrays are a special composite type in UnrealScript that contains a variable number of elements in a well-defined order. These elements all have the same type, called the "inner type" of the array.
UnrealScript's dynamic arrays are a true dynamic array implementation, i.e. unlike Java's dynamically-allocated fixed-size arrays they can be resized at runtime. The type declaration syntax was available (almost) from the start, but Unreal Engine 1 never provided any way to actually access or modify them at the UnrealScript level. In other words, dynamic arrays are fully usable in UnrealScript only in Unreal Engine 2 and later.
Unlike any other data type in UnrealScript, dynamic arrays have absolutely no support for replication. Attempting to replicate a dynamic array variable will have no effect on the remote instance of that variable. Attempting to use a dynamic array as parameter of a replicated function will result in the parameter being empty when the function is executed on the remote side.
Contents
Declaration syntax
Dynamic arrays are declared as part of the type:
array< type >
The inner type of a dynamic array can be a class limiter or the name of any other non-array type, including delegate types. Note that Unreal Engine 2 does not support dynamic arrays of type bool and the compiler will complain accordingly. Dynamic arrays of bool values are possible in Unreal Engine 3, though.
Be careful when declaring a dynamic array of a class limiter or delegate type. The compiler recognized two consecutive >
characters as the operator >>
and will fail with a syntax error. Insert whitespace to get around this limitation:
array< class< classname > >
A dynamic array type can be used in all places that allow a type definition. The following example code defines a class-global dynamic array of bytes and a function that uses dynamic arrays as return type and as the type of a parameter and a local variable:
var array<byte> ByteArray< SEMI > function array<int> RoundAll(array<float> Values) { local array<int> Result; //... return Result; }
The only exception are type declarations of variables, struct members and function parameters that are declared as static arrays. In this case, the dynamic array declaration is ignored.
Usage in code
Dynamic arrays provide various ways for reading and manipulating the content and length of the array. All of these must be done through variables or struct members, dynamic arrays returned from functions must be assigned to a variable first.
Accessing array data
The entire array data can be passed around if the target variable or function parameter or return type is declared as a dynamic array of the same inner type as the source array. The array data is copied in this process, so afterwards there are two independent arrays with the same data, modifications to one of them won't affect the other array's data in any way.
To access values of individual array elements, use the following syntax:
arrayreference[index]
The index may be any non-negative that is smaller than the length of the array. Any other values, i.e. negative numbers or values >= the length of the array, will return the null value of the array's inner type and write an out-of-bounds warning message to the main log file.
The same syntax can be used for assigning values to individual array elements. In this case the index must be non-negative, but may exceed the array length. If the index is equal to or greater than the current length of the array, the array grows so its last element has the specified index, i.e. its length is now index + 1
. If you can estimate the final number of elements an array will have, you can resize it manually before assigning the values.
An access method only available in Unreal Engine 3 is iteration via the foreach loop:
foreach arrayreference(valuevariable , [indexvariable]) { ... }
You can just loop over the values, or also let the loop fill in a variable with the current element's index. The value variable must be of the same type as the array's inner type, the index variable must be of type int. In Unreal Engine 2 you have to use a regular for loop with a counter variable to iterate over the array:
for (index = 0; index < arrayreference.Length; ++index) { value = arrayreference[index]; //... }
Accessing and modifying the array length
The length of an array can be retrieved with the following syntax:
arrayreference.Length
If used on the left side of the simple assignment operator, this syntax can also be used to add or remove elements to/from the array. Like all operations that add elements to the array, this will initialize the new elements with the null value of the array's inner type. Important: The Length attribute must not be used on the left side of combined assignment operators or passed to a function parameter declared with the out modifier!
Inserting and removing elements
To insert elements anywhere in the array, you can use the following syntax:
arrayreference.Insert(index, count);
This will insert count elements into the array, so that the first inserted element ends up at the specified index. The element originally located at index and any following elements are moved to make room for the new elements. The inserted elements are initialized with null values.
To remove elements from anywhere in the array, use the following syntax:
arrayreference.Remove(index, count);
This will remove count successive elements, starting with the element at index. Elements after the removed array section are moved to close the gap.
Additional array operations in Unreal Engine 3
To add empty elements at the end of the array, use:
arrayreference.Add(count);
This has the same effect as any of the following operations, but the intention is much more obvious:
arrayreference.Length = arrayreference.Length + count;
arrayreference.Insert(arrayreference.Length, count);
To add a single value to the end of the array, use:
arrayreference.AddItem(value);
This is basically the same as arrayreference[arrayreference.Length] = value;
.
Inserting individual items in the middle of the array can be done with the following syntax:
arrayreference.InsertItem(index, value);
The corresponding Unreal Engine 2 code would be arrayreference.Insert(index, 1); arrayreference[index] = value;
, i.e. two statements.
To remove all occurrences of a specific value from the array, you can use:
arrayreference.RemoveItem(value);
This will perform a linear search for the value and remove any instance it finds. In Unreal Engine 2 you need something like this for loop to do the same:
local int i; for (i = 0; i < arrayreference.length; ++i) { if (arrayreference[i] == value) { arrayreference.Remove(i--, 1); } }
Finally, Unreal Engine 3 offers two methods to search for values in an array. The simple version just looks for a value:
arrayreference.Find(value)
This returns the index of the first element containing the specified value. If the array doesn't contain this value, INDEX_NONE
is returned, i.e. the value -1. For dynamic array of structs, a second version of Find is available, which looks for values of struct members:
arrayreference.Find(membername, value)
The member name must be a name literal specifying the name of a struct member variable.
Usage in defaultproperties block
The default data for a dynamic array can either be specified per element, similar to static arrays, or for the entire array at once.
The per-element syntax is identical to that of static arrays:
arrayvariable[index] = value
For historical reasons, you can also use round parentheses to enclose the array index.
To specify all elements at once, or to clear an array from a superclass, use the following syntax:
arrayvariable = (value,value,...)
This will set the default value of the array variable to contain the specified number of elements with the specified values. A pair of empty parentheses, i.e. ()
, will explicitly clear the array. As always with defaultproperties, you can not execute any code here. For Unreal Engine 2 this includes not being able to use declared constants.
Additional operations in Unreal Engine 3
In Unreal Engine 3 you can use more convenient operations to manipulate the default values of dynamic arrays based on their parent class default data:
arrayvariable.Empty
clears the entire arrayarrayvariable.Add(value)
adds the value to the end of the arrayarrayvariable.Remove(value)
removes all occurrences of the specified value from the arrayarrayvariable.RemoveIndex(index)
removes the element with the specified indexarrayvariable.Replace(search,replacement)
replaces all occurrences of the search value with the replacement value
These operations can be mixed with regular array default values and will be "executed" at compile-time in the order they are found.
Suppose, class X contains an array called values that was filled with the following default data:
values = (1,2,3,4,5,4,3,2,1)
Now a class Y that extends X could modify the inherited default array data:
values.Remove(4) values.Replace(1,10) values.Add(1)
Its actual default array data now is (10,2,3,5,3,2,10,1)
.
Download (not export!) the original UT3 UnrealScript source files for more examples.
Usage in UnrealEd
Using and modifying dynamic array properties in UnrealEd property windows is pretty straight-forward with the buttons provided by the property window.
- Empty
- Removes all array elements.
- Add
- Adds an empty element at the end of the array.
- Duplicate
- Duplicates the array element. (This button is not available in UnrealEd 3.)
- Delete
- Removes this array element.
- Insert
- Inserts an empty element above this one.
See also
- UnrealScript Language Reference/Dynamic Arrays (Unreal Engine 2)
- UnrealScript Language Reference/Dynamic Arrays (Unreal Engine 3)
Declarations | Preprocessor • Classes • Interfaces • Cpptext • Constants • Enums • Structs • Variables (Metadata) • Replication block • Operators • Delegates • Functions • States • Defaultproperties (Subobjects) |
---|---|
Types | bool • byte • float • int • name • string • Object • Class • Enums • Structs (Vector ⋅ Rotator ⋅ Quat ⋅ Color) • Static arrays • Dynamic arrays • Delegates • Typecasting |
Literals | Boolean • Float • Integer • Names • Objects (None ⋅ Self) • Vectors • Rotators • Strings |
Flow | GoTo • If • Assert • Return • Stop • Switch • While • Do...Until • For • ForEach • Break • Continue |
Specifiers | Super • Global • Static • Default • Const |
UnrealScript | Syntax • .UC • .UCI • .UPKG • Comments • #directives • Native |