Posted 16 October 2016 - 08:59 PM
It is often a good idea to split your program up into multiple files when it gets too large. Sadly, ComputerCraft does not provide any good ways to accomplish this. This tutorial shows one way to organise your source code.
While there are many different ways to do this, this method has the following advantages:
So let's put this function to use. Let's say we wanted a file which has a bunch of utility functions. We would create a file called utils.lua, which will return a table containing our functions. That could look something like this:
With our shiny new function, using this file is easy!
And check this out:
After requiring our utils.lua file again, you'll notice that it returns the same table as the first time we called it! That's our cache at work.
Anyway, I hope this tutorial has helped you. Feel free to ask questions in a reply!
While there are many different ways to do this, this method has the following advantages:
- It does not touch the global table, making access to external variables fast, while also keeping _G unpolluted.
- Each source file will only be executed once, meaning that, just like os.loadAPI, everything defined in the file will only be defined once.
- Less importantly, source files can return any type of data, not just tables.
local require
do
local requireCache = {}
require = function(file)
local absolute = shell.resolve(file)
if requireCache[absolute] ~= nil then
--# Lucky day, this file has already been loaded once!
--# Return its cached result.
return requireCache[absolute]
end
--# Create a custom environment so that loaded
--# source files also have access to require.
local env = {
require = require
}
setmetatable(env, { __index = _G, __newindex = _G })
--# Load the source file with loadfile, which
--# also allows us to pass our custom environment.
local chunk, err = loadfile(absolute, env)
--# If chunk is nil, then there was a syntax error
--# or the file does not exist.
if chunk == nil then
return error(err)
end
--# Execute the file, cache and return its return value.
local result = chunk()
requireCache[absolute] = result
return result
end
end
So let's put this function to use. Let's say we wanted a file which has a bunch of utility functions. We would create a file called utils.lua, which will return a table containing our functions. That could look something like this:
local utils = {}
function utils.clamp(val, min, max)
return math.min(math.max(val, min), max)
end
return utils
With our shiny new function, using this file is easy!
local utils = require("utils.lua")
print(utils.clamp(2, 3, 8))
print(utils.clamp(5, 3, 8))
print(utils.clamp(9, 3, 8))
--# Prints 3, 5 and 8.
And check this out:
utils.test = "Hello!"
local otherUtils = require("utils.lua")
print(otherUtils.test)
--# Prints "Hello!".
After requiring our utils.lua file again, you'll notice that it returns the same table as the first time we called it! That's our cache at work.
Anyway, I hope this tutorial has helped you. Feel free to ask questions in a reply!