Difference between revisions of "Foreach"

From the Fallout3 GECK Wiki
Jump to navigation Jump to search
imported>Odessa
(note on direct array access)
imported>Odessa
 
(3 intermediate revisions by the same user not shown)
Line 1: Line 1:
{{Function
Added by NVSE 4. Used to repeat a script block for each entry in a collection. The collection may be either a container, [[Array Variable|array]] or [[String Variable|string]]. This can be a good alternative to using [[while]] or [[goto]] because it avoids infinite loop crash mistakes. However, be wary altering the size of the collection within the loop, as this may result in unexpected behavior.
|origin = NVSE
|summary = Added by NVSE V4. Used to repeat a script block for each entry in an array. Each entry is itself a [[Array Variables|stringmap array]] with two fields, <b>"key"</b> and <b>"value"</b>.


Within foreach loops, the command <b>continue</b> may be used to skip any remaining loop code for that entry, and move on to the next. In the same context, the command <b>break</b> may be used to end the loop immediately, ignoring any remaining code and entries.
Within foreach loops, the command <b>continue</b> may be used to skip any remaining loop code for that entry, and move on to the next. In the same context, the command <b>break</b> may be used to end the loop immediately, ignoring any remaining code and entries.


|name = Foreach
==Syntax and Usage==
|returnType = void
In the case of a container, an entry is a temporary reference to an item in its inventory. This means it may be used as a [[calling reference]], but becomes invalid once the loop ends. (See also: [[GetInvRefsForItem]], [[CopyIR]], [[RemoveMeIR]], [[IsEquipped]]).
|arguments =
<pre>
  {{FunctionArgument
ref Item
  |Name = entry
ref Container
  |Type = array{{FunctionArgument
foreach Item:tempref <- Container:ref
  |Name = <-
    ; Item is a temporary reference to an item in the container
  |Type =
loop
  }}
</pre>
  }}{{FunctionArgument
 
  |Name = set
For an [[Array Variable|array]], each entry is a stringmap with two fields, <b>"key"</b> and <b>"value"</b>. The key is the index of the entry in the collection (0, 1, 2... for regular list arrays). (Note: you can replace 'entry["value"]' with the shorthand '*entry', see [[NVSE Expressions]])
  |Type = array
  }}
}}
<pre>
<pre>
array_var SomeArray
array_var Entry
array_var Entry
array_var Collection


foreach Entry <- SomeArray
foreach Entry:array <- Collection:array
     ; Entry["key"] is the key (index) of each entry (0, 1, 2... for lists)
     ; Entry["key"] is the key (index) of each entry (0, 1, 2... for lists)
     ; Entry["value"] is the value of each entry in the array
     ; Entry["value"] is the value of each entry in the array
loop
</pre>
For a string, each entry is a string containing a single character.
<pre>
string_var Char
string_var Source
foreach Char:string <- Source:string
    ; Char is a single character in String
loop
loop
</pre>
</pre>


==Example==
==Example==
<pre>
ref rItem
ref rActor
foreach rItem <- rActor
  if rItem.IsEquipped
        rItem.UnequipMe
  endif
