Is it possible to make a module that does not use Roblox Bindable Events that reuses threads?
Basically what I mean is:
you have a function that calls a set of other functions {a,b,c,…} and passes some parameters
for i = 1,#s do
s[i]()
end
so that makes all the functions use the current thread and thus reusing is achieved
but I also want to make it so when one function yields, a new thread is created for it to run on and the rest of the functions can continue being called on the original thread
btw I want this process to be automatic so that means no manually wrapping the functions if I know they will yield
I think you could do something like this using coroutines but it may not be actually faster. How I would do this is I would have one current coroutine that runs each function and use coroutine.status to check if it has yielded yet (ready for the next function call). If it is not ready, I would create a new coroutine to run the next function.
e.g
function runFunctionLoop()
while true do
local f, args = coroutine.yield()
if f == nil then break end
f(unpack(args))
if typeof(f) == "function" then
f(unpack(args))
end
end
end
-- Resumes a coroutine one last time to stop the loop running
function disposeCoroutine(coro)
spawn(function()
coroutine.resume(coro)
end)
end
local myFunctionRunner = coroutine.create(runFunctionLoop)
coroutine.resume(myFunctionRunner)
for i = 1,#s do
if coroutine.status(myFunctionRunner) == "running" then
-- Last function yielded? Create a new thread to run the next function.
disposeCoroutine(myFunctionRunner)
myFunctionRunner = coroutine.create(runFunctionLoop)
coroutine.resume(myFunctionRunner)
end
coroutine.resume(myFunctionRunner, s[i], {})
end
I have not tested this code, but you can probably get a basic idea of how it can be done. It is likely even slower than just using a new thread for each function though, so it might be interesting to benchmark it.
So when running code that has no yielding in it, you are guaranteed it will all run in one block and the pseudo lua thread scheduler won’t pause the code to run other code in between?
Yeah, I think so. The two main potential problems I see with the code I posted is if coroutine.resume will resume the coroutine after the current thread has finished running (in which case it will always create a new coroutine) or if there is a problem with how wait interacts with coroutine.yeild (see here).