Array: Difference between revisions
Killzone Kid (talk | contribs) (→Create an array: wrong results in example) |
Lou Montana (talk | contribs) m (Add a way to find duplicate items) |
||
Line 15: | Line 15: | ||
[[private]] _myNewArray = _myArray; | [[private]] _myNewArray = _myArray; | ||
_myArray [[set]] [1, "z"]; | _myArray [[set]] [1, "z"]; | ||
_myNewArray [[select]] 1; {{ | _myNewArray [[select]] 1; {{cc|will be "z"}} | ||
An array set through [[setVariable]] does not need to be assigned again if you modify it by reference: | An array set through [[setVariable]] does not need to be assigned again if you modify it by reference: | ||
Line 21: | Line 21: | ||
[[private]] _myArray = [[player]] [[getVariable]] "myArray"; | [[private]] _myArray = [[player]] [[getVariable]] "myArray"; | ||
_myArray [[set]] [1, "z"]; | _myArray [[set]] [1, "z"]; | ||
[[player]] [[getVariable]] "myArray"; {{ | [[player]] [[getVariable]] "myArray"; {{cc|is ["a", "z", "c"]}} | ||
=== Create an array === | === Create an array === | ||
{{ | {{cc|Example of an empty array}} | ||
[[private]] _myArray = []; | [[private]] _myArray = []; | ||
[[count]] _myArray; {{ | [[count]] _myArray; {{cc|returns 0}} | ||
{{ | {{cc|Example of a filled array}} | ||
[[private]] _myFilledArray = ["abc", "def"]; | [[private]] _myFilledArray = ["abc", "def"]; | ||
[[count]] _myFilledArray; {{ | [[count]] _myFilledArray; {{cc|returns 2}} | ||
An array can hold another array within it, that can hold another array itself, etc: | An array can hold another array within it, that can hold another array itself, etc: | ||
[[private]] _myArray = <nowiki>[["my", "subArray", 1], ["mySubArray2"], [["my", "sub", "sub", "array"]]];</nowiki> | [[private]] _myArray = <nowiki>[["my", "subArray", 1], ["mySubArray2"], [["my", "sub", "sub", "array"]]];</nowiki> | ||
[[count]] _myArray; {{ | [[count]] _myArray; {{cc|returns 3}} | ||
[[count]] (_myArray [[select]] 0); {{ | [[count]] (_myArray [[select]] 0); {{cc|returns 3}} | ||
[[count]] (_myArray [[select]] 1); {{ | [[count]] (_myArray [[select]] 1); {{cc|returns 1}} | ||
[[count]] (_myArray [[select]] 2); {{ | [[count]] (_myArray [[select]] 2); {{cc|returns 1}} | ||
[[count]] ((_myArray [[select]] 2) [[select]] 0); {{ | [[count]] ((_myArray [[select]] 2) [[select]] 0); {{cc|returns 4}} | ||
=== Getting an element === | === Getting an element === | ||
Line 46: | Line 46: | ||
[[private]] _myArray = ["first item", "second item", "third item"]; | [[private]] _myArray = ["first item", "second item", "third item"]; | ||
_myArray [[select]] 0; {{ | _myArray [[select]] 0; {{cc|returns "first item"}} | ||
_myArray [[a_hash_b|#]] 2; {{ | _myArray [[a_hash_b|#]] 2; {{cc|returns "third item" - {{arma3}} only}} | ||
=== Setting an element === | === Setting an element === | ||
[[private]] _myArray = ["first item", "second item", "third item"]; | [[private]] _myArray = ["first item", "second item", "third item"]; | ||
_myArray [[select]] 1; {{ | _myArray [[select]] 1; {{cc|returns "second item"}} | ||
_myArray [[set]] [1, "hello there"]; {{ | _myArray [[set]] [1, "hello there"]; {{cc|_myArray is ["first item", "hello there", "third item"]}} | ||
{{Important | If the index given to the [[set]] command is out of bounds, the array will [[resize]] to incorporate the index ''as its last value''. | {{Important | If the index given to the [[set]] command is out of bounds, the array will [[resize]] to incorporate the index ''as its last value''. | ||
Line 61: | Line 61: | ||
[[private]] _myArray = ["first item", "second item", "third item"]; | [[private]] _myArray = ["first item", "second item", "third item"]; | ||
[[count]] _myArray; {{ | [[count]] _myArray; {{cc|returns 3}} | ||
=== Changing array size === | === Changing array size === | ||
Line 67: | Line 67: | ||
The [[resize]] command is made to reduce or expand an array: | The [[resize]] command is made to reduce or expand an array: | ||
[[private]] _myArray = [1, 2, 3, 4, 5]; | [[private]] _myArray = [1, 2, 3, 4, 5]; | ||
_myArray [[resize]] 3; {{ | _myArray [[resize]] 3; {{cc|_myArray is [1, 2, 3]}} | ||
[[private]] _myArray = [1, 2, 3]; | [[private]] _myArray = [1, 2, 3]; | ||
_myArray [[resize]] 5; {{ | _myArray [[resize]] 5; {{cc|_myArray is [1, 2, 3, [[nil]], [[nil]]]}} | ||
{{Important | You do '''not''' need to extend an array before adding elements!}} | {{Important | You do '''not''' need to extend an array before adding elements!}} | ||
Line 79: | Line 79: | ||
[[private]] _myNewArray = _myArray; | [[private]] _myNewArray = _myArray; | ||
_myArray [[set]] [1, "z"]; | _myArray [[set]] [1, "z"]; | ||
_myNewArray [[select]] 1; {{ | _myNewArray [[select]] 1; {{cc|will be "z"}} | ||
[[private]] _myArray = <nowiki>[["a", "b", "c"], ["d", "e", "f"];</nowiki> | [[private]] _myArray = <nowiki>[["a", "b", "c"], ["d", "e", "f"];</nowiki> | ||
[[private]] _subArray1 = _myArray [[select]] 0; | [[private]] _subArray1 = _myArray [[select]] 0; | ||
_subArray1 [[set]] [1, "z"]; | _subArray1 [[set]] [1, "z"]; | ||
{{ | {{cc|_subArray1 is now ["a", "z", "c"]}} | ||
{{ | {{cc|_myArray is now <nowiki>[["a", "z", "c"], ["d", "e", "f"]]</nowiki>}} | ||
In order to avoid this behaviour, '''copy''' the array with [[+|+ (plus)]]: | In order to avoid this behaviour, '''copy''' the array with [[+|+ (plus)]]: | ||
{{ | {{cc|making copy}} | ||
[[private]] _myArray = ["a", "b", "c"]; | [[private]] _myArray = ["a", "b", "c"]; | ||
[[private]] _myNewArray = [[+]]_myArray; | [[private]] _myNewArray = [[+]]_myArray; | ||
_myArray [[set]] [1, "z"]; | _myArray [[set]] [1, "z"]; | ||
_myNewArray [[select]] 1; {{ | _myNewArray [[select]] 1; {{cc|still "b"}} | ||
Sub-arrays are also deep-copied {{Inline code|_myNewArray}} will not point at the same sub-array instances. | Sub-arrays are also deep-copied {{Inline code|_myNewArray}} will not point at the same sub-array instances. | ||
Line 102: | Line 102: | ||
[[private]] _myArray = [1, 2, 3]; | [[private]] _myArray = [1, 2, 3]; | ||
_myArray [[pushBack]] 4; {{ | _myArray [[pushBack]] 4; {{cc|_myArray is [1, 2, 3, 4]}} | ||
_myArray [[append]] [5, 6]; {{ | _myArray [[append]] [5, 6]; {{cc|_myArray is [1, 2, 3, 4, 5, 6]}} | ||
You could also use [[+| (+)]] operator to add arrays. The difference is that addition returns a copy of array and thus [[Code Optimisation#Adding elements |a little slower]] than [[append]] and [[pushBack]], which modify target array. | You could also use [[+| (+)]] operator to add arrays. The difference is that addition returns a copy of array and thus [[Code Optimisation#Adding elements |a little slower]] than [[append]] and [[pushBack]], which modify target array. | ||
[[private]] _myArray = [1, 2, 3]; | [[private]] _myArray = [1, 2, 3]; | ||
_myArray = _myArray [[+]] [4]; {{ | _myArray = _myArray [[+]] [4]; {{cc|_myArray is [1, 2, 3, 4]}} | ||
_myArray = _myArray [[+]] [5, 6]; {{ | _myArray = _myArray [[+]] [5, 6]; {{cc|_myArray is [1, 2, 3, 4, 5, 6]}} | ||
=== Removing (deleting) elements === | === Removing (deleting) elements === | ||
Line 116: | Line 116: | ||
[[private]] _myArray = [1, 2, 3, 4, 5]; | [[private]] _myArray = [1, 2, 3, 4, 5]; | ||
_myArray [[deleteAt]] 0; {{ | _myArray [[deleteAt]] 0; {{cc|_myArray is [2, 3, 4, 5]}} | ||
[[private]] _myArray = [1, 2, 3, 4, 5]; | [[private]] _myArray = [1, 2, 3, 4, 5]; | ||
_myArray [[deleteRange]] [1, 2]; {{ | _myArray [[deleteRange]] [1, 2]; {{cc|_myArray is [1, 4, 5]}} | ||
You can also use [[-|(-)]] operator to subtract arrays. The subtraction returns array copy, just like addition, and this [[Code Optimisation#Removing elements|not as fast]] as [[deleteAt]] and [[deleteRange]] which modify target arrays. | You can also use [[-|(-)]] operator to subtract arrays. The subtraction returns array copy, just like addition, and this [[Code Optimisation#Removing elements|not as fast]] as [[deleteAt]] and [[deleteRange]] which modify target arrays. | ||
[[private]] _myArray = [1, 2, 3, 4, 5]; | [[private]] _myArray = [1, 2, 3, 4, 5]; | ||
_myArray = _myArray [[-]] [1]; {{ | _myArray = _myArray [[-]] [1]; {{cc|_myArray is [2, 3, 4, 5]}} | ||
In {{arma3}} it became possible to also subtract nested arrays: | In {{arma3}} it became possible to also subtract nested arrays: | ||
[[private]] _myArray = <nowiki>[[1, 2, 3], [4, 5, 6], [7, 8, 9]];</nowiki> | [[private]] _myArray = <nowiki>[[1, 2, 3], [4, 5, 6], [7, 8, 9]];</nowiki> | ||
_myArray = _myArray [[-]] <nowiki>[[4, 5, 6]];</nowiki> {{ | _myArray = _myArray [[-]] <nowiki>[[4, 5, 6]];</nowiki> {{cc|_myArray is <nowiki>[[1, 2, 3], [7, 8, 9]]</nowiki>}} | ||
The subtraction will remove ''all'' elements of second array from the first array: | The subtraction will remove ''all'' elements of second array from the first array: | ||
_myArray = [1, 2, 3, 1, 2, 3] [[-]] [1, 2]; {{ | _myArray = [1, 2, 3, 1, 2, 3] [[-]] [1, 2]; {{cc|_myArray is [3, 3]}} | ||
The solution to this issue is the combined use of [[set]] and an item that you know is '''not''' present in the array: | The solution to this issue is the combined use of [[set]] and an item that you know is '''not''' present in the array: | ||
[[private]] _myArray = [1, 2, 3, 1, 2, 3]; | [[private]] _myArray = [1, 2, 3, 1, 2, 3]; | ||
_myArray [[set]] [2, [[objNull]]]; {{ | _myArray [[set]] [2, [[objNull]]]; {{cc|_myArray is [1, 2, [[objNull]], 1, 2, 3]]}} | ||
_myArray = _myArray [[-]] <nowiki>[</nowiki>[[objNull]]]; {{ | _myArray = _myArray [[-]] <nowiki>[</nowiki>[[objNull]]]; {{cc|_myArray is [1, 2, 1, 2, 3]}} | ||
Using this technique, it is possible to mimic [[deleteRange]] behaviour this way: | Using this technique, it is possible to mimic [[deleteRange]] behaviour this way: | ||
[[private]] _myArray = [1, 2, 3, 4, 5]; | [[private]] _myArray = [1, 2, 3, 4, 5]; | ||
{ _myArray [[set]] [_x, [[objNull]]] } [[forEach]] [1, 2]; {{ | { _myArray [[set]] [_x, [[objNull]]] } [[forEach]] [1, 2]; {{cc|_myArray is [1, [[objNull]], [[objNull]], 4, 5]}} | ||
_array = _array [[-]] [objNull]; {{ | _array = _array [[-]] [objNull]; {{cc|_myArray is [1, 4, 5]}} | ||
=== Going through the array === | === Going through the array === | ||
Line 157: | Line 157: | ||
[[private]] _myArray = [1, 2, 3, 4, 5]; | [[private]] _myArray = [1, 2, 3, 4, 5]; | ||
[[for]] "_i" [[from]] 0 [[to]] '''([[count]] _myArray) -1''' [[do]] { {{ | [[for]] "_i" [[from]] 0 [[to]] '''([[count]] _myArray) -1''' [[do]] { {{cc|[[count]] would return 5, but 5 is at array index 4}} | ||
[[systemChat]] [[str]] (_myArray [[select]] _i); | [[systemChat]] [[str]] (_myArray [[select]] _i); | ||
}; | }; | ||
Line 170: | Line 170: | ||
[[private]] _myArray = [1, 2, 3, 4, 5]; | [[private]] _myArray = [1, 2, 3, 4, 5]; | ||
_myArray = _myArray [[apply]] { [[_x]] [[*]] 2 }; {{ | _myArray = _myArray [[apply]] { [[_x]] [[*]] 2 }; {{cc|_myArray is [2, 4, 6, 8, 10]}} | ||
{{ | {{cc|same as}} | ||
_myArray =+ _myArray; | _myArray =+ _myArray; | ||
[[for]] "_i" [[from]] 0 [[to]] [[count]] _myArray -1 [[do]] { | [[for]] "_i" [[from]] 0 [[to]] [[count]] _myArray -1 [[do]] { | ||
Line 184: | Line 184: | ||
[[private]] _myArray = [1, 2, 3, 4, 5]; | [[private]] _myArray = [1, 2, 3, 4, 5]; | ||
[[private]] _filteredArray = _myArray [[select]] { [[_x]] > 3 }; {{ | [[private]] _filteredArray = _myArray [[select]] { [[_x]] > 3 }; {{cc|_filteredArray is [4, 5]}} | ||
{{ | {{cc|same as}} | ||
[[private]] _filteredArray = []; | [[private]] _filteredArray = []; | ||
{ [[if]] ([[_x]] > 3) [[then]] { _filteredArray [[pushBack]] [[_x]] } } [[forEach]] _myArray; | { [[if]] ([[_x]] > 3) [[then]] { _filteredArray [[pushBack]] [[_x]] } } [[forEach]] _myArray; | ||
Line 195: | Line 195: | ||
[[private]] _myArray = [1, 2, 3, 4, 5]; | [[private]] _myArray = [1, 2, 3, 4, 5]; | ||
_myArray [[findIf]] { [[_x]] == 3 } > -1; {{ | _myArray [[findIf]] { [[_x]] == 3 } > -1; {{cc|returns [[true]], meaning there is an element that equals 3}} | ||
_myArray [[findIf]] { [[_x]] == 6 } > -1; {{ | _myArray [[findIf]] { [[_x]] == 6 } > -1; {{cc|returns [[false]], meaning there is no element that is equal to 6}} | ||
You could use [[count]] to achieve the same result, however [[count]] won't stop until it iterated through the whole array, so it might take [[Code Optimisation#findIf|longer]]. | You could use [[count]] to achieve the same result, however [[count]] won't stop until it iterated through the whole array, so it might take [[Code Optimisation#findIf|longer]]. | ||
[[private]] _myArray = [1, 2, 3, 4, 5]; | [[private]] _myArray = [1, 2, 3, 4, 5]; | ||
{ [[_x]] == 3 } [[count]] _myArray > 0; {{ | { [[_x]] == 3 } [[count]] _myArray > 0; {{cc|returns [[true]], meaning there is an element that equals 3}} | ||
{ [[_x]] == 6 } [[count]] _myArray > 0; {{ | { [[_x]] == 6 } [[count]] _myArray > 0; {{cc|returns [[false]], meaning there is no element that is equal to 6}} | ||
=== arrayIntersect === | === arrayIntersect === | ||
Line 210: | Line 210: | ||
[[private]] _array1 = [1, 2, 3, 4]; | [[private]] _array1 = [1, 2, 3, 4]; | ||
[[private]] _array2 = [3, 4, 5, 6]; | [[private]] _array2 = [3, 4, 5, 6]; | ||
[[private]] _result = _array1 [[arrayIntersect]] _array2; {{ | [[private]] _result = _array1 [[arrayIntersect]] _array2; {{cc|_result is [3, 4]}} | ||
'''You can remove duplicates (get unique items) with this command:''' | |||
[[private]] _myarray = [1, 2, 2, 3, 4]; | |||
[[private]] _result = _myArray [[arrayIntersect]] _myArray; {{cc|_result is [1, 2, 3, 4]}} | |||
Be wary that [[nil]] elements get removed by this method: | |||
[[private]] _myarray = [1, 2, nil, 3, 4]; | |||
[[private]] _result = _myArray [[arrayIntersect]] _myArray; {{cc|_result is [1, 2, 3, 4]}} | |||
=== Sorting an array === | === Sorting an array === | ||
Line 219: | Line 229: | ||
[[private]] _myArray = ["zzz", "aaa", "ccc"]; | [[private]] _myArray = ["zzz", "aaa", "ccc"]; | ||
_myArray [[sort]] [[true]]; {{ | _myArray [[sort]] [[true]]; {{cc|_myArray is ["aaa", "ccc", "zzz"]}} | ||
[[private]] _myArray = [666, 57, 1024, 42]; | [[private]] _myArray = [666, 57, 1024, 42]; | ||
_myArray [[sort]] [[false]]; {{ | _myArray [[sort]] [[false]]; {{cc|_myArray is [1024, 666, 57, 42]}} | ||
[[private]] _myArray = <nowiki>[["zzz", 0], ["aaa", 42], ["ccc", 33]];</nowiki> | [[private]] _myArray = <nowiki>[["zzz", 0], ["aaa", 42], ["ccc", 33]];</nowiki> | ||
_myArray [[sort]] [[true]]; {{ | _myArray [[sort]] [[true]]; {{cc|_myArray is <nowiki>[["aaa", 42], ["ccc", 33], ["zzz", 0]]</nowiki>}} | ||
==== reverse ==== | ==== reverse ==== | ||
Line 231: | Line 241: | ||
The [[reverse]] command simply reverses the array order: | The [[reverse]] command simply reverses the array order: | ||
[[private]] _myArray = [99, 33, 17, 24, "a", [3,2,1], 7777]; | [[private]] _myArray = [99, 33, 17, 24, "a", [3,2,1], 7777]; | ||
[[reverse]] _myArray; {{ | [[reverse]] _myArray; {{cc|_myArray is [7777, [3,2,1], "a", 24, 17, 33, 99]}} | ||
==== BIS_fnc_sortBy ==== | ==== BIS_fnc_sortBy ==== | ||
Line 243: | Line 253: | ||
=== Index rounding === | === Index rounding === | ||
In Arma scripts, indices are rounded to the nearest whole number. | In Arma scripts, indices are rounded to the nearest whole number. | ||
A boundary case (X.5, where X is any whole number) rounds to the nearest '''even''' whole number. | A boundary case (X.5, where X is any whole number) rounds to the nearest '''even''' whole number. | ||
Line 265: | Line 276: | ||
[[private]] _myArray = ["element0"]; | [[private]] _myArray = ["element0"]; | ||
_myArray [[select]] -1; {{ | _myArray [[select]] -1; {{cc|throws a [[Error Zero Divisor]] error message}} | ||
_myArray [[select]] 0; {{ | _myArray [[select]] 0; {{cc|returns "element0"}} | ||
_myArray [[select]] 1; {{ | _myArray [[select]] 1; {{cc|returns [[nil]]}} | ||
_myArray [[select]] 2; {{ | _myArray [[select]] 2; {{cc|throws a [[Error Zero Divisor]] error message}} | ||
==== set ==== | ==== set ==== | ||
Line 278: | Line 289: | ||
=== Bad syntax === | === Bad syntax === | ||
{{ | {{cc|Error: Unexpected ","}} | ||
[[private]] _myErroneousArray = ["Weapon1", "Weapon2", "Weapon3",]; {{ | [[private]] _myErroneousArray = ["Weapon1", "Weapon2", "Weapon3",]; {{cc|The last element in an array must exclude the ","}} | ||
[[Category: Data Types]] | [[Category: Data Types]] |
Revision as of 09:52, 31 August 2019
Template:SideTOC An Array is a list of items of varying variable types. Different types can coexist within the same array. An Array can either be one-dimensional or multi-dimensional.
Working with arrays
Array properties
An array variable is a reference to the array (see Wikipedia reference page); this means that if the array is edited, all the scripts/functions using a reference to this array will see the edition.
private _myArray = ["a", "b", "c"]; private _myNewArray = _myArray; _myArray set [1, "z"]; _myNewArray select 1; // will be "z"
An array set through setVariable does not need to be assigned again if you modify it by reference:
player setVariable ["myArray", ["a", "b", "c"]]; private _myArray = player getVariable "myArray"; _myArray set [1, "z"]; player getVariable "myArray"; // is ["a", "z", "c"]
Create an array
// Example of an empty array private _myArray = []; count _myArray; // returns 0 // Example of a filled array private _myFilledArray = ["abc", "def"]; count _myFilledArray; // returns 2
An array can hold another array within it, that can hold another array itself, etc:
private _myArray = [["my", "subArray", 1], ["mySubArray2"], [["my", "sub", "sub", "array"]]]; count _myArray; // returns 3 count (_myArray select 0); // returns 3 count (_myArray select 1); // returns 1 count (_myArray select 2); // returns 1 count ((_myArray select 2) select 0); // returns 4
Getting an element
An array uses a zero-based index for its elements:
private _myArray = ["first item", "second item", "third item"]; _myArray select 0; // returns "first item" _myArray # 2; // returns "third item" - Arma 3 only
Setting an element
private _myArray = ["first item", "second item", "third item"]; _myArray select 1; // returns "second item" _myArray set [1, "hello there"]; // _myArray is ["first item", "hello there", "third item"]
Counting elements
private _myArray = ["first item", "second item", "third item"]; count _myArray; // returns 3
Changing array size
The resize command is made to reduce or expand an array:
private _myArray = [1, 2, 3, 4, 5]; _myArray resize 3; // _myArray is [1, 2, 3]
private _myArray = [1, 2, 3]; _myArray resize 5; // _myArray is [1, 2, 3, nil, nil]
Array Copy
private _myArray = ["a", "b", "c"]; private _myNewArray = _myArray; _myArray set [1, "z"]; _myNewArray select 1; // will be "z"
private _myArray = [["a", "b", "c"], ["d", "e", "f"]; private _subArray1 = _myArray select 0; _subArray1 set [1, "z"]; // _subArray1 is now ["a", "z", "c"] // _myArray is now [["a", "z", "c"], ["d", "e", "f"]]
In order to avoid this behaviour, copy the array with + (plus):
// making copy private _myArray = ["a", "b", "c"]; private _myNewArray = +_myArray; _myArray set [1, "z"]; _myNewArray select 1; // still "b"
Sub-arrays are also deep-copied _myNewArray
will not point at the same sub-array instances.
Adding (appending) elements
In Arma 3 use append and pushBack commands:
private _myArray = [1, 2, 3]; _myArray pushBack 4; // _myArray is [1, 2, 3, 4] _myArray append [5, 6]; // _myArray is [1, 2, 3, 4, 5, 6]
You could also use (+) operator to add arrays. The difference is that addition returns a copy of array and thus a little slower than append and pushBack, which modify target array.
private _myArray = [1, 2, 3]; _myArray = _myArray + [4]; // _myArray is [1, 2, 3, 4] _myArray = _myArray + [5, 6]; // _myArray is [1, 2, 3, 4, 5, 6]
Removing (deleting) elements
In Arma 3 the deleteAt and deleteRange commands are available:
private _myArray = [1, 2, 3, 4, 5]; _myArray deleteAt 0; // _myArray is [2, 3, 4, 5]
private _myArray = [1, 2, 3, 4, 5]; _myArray deleteRange [1, 2]; // _myArray is [1, 4, 5]
You can also use (-) operator to subtract arrays. The subtraction returns array copy, just like addition, and this not as fast as deleteAt and deleteRange which modify target arrays.
private _myArray = [1, 2, 3, 4, 5]; _myArray = _myArray - [1]; // _myArray is [2, 3, 4, 5]
In Arma 3 it became possible to also subtract nested arrays:
private _myArray = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]; _myArray = _myArray - [[4, 5, 6]]; // _myArray is [[1, 2, 3], [7, 8, 9]]
The subtraction will remove all elements of second array from the first array:
_myArray = [1, 2, 3, 1, 2, 3] - [1, 2]; // _myArray is [3, 3]
The solution to this issue is the combined use of set and an item that you know is not present in the array:
private _myArray = [1, 2, 3, 1, 2, 3]; _myArray set [2, objNull]; // _myArray is [1, 2, objNull, 1, 2, 3]] _myArray = _myArray - [objNull]; // _myArray is [1, 2, 1, 2, 3]
Using this technique, it is possible to mimic deleteRange behaviour this way:
private _myArray = [1, 2, 3, 4, 5]; { _myArray set [_x, objNull] } forEach [1, 2]; // _myArray is [1, objNull, objNull, 4, 5] _array = _array - [objNull]; // _myArray is [1, 4, 5]
Going through the array
The simplest way to iterate through an array is the forEach command:
private _myArray = [1, 2, 3, 4, 5]; { systemChat str _x } forEach _myArray;
A combination of for, count and select can also be used:
private _myArray = [1, 2, 3, 4, 5]; for "_i" from 0 to (count _myArray) -1 do { // count would return 5, but 5 is at array index 4 systemChat str (_myArray select _i); };
Advanced usage
apply
Similar to the "map" function in Javascript, apply allows to apply code to every elements in an array and return a copy:
private _myArray = [1, 2, 3, 4, 5]; _myArray = _myArray apply { _x * 2 }; // _myArray is [2, 4, 6, 8, 10] // same as _myArray =+ _myArray; for "_i" from 0 to count _myArray -1 do { private _element = _myArray select _i; _myArray set [_i, _element * 2]; };
select
A simple way to filter an array (and obtain a new one) is using select's alternative syntax:
private _myArray = [1, 2, 3, 4, 5]; private _filteredArray = _myArray select { _x > 3 }; // _filteredArray is [4, 5] // same as private _filteredArray = []; { if (_x > 3) then { _filteredArray pushBack _x } } forEach _myArray;
findIf
The findIf command was introduced in Arma 3 and allows you to go through the whole list and stop as soon as the condition is met, returning the condition-meeting element's array index:
private _myArray = [1, 2, 3, 4, 5]; _myArray findIf { _x == 3 } > -1; // returns true, meaning there is an element that equals 3 _myArray findIf { _x == 6 } > -1; // returns false, meaning there is no element that is equal to 6
You could use count to achieve the same result, however count won't stop until it iterated through the whole array, so it might take longer.
private _myArray = [1, 2, 3, 4, 5]; { _x == 3 } count _myArray > 0; // returns true, meaning there is an element that equals 3 { _x == 6 } count _myArray > 0; // returns false, meaning there is no element that is equal to 6
arrayIntersect
The arrayIntersect command returns a new array filled with the items found in both provided lists:
private _array1 = [1, 2, 3, 4]; private _array2 = [3, 4, 5, 6]; private _result = _array1 arrayIntersect _array2; // _result is [3, 4]
You can remove duplicates (get unique items) with this command:
private _myarray = [1, 2, 2, 3, 4]; private _result = _myArray arrayIntersect _myArray; // _result is [1, 2, 3, 4]
Be wary that nil elements get removed by this method:
private _myarray = [1, 2, nil, 3, 4]; private _result = _myArray arrayIntersect _myArray; // _result is [1, 2, 3, 4]
Sorting an array
sort
The sort command allows for sorting an array of String, Number or sub-Arrays of string/number. It modifies the original array and does not return anything:
private _myArray = ["zzz", "aaa", "ccc"]; _myArray sort true; // _myArray is ["aaa", "ccc", "zzz"]
private _myArray = [666, 57, 1024, 42]; _myArray sort false; // _myArray is [1024, 666, 57, 42]
private _myArray = [["zzz", 0], ["aaa", 42], ["ccc", 33]]; _myArray sort true; // _myArray is [["aaa", 42], ["ccc", 33], ["zzz", 0]]
reverse
The reverse command simply reverses the array order:
private _myArray = [99, 33, 17, 24, "a", [3,2,1], 7777]; reverse _myArray; // _myArray is [7777, [3,2,1], "a", 24, 17, 33, 99]
BIS_fnc_sortBy
The function BIS_fnc_sortBy has been created for more complex sorting. Its algorithm input must return a number:
private _closestHelicopters = [[_heli1, _heli2, _heli3], [], { player distance _x }, "ASCEND"] call BIS_fnc_sortBy;
Common errors
Index rounding
In Arma scripts, indices are rounded to the nearest whole number. A boundary case (X.5, where X is any whole number) rounds to the nearest even whole number.
- Boundary cases
- -0.5 <= index <= 0.5 rounds to 0
- 0.5 < index < 1.5 rounds to 1
- 1.5 <= index <= 2.5 rounds to 2
- 2.5 < index < 3.5 rounds to 3
- In short
- -0.5 rounds up to 0
- 0.5 rounds down to 0
- 1.5 rounds up to 2
- 2.5 rounds down to 2
- 3.5 rounds up to 4
etc.
Index out of Range
The following code lists Arma 3 behaviour on wrong indices:
private _myArray = ["element0"]; _myArray select -1; // throws a Error Zero Divisor error message _myArray select 0; // returns "element0" _myArray select 1; // returns nil _myArray select 2; // throws a Error Zero Divisor error message
set
If the index given to the set command is out of bounds:
- If the index rounded to a negative number, then an Error Zero Divisor message will be displayed in game.
- If the index rounded to a positive number, then the array will resize to incorporate the index as its last value. Each element between the last valid element, and the new set element, will be the null type
Bad syntax
// Error: Unexpected "," private _myErroneousArray = ["Weapon1", "Weapon2", "Weapon3",]; // The last element in an array must exclude the ","