loop
; Will unequip all equipped items from rActor
</pre>
<pre>
<pre>
array_var Beatles
array_var Beatles
Line 86: Line 104:
</pre>
</pre>
Note that above we reference <b>Entry["value"]</b> in the [[Print]] function directly, rather than use an intermediary variable (<b>let SomeVar := Entry["value"]..</b>). This is only possible when using NVSE aware functions or the [[Script Compiler Override]].
Note that above we reference <b>Entry["value"]</b> in the [[Print]] function directly, rather than use an intermediary variable (<b>let SomeVar := Entry["value"]..</b>). This is only possible when using NVSE aware functions or the [[Script Compiler Override]].
==See Also==
==See Also==
*[[While]]
*[[While]]
Line 92: Line 111:
*[[Eval]]
*[[Eval]]
*[[Label]]/[[Goto]]
*[[Label]]/[[Goto]]
*[[GetListForms]] (converts a form list to an array, so you can use foreach with it)
*[[NVSE Expressions]]
==External Links==
==External Links==
*[http://obse.silverlock.org/obse_command_doc.html#OBSE_Expressions List of supported expression found in OBSE, these are equivalent in NVSE]
*[http://obse.silverlock.org/obse_command_doc.html#OBSE_Expressions List of supported expression found in OBSE, these are equivalent in NVSE]
*[http://fallout.bethsoft.com/eng/links/privacyredirect.php?site=http://www.loverslab.com/topic/26749-tutorial-nvse4-part-1-syntax-and-expressions/ Tutorial on syntax and expressions in NVSE 4]
*[http://fallout.bethsoft.com/eng/links/privacyredirect.php?site=http://www.loverslab.com/topic/26749-tutorial-nvse4-part-1-syntax-and-expressions/ Tutorial on syntax and expressions in NVSE 4] (this link requires pre-setting user details for this site)
[[Category:Functions_(NVSE)]]
[[Category:Functions_(NVSE)]]
[[Category:Commands]]
[[Category:Commands]]
[[Category:Scripting]]
[[Category:Scripting]]

Latest revision as of 16:56, 21 March 2015

Added by NVSE 4. Used to repeat a script block for each entry in a collection. The collection may be either a container, array or string. This can be a good alternative to using while or goto because it avoids infinite loop crash mistakes. However, be wary altering the size of the collection within the loop, as this may result in unexpected behavior.

Within foreach loops, the command continue may be used to skip any remaining loop code for that entry, and move on to the next. In the same context, the command break may be used to end the loop immediately, ignoring any remaining code and entries.

Syntax and Usage[edit | edit source]

In the case of a container, an entry is a temporary reference to an item in its inventory. This means it may be used as a calling reference, but becomes invalid once the loop ends. (See also: GetInvRefsForItem, CopyIR, RemoveMeIR, IsEquipped).

ref Item
ref Container
foreach Item:tempref <- Container:ref
    ; Item is a temporary reference to an item in the container
loop

For an array, each entry is a stringmap with two fields, "key" and "value". The key is the index of the entry in the collection (0, 1, 2... for regular list arrays). (Note: you can replace 'entry["value"]' with the shorthand '*entry', see NVSE Expressions)

array_var Entry
array_var Collection

foreach Entry:array <- Collection:array
    ; Entry["key"] is the key (index) of each entry (0, 1, 2... for lists)
    ; Entry["value"] is the value of each entry in the array
loop

For a string, each entry is a string containing a single character.

string_var Char
string_var Source

foreach Char:string <- Source:string
    ; Char is a single character in String
loop

Example[edit | edit source]

ref rItem
ref rActor

foreach rItem <- rActor
   if rItem.IsEquipped
        rItem.UnequipMe
   endif
loop

; Will unequip all equipped items from rActor
array_var Beatles
array_var Entry
ref rMusician
int iPosition

let Beatles := ar_List JohnREF, PaulREF, GeorgeREF, RingoREF

foreach Entry <- Beatles
    let iPosition := Entry["key"]
    let rMusician := Entry["value"]
    Print "Entry #" + $iPosition + " is " + $rMusician
loop

; Will print in game:
; Entry #0 is John Lennon
; Entry #1 is Paul McCartney
; Entry #2 is George Harrison
; Entry #3 is Ringo Starr

Using continue:

foreach Entry <- Beatles
    let rMusician := Entry["value"]
    if rMusician.GetDead
        continue ; * Go direct to next entry: we ignore dead members
    endif
    rMusician.AddItem Beer, 1
loop

; Every living member of the Beatles is given a beer

Using break:

foreach Entry <- Beatles
    let rMusician := Entry["value"]
    if rMusician.GetInWorldSpace Liverpool
        rMusician.AddItem Beer, 1
    else
        break ; * End Loop immediately if we find a member is not in Liverpool
    endif
loop

; Give a beer to each member of the Beatles until one is found not to be in Liverpool- assume that all Beatles except Paul are in Liverpool; since Paul is the second entry of the array, only John, the first, gets a beer.

You can also use the Ar_Range command to approximate the traditional 'C' style for loop. The code below prints the numbers 0-10:

foreach Entry <- (Ar_Range 0, 10)
    Print $Entry["value"]
loop

Note that above we reference Entry["value"] in the Print function directly, rather than use an intermediary variable (let SomeVar := Entry["value"]..). This is only possible when using NVSE aware functions or the Script Compiler Override.

See Also[edit | edit source]

External Links[edit | edit source]