An array should not be copied with a normal "assignment" like :local array1 $array2, because it is passed by reference.
If after such an "assignment" the values of the elements of the first array are changed, then they will also change in the second one! the first array contains a reference to the second.
Below is an example of such behavior:
Code: Select all
:local array1 "empty"
:local array2 [:toarray "4,5,6"]
:put "-----------"
:put $array1;
:put $array2
Code: Select all
:set array1 $array2
:set ($array1->0) 10
:put "-----------"
:put $array1;
:put $array2
Console output:
-----------
empty
4;5;6
-----------
10;5;6
10;5;6
And some say that arrays are not passed by reference in Mikrotik ...
But, if after such manipulations the second array is reset to zero, then its elements will remain in the first one
Code: Select all
:set array2 [ ]
:put $array1;
When an array is passed to a function as a parameter, its full copy is passed. Changes that happen to an array in a function will not affect the original array.
Code: Select all
# The code creates a global array, passes it to the function
:global arrayTest [:toarray ""]
:set $arrayTest ({a=10;b=20;c=30})
:global arrayChange
:put ("fArray\t\t" . ([:tostr [$arrayChange fArray=$arrayTest]]))
:put ("arrayTest\t" . [:tostr $arrayTest])
Code: Select all
# The function changes the elements in the array and returns the changed array
:global arrayChange
:if (!any $arrayChange) do={ :global arrayChange do={
:set ($fArray->"a") 40
:set ($fArray->"b") 50
:set ($fArray->"c") 60
:return $fArray
}
}
Let's run the arrayTest function:
Code: Select all
[admin@MikroTik] > system/script/run arrayTest
a=40;b=50;c=60
a=10;b=20;c=30
and we see that the original array has not changed !
Maybe this behavior is due to the fact that the array can be a function? That is, before changing the values of an array, it must be declared as a global function?
:global arrayChange
:if (!any $arrayChange) do={ :global arrayChange do={
:global $fArray
:set ($fArray->"a") 40
:set ($fArray->"b") 50
:set ($fArray->"c") 60
:return $fArray
}.
there is no way to check now ... But I think it should be like this.