local v=script.Parent local E=require(v.copy)local L=v.Parent local C=require(L.t)local function p(v)return v end local function s(v,...)if type(v)=="\102\117\110\099\116\105\111\110"then return v(...)end end local x=C.optional(C.callback)local G=C.tuple(C.table,C.integer,x,x)local function z(v,L,C,x)assert(G(v,L,C,x))local z=#v if L<0 then L=z+L end assert(L>0 and L<=z+1,string.format("\105\110\100\101\120 \037\100 \111\117\116 \111\102 \098\111\117\110\100\115 \111\102 \108\105\115\116 \111\102 \108\101\110\103\116\104 \037\100",L,z))C=C or p local k=E(v)if k[L]~=nil then k[L]=C(k[L],L)else k[L]=s(x,L)end return k end return z
local List = script.Parent
local copy = require(List.copy)

local Llama = List.Parent
local t = require(Llama.t)

local function noUpdate(value)
	return value
end

local function call(callback, ...)
	if type(callback) == "function" then
		return callback(...)
	end
end

local optionalCallbackType = t.optional(t.callback)
local validate = t.tuple(t.table, t.integer, optionalCallbackType, optionalCallbackType)

local function update(list, index, updater, callback)
	assert(validate(list, index, updater, callback))

	local len = #list

	if index < 0 then
		index = len + index
	end

	assert(index > 0 and index <= len + 1, string.format("index %d out of bounds of list of length %d", index, len))

	updater = updater or noUpdate

	local new = copy(list)

	if new[index] ~= nil then
		new[index] = updater(new[index], index)
	else
		new[index] = call(callback, index)
	end

	return new
end

return update