|
|
Line 1: |
Line 1: |
| {{SideTOC}}
| |
| An '''Array''' is a list of items of varying [[:Category:Types|variable types]]. Different types can coexist within the same array.
| |
| An Array can be both single-dimension and multi-dimensional.
| |
| {{Warning | Since {{arma3}} v1.55.133789 arrays are limited to maximum of '''9,999,999''' (sometimes 10,000,000) elements}}
| |
|
| |
|
| |
| == Working with arrays ==
| |
|
| |
| === Array properties ===
| |
|
| |
| An array variable is a '''pointer''' to the array (see [[https://en.wikipedia.org/wiki/Pointer (computer programming)|Wikipedia pointer 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; {{codecomment|// 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"; {{codecomment|// is ["a", "z", "c"]}}
| |
|
| |
| === Create an array ===
| |
|
| |
| {{codecomment|// Example of an empty array}}
| |
| [[private]] _myArray = [];
| |
| [[count]] _myArray; {{codecomment|// returns 0}}
| |
|
| |
| {{codecomment|// Correct syntax}}
| |
| [[private]] _myFilledArray = ["Weapon1", "Weapon2"];
| |
| [[count]] _myFilledArray; {{codecomment|// returns 2}}
| |
|
| |
| 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>
| |
| [[count]] _myArray; {{codecomment|// returns 2}}
| |
| [[count]] (_myArray [[select]] 0); {{codecomment|// returns 3}}
| |
| [[count]] (_myArray [[select]] 1); {{codecomment|// returns 4}}
| |
| [[count]] (_myArray [[select]] 2); {{codecomment|// returns 1}}
| |
| [[count]] ((_myArray [[select]] 2) [[select]] 0); {{codecomment|// 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; {{codecomment|// returns "first item"}}
| |
| _myArray [[a_hash_b|#]] 2; {{codecomment|// returns "third item" - {{arma3}} only}}
| |
|
| |
| === Setting an element ===
| |
|
| |
| [[private]] _myArray = ["first item", "second item", "third item"];
| |
| _myArray [[select]] 1; {{codecomment|// returns "second item"}}
| |
| _myArray [[set]] [1, "hello there"]; {{codecomment|// _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''.
| |
| All the "empty spaces" between the last valid element and the new [[set]] element will be filled with [[nil]]}}
| |
|
| |
| === Counting elements ===
| |
|
| |
| [[private]] _myArray = ["first item", "second item", "third item"];
| |
| [[count]] _myArray; {{codecomment|// 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; {{codecomment|// _myArray is [1, 2, 3]}}
| |
|
| |
| [[private]] _myArray = [1, 2, 3];
| |
| _myArray [[resize]] 5; {{codecomment|// _myArray is [1, 2, 3, [[nil]], [[nil]]]}}
| |
|
| |
| {{Important | You do '''not''' need to extend an array before adding elements!}}
| |
|
| |
| === Array duplication ===
| |
|
| |
| [[private]] _myArray = ["a", "b", "c"];
| |
| [[private]] _myNewArray = _myArray;
| |
| _myArray [[set]] [1, "z"];
| |
| _myNewArray [[select]] 1; {{codecomment|// will be "z"}}
| |
|
| |
| [[private]] _myArray = <nowiki>[["a", "b", "c"], ["d", "e", "f"];</nowiki>
| |
| [[private]] _subArray1 = _myArray [[select]] 0;
| |
| _subArray1 [[set]] [1, "z"];
| |
| {{codecomment|// _subArray1 is now ["a", "z", "c"]}}
| |
| {{codecomment|// _myArray is now <nowiki>[["a", "z", "c"], ["d", "e", "f"]]</nowiki>}}
| |
|
| |
| In order to avoid this behaviour, '''duplicate''' the array with [[+|+ (plus)]]:
| |
|
| |
| {{codecomment|// duplication}}
| |
| [[private]] _myArray = ["a", "b", "c"];
| |
| [[private]] _myNewArray = [[+]]_myArray;
| |
| _myArray [[set]] [1, "z"];
| |
| _myNewArray [[select]] 1; {{codecomment|// still "b"}}
| |
|
| |
| Sub-arrays are also deep-duplicated; {{Inline code|_myNewArray}} will not point at the same sub-array instances.
| |
|
| |
| === Adding (appending) elements ===
| |
|
| |
| In {{arma3}} use [[append]] and [[pushBack]] commands:
| |
|
| |
| [[private]] _myArray = [1, 2, 3];
| |
| _myArray [[pushBack]] 4; {{codecomment|// _myArray is [1, 2, 3, 4]}}
| |
| _myArray [[append]] [5, 6]; {{codecomment|// _myArray is [1, 2, 3, 4, 5, 6]}}
| |
|
| |
|
| |
| Before {{arma3}} you had to use [[+| (plus)]] in order to add a new element:
| |
|
| |
| [[private]] _myArray = [1, 2, 3];
| |
| _myArray = _myArray [[+]] [4]; {{codecomment|// _myArray is [1, 2, 3, 4]}}
| |
| _myArray = _myArray [[+]] [5, 6]; {{codecomment|// _myArray is [1, 2, 3, 4, 5, 6]}}
| |
|
| |
| {{Important | [[append]] and [[pushBack]] have been introduced in {{arma3}} and '''should be used''' for [[Code Optimisation#Adding elements|performance concerns]].}}
| |
|
| |
| === Removing (deleting) elements ===
| |
|
| |
| In {{arma3}} use [[deleteAt]] and [[deleteRange]] commands:
| |
|
| |
| [[private]] _myArray = [1, 2, 3, 4, 5];
| |
| _myArray [[deleteAt]] 0; {{codecomment|// _myArray is [2, 3, 4, 5]}}
| |
|
| |
| [[private]] _myArray = [1, 2, 3, 4, 5];
| |
| _myArray [[deleteRange]] [1, 2]; {{codecomment|// _myArray is [1, 4, 5]}}
| |
|
| |
| You can also use [[-|- (minus)]] to remove nested arrays '''in {{arma3}} only''':
| |
|
| |
| [[private]] _myArray = <nowiki>[[1, 2, 3], [4, 5, 6], [7, 8, 9]];</nowiki>
| |
| _myArray = _myArray [[-]] <nowiki>[[4, 5, 6]];</nowiki> {{codecomment|// _myArray is <nowiki>[[1, 2, 3], [7, 8, 9]]</nowiki>}}
| |
|
| |
|
| |
| Before {{arma3}} you had to use [[-|- (minus)]] for all these operations:
| |
|
| |
| [[private]] _myArray = [1, 2, 3, 4, 5];
| |
| _myArray = _myArray [[-]] [1]; {{codecomment|// _myArray is [2, 3, 4, 5]}}
| |
|
| |
| The issue with this solution is that ''all'' item instances (here, <tt>1</tt>) would be removed:
| |
|
| |
| [[private]] _myArray = [1, 2, 1, 2, 1];
| |
| _myArray = _myArray [[-]] [1]; {{codecomment|// _myArray is [2, 2]}}
| |
|
| |
| 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, 1, 2, 1];
| |
| _myArray [[set]] [2, [[objNull]]]; {{codecomment|// _myArray is [1, 2, [[objNull]], 2, 1]]}}
| |
| _myArray = _myArray [[-]] <nowiki>[</nowiki>[[objNull]]]; {{codecomment|// _myArray is [1, 2, 2, 1]]}}
| |
|
| |
| 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]; {{codecomment|// _myArray is [1, [[objNull]], [[objNull]], 4, 5]}}
| |
| _array = _array [[-]] [objNull]; {{codecomment|// _myArray is [1, 4, 5]}}
| |
|
| |
| {{Important | [[deleteAt]] and [[deleteRange]] have been introduced in {{arma3}} and '''should be used''' for [[Code Optimisation#Removing elements|performance concerns]].}}
| |
|
| |
| === 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]] { {{codecomment|// [[count]] would return 5, but 5 is at array index 4}}
| |
| [[systemChat]] [[str]] (_myArray [[select]] _i);
| |
| };
| |
|
| |
|
| |
| == Advanced usage ==
| |
|
| |
| === apply ===
| |
|
| |
| Similar to the [https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array/map "map" function in Javascript],
| |
| [[apply]] allows to apply code to every elements in an array, without changing reference to said array:
| |
|
| |
| [[private]] _myArray = [1, 2, 3, 4, 5];
| |
| _myArray [[apply]] { [[_x]] [[*]] 2 }; {{codecomment|// _myArray is [2, 4, 6, 8, 10]}}
| |
|
| |
| {{codecomment|// same as}}
| |
| [[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 }; {{codecomment|// _filteredArray is [4, 5]}}
| |
|
| |
| {{codecomment|// same as}}
| |
| [[private]] _filteredArray = [];
| |
| { [[if]] ([[_x]] > 3) [[then]] { _filteredArray [[pushBack]] [[_x]] } } [[forEach]] _myArray;
| |
|
| |
| === findIf ===
| |
|
| |
| [[findIf]] command 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];
| |
| { [[_x]] == 3 } [[findIf]] _myArray == -1; {{codecomment|// returns [[false]], meaning an element equals 3}}
| |
| { [[_x]] == 6 } [[findIf]] _myArray == -1; {{codecomment|// returns [[true]], meaning no elements equal 6}}
| |
|
| |
|
| |
| Before {{arma3}} you had to use [[count]]:
| |
|
| |
| [[private]] _myArray = [1, 2, 3, 4, 5];
| |
| { [[_x]] == 3 } [[count]] _myArray > 0; {{ codecomment|// returns [[true]], meaning an element equals 3}}
| |
| { [[_x]] == 6 } [[count]] _myArray > 0; {{ codecomment|// returns [[false]], meaning no elements equal 6}}
| |
|
| |
| {{Important | [[findIf]] has been introduced in {{arma3}} and '''should be used''' for [[Code Optimisation#findIf|performance concerns]].}}
| |
|
| |
| === 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; {{codecomment|// _result is [3, 4]}}
| |
|
| |
| === Sorting an array ===
| |
|
| |
| ==== sort ====
| |
|
| |
| The [[sort]] command allows for sorting an array of [[String]], [[Number]] or sub-[[Array]]s of string/number. It modifies the original array and '''does not return anything''':
| |
|
| |
| [[private]] _myArray = ["zzz", "aaa", "ccc"];
| |
| _myArray [[sort]] [[true]]; {{codecomment|// _myArray is ["aaa", "ccc", "zzz"]}}
| |
|
| |
| [[private]] _myArray = [666, 57, 1024, 42];
| |
| _myArray [[sort]] [[false]]; {{codecomment|// _myArray is [1024, 666, 57, 42]}}
| |
|
| |
| [[private]] _myArray = <nowiki>[["zzz", 0], ["aaa", 42], ["ccc", 33]];</nowiki>
| |
| _myArray [[sort]] [[true]]; {{codecomment|// _myArray is <nowiki>[["aaa", 42], ["ccc", 33], ["zzz", 0]]</nowiki>}}
| |
|
| |
| ==== reverse ====
| |
|
| |
| The [[reverse]] command simply reverses the array order:
| |
| [[private]] _myArray = [99, 33, 17, 24, "a", [3,2,1], 7777];
| |
| [[reverse]] _myArray; {{codecomment|// _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 = <nowiki>[</nowiki>[_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 {{arma3}} behaviour on wrong indices:
| |
|
| |
| [[private]] _myArray = ["element0"];
| |
| _myArray [[select]] -1; {{codecomment|// throws a [[Error Zero Divisor]] error message}}
| |
| _myArray [[select]] 0; {{codecomment|// returns "element0"}}
| |
| _myArray [[select]] 1; {{codecomment|// returns [[nil]]}}
| |
| _myArray [[select]] 2; {{codecomment|// 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 [[Nothing|null type]]
| |
|
| |
| === Bad syntax ===
| |
|
| |
| {{codecomment|// Error: Unexpected ","}}
| |
| [[private]] _myErroneousArray = ["Weapon1", "Weapon2", "Weapon3",]; {{codecomment|// The last element in an array must exclude the ","}}
| |
|
| |
|
| |
| [[:Category: Data Types]]
| |
|
| |
| [[Category: Sandbox]] | | [[Category: Sandbox]] |