HomeUser Control Panel (unavailable in archive)ForumsTutorialsArt GalleryResourcesMaps

Iterating through structs...

05-24-2008, 05:12 AM#1
Av3n
Ok I've stumbled upon a problem, iterating through structs via timer etc.

I need help for a somewhat template of iterating through structs via timer that which i can...
  • Start and Pause the timer easily
  • No double frees or looping through structs if there ain't none.
  • Easy removable from the array in which the structs are stored

It would be nice that you put a example on how to useyour way of itertin structs

Cheers

-Av3n
05-24-2008, 07:13 AM#2
TheDamien
Collapse JASS:
globals
    YourStruct array S
    integer N = -1
endglobals

function Add takes YourStruct s returns nothing
    set N = N+1
    set S[N] = s
endfunction

function Loop takes nothing returns nothing
    local integer i = N
    loop
        exitwhen i < 0
        S[i].doStuff()
        if (S[i].weWantToRemove()) then
            set S[i] = S[N]
            set N = N-1
        endif
        set i = i-1
    endloop
endfunction

If you want to be able to remove structs at leisure, rather than during the loop, try a linked list.
05-24-2008, 07:25 AM#3
Strilanc
TheDamien is close, but he forgot to not decrease 'i' if the struct is removed (to avoid skipping the previously last struct).

But yeah, the general idea is to just maintain a list of all your things.
05-24-2008, 07:45 AM#4
grim001
Quote:
Originally Posted by Strilanc
TheDamien is close, but he forgot to not decrease 'i' if the struct is removed (to avoid skipping the previously last struct).

Not true, the last struct was done first, so i should always be decremented.

The only problem with the example is that N should be initialized to -1 and the loop should exit when i < 0. Otherwise array index 0 isn't being used.
Anyway this is my preferred style:

Collapse JASS:
globals
    MyStruct array MyStructs
    integer MyStructs_N = -1
endglobals

struct MyStruct

    static method create takes nothing returns MyStruct
        local MyStruct ms = MyStruct.allocate()
            set MyStructs_N = MyStructs_N + 1
            set MyStructs[MyStructs_N] = ms
        return ms
    endmethod

endstruct

function Main takes nothing returns nothing
    local integer i = MyStructs_N
    local MyStruct ms

        loop
            exitwhen i < 0
            set ms = MyStructs[i]

            //do stuff

            if (want to remove) then
                call ms.destroy()
                set MyStructs[i] = MyStructs[MyStructs_N]
                set MyStructs_N = MyStructs_N - 1
                if MyStucts_N == -1 then
                    call PauseTimer(GetExpiredTimer())
                endif
            endif
            set i = i - 1
        endloop

endfunction
05-24-2008, 07:50 AM#5
TheDamien
If i is not decreased S[N] will have been processed twice.

EDIT: True, grim. I'll change that now.
05-24-2008, 11:23 AM#6
Vexorian
It's cool to Pause the timer after the loop if N became 0-1.

Both examples are confusing, that variable shouldn't be called N, but last or something like that.
05-24-2008, 08:42 PM#7
Av3n
Thanks a lot guys.

-Av3n
05-24-2008, 09:14 PM#8
Strilanc
Oh whoops: I'm so used to moving upwards through arrays it's turned into a knee-jerk "I need to not increment when I remove".