Hi
Short question this time. What is the least-bloated way to insert a value into a list at the first index using add(). I couldnt figure out a method which is elegant and simple.
Thanks
add(mytable, myvalue)
mytable[#mytable], mytable[1] = mytable[1], mytable[#mytable]
I don't think there's a much "smoother" way to do that...
Edit: For anyone coming across this at a later date, note that as of June 2020 pico-8 (PICO-8 0.2.1) has the following API changes:
"add() now comes with an optional 3rd parameter: an integer that specifies the location in the table that the new value should be inserted at. Similarly, a new variation of del() is available: deli(tbl, index) ("delete by index") allows deleting from a given location in the table rather than by value."
For full text, see zep's post: https://www.lexaloffle.com/bbs/?tid=38665
If you want to use add to insert a value at the index=1, and you want to shift all the values up by one (rather than just swap the first and last elements as Astorek86's code does) you could:
function _init() addatend=add add=newadd end function newadd(t,v) for i=#t+1,2,-1 do t[i]=t[i-1] end --insert new value t[1]=v return v end |
If your intention wasn't to repurpose add (an overly literal interpretation, probably), you could just name the new function addatstart and not do the renaming in _init.
I don't know that it's the least-bloated way of doing it, and it has to iterate over the whole list.
Edited to return v, as Felice has done with the insert example - being relatively new to Lua and pico-8 I was unaware of this return.
you could try
table = { new_value, unpack(table) } |
it creates a new table though, so make sure you update other references to the old table anywhere else.
also no idea how fast it is when called repeatedly on large tables...
You could skip the add() there:
mytable[#mytable+1], mytable[1] = mytable[1], mytable[#mytable] |
Mind you, I don't think this is what the OP wanted.
I think the OP wants an insert function:
function ins(t,v,i) i=i or 1 -- default the insertion point to the head of the list for j=#t,i,-1 do t[j+1]=t[j] end t[i]=v return v -- do like add() and return the inserted value end mytable = {1,2,3} -- {1,2,3} ins(mytable, 0) -- {0,1,2,3} ins(mytable, "wow", 3) -- {0,1,"wow",2,3} |
@ultrabrite clever! unpack cost is proportional to list size, but agree that allocation cost of the array might be a killer (vs swapping in place)
alternative is to add as usual and iterate array from the end 😬
If you create a linked list (https://en.wikipedia.org/wiki/Linked_list), you'd be able to get the fastest insert at the beginning of the list. It's not stored in a single table now, but the memory constraint ends up being a constant multiple different, so it's not a big difference.
[Please log in to post a comment]