@Van,
I think you are remembering the combined inuse/freelist idea I put together. Basically the array is split into two halves - the lower half is inuse, and the upper half is free for future use, and you manage the boundary between them.
Here's the simpler one where the order of the items in the array does not matter:
type MyType_T
Key as integer
Data1 as integer
Data2 as float
endtype
global dim MyArray() as MyType_t
set array index MyArray(), -1
PrintArray(0)
AddNewUnordered()
MyArray().Key = 123
AddNewUnordered()
MyArray().Key = 456
PrintArray(100)
RemoveUnordered(0)
PrintArray(200)
AddNewUnordered()
MyArray().Key = 789
PrintArray(300)
wait key
end
function AddNewUnordered()
next array index MyArray()
if array index valid( MyArray() ) = 0 then array insert at bottom MyArray(), 10 ` Grow in steps of 10 - tunable
endfunction
function RemoveUnordered(Index as integer)
swap array items MyArray(), Index, get array index( MyArray() )
previous array index MyArray()
endfunction
function PrintArray(x as integer)
local i as integer
local y as integer
y = 0
text x, y, "Size: " + str$( array count( MyArray() ) )
inc y, 15
text x, y, "Index: " + str$( get array index( MyArray() ) )
inc y, 30
for i = 0 to get array index( MyArray() )
text x, y, "+ " + str$(i) + " : " + str$( MyArray(i).Key )
inc y, 15
next
for i = get array index( MyArray() ) + 1 to array count( MyArray() )
text x, y, "- " + str$(i) + " : " + str$( MyArray(i).Key )
inc y, 15
next
endfunction
... and here's the sorted one:
type MyType_T
Key as integer
Data1 as integer
Data2 as float
endtype
global dim MyArray() as MyType_t
set array index MyArray(), -1
PrintArray(0)
AddNewOrdered(123)
AddNewOrdered(456)
PrintArray(100)
RemoveOrdered(123)
PrintArray(200)
AddNewOrdered(789)
PrintArray(300)
wait key
end
function AddNewOrdered(Key as integer)
local Index as integer
Index = SearchOrdered(Key, 1) ` find match or insert point
if Index > get array index( MyArray() )
` Append
next array index MyArray()
if array index valid( MyArray() ) = 0 then array insert at bottom MyArray(), 10 ` Tunable
MyArray().Key = Key
else
if MyArray(Index).Key <> Key
` Insert
next array index MyArray()
if array index valid( MyArray() ) = 0 then array insert at bottom MyArray(), 10 ` Tunable
MyArray().Key = Key
rotate array MyArray(), 1, Index, get array index( MyArray() )
endif
endif
endfunction Index
function RemoveOrdered(Key as integer)
local Index as integer
Index = SearchOrdered( Key, 0 ) ` find exact match only
if Index >= 0
rotate array MyArray(), -1, Index, get array index( MyArray() )
previous array index MyArray()
endif
endfunction
function SearchOrdered(Key as integer, Nearest as integer)
local High as integer
local Low as integer
local Middle as integer
Low = -1
High = get array index( MyArray() ) + 1
while High - Low > 1
Middle = (High + Low) / 2
if MyArray(Middle).Key < Key
Low = Middle
else
High = Middle
endif
endwhile
if Nearest = 0
if High > get array index( MyArray() ) then exitfunction -1
if MyArray(High).Key <> Key then exitfunction -1
endif
endfunction High
function PrintArray(x as integer)
local i as integer
local y as integer
y = 0
text x, y, "Size: " + str$( array count( MyArray() ) )
inc y, 15
text x, y, "Index: " + str$( get array index( MyArray() ) )
inc y, 30
for i = 0 to get array index( MyArray() )
text x, y, "+ " + str$(i) + " : " + str$( MyArray(i).Key )
inc y, 15
next
for i = get array index( MyArray() ) + 1 to array count( MyArray() )
text x, y, "- " + str$(i) + " : " + str$( MyArray(i).Key )
inc y, 15
next
endfunction
Both rely on my plug-ins for identifying where the boundary between inuse and free array items is, and for fast swapping/shifting of items within the array