Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Start a Lua mathx module to hold round, shuffle, random, and a few ot…
…her things
- Loading branch information
1 parent
7c95e9d
commit dc86c43
Showing
9 changed files
with
237 additions
and
151 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,99 @@ | ||
--[========[Additional mathematical functions]========] | ||
print("Loading mathx module...") | ||
|
||
function mathx.random_choice(possible_values, random_func) | ||
random_func = random_func or mathx.random | ||
assert(type(possible_values) == "table" or type(possible_values) == "string", | ||
string.format("mathx.random_choice expects a string or table as parameter, got %s instead", | ||
type(possible_values))) | ||
|
||
local items = {} | ||
local num_choices = 0 | ||
|
||
if type(possible_values) == "string" then | ||
-- split on commas | ||
for word in possible_values:split() do | ||
-- does the word contain two dots? If yes, that's a range | ||
local dots_start, dots_end = word:find("%.%.") | ||
if dots_start then | ||
-- split on the dots if so and cast to numbers | ||
local low = tonumber(word:sub(1, dots_start-1)) | ||
local high = tonumber(word:sub(dots_end+1)) | ||
-- perhaps someone passed a string as part of the range, intercept the issue | ||
if not (low and high) then | ||
wesnoth.message("Malformed range: " .. word) | ||
table.insert(items, word) | ||
num_choices = num_choices + 1 | ||
else | ||
if low > high then | ||
-- low is greater than high, swap them | ||
low, high = high, low | ||
end | ||
|
||
-- if both ends represent the same number, then just use that number | ||
if low == high then | ||
table.insert(items, low) | ||
num_choices = num_choices + 1 | ||
else | ||
-- insert a table representing the range | ||
table.insert(items, {low, high}) | ||
-- how many items does the range contain? Increase difference by 1 because we include both ends | ||
num_choices = num_choices + (high - low) + 1 | ||
end | ||
end | ||
else | ||
-- handle as a string | ||
table.insert(items, word) | ||
num_choices = num_choices + 1 | ||
end | ||
end | ||
else | ||
num_choices = #possible_values | ||
items = possible_values | ||
-- We need to parse ranges separately anyway | ||
for i, val in ipairs(possible_values) do | ||
if type(val) == "table" then | ||
assert(#val == 2 and type(val[1]) == "number" and type(val[2]) == "number", "Malformed range for helper.rand") | ||
if val[1] > val[2] then | ||
val = {val[2], val[1]} | ||
end | ||
num_choices = num_choices + (val[2] - val[1]) | ||
end | ||
end | ||
end | ||
|
||
local idx = random_func(1, num_choices) | ||
|
||
for i, item in ipairs(items) do | ||
if type(item) == "table" then -- that's a range | ||
local elems = item[2] - item[1] + 1 -- amount of elements in the range, both ends included | ||
if elems >= idx then | ||
return item[1] + elems - idx | ||
else | ||
idx = idx - elems | ||
end | ||
else -- that's a single element | ||
idx = idx - 1 | ||
if idx == 0 then | ||
return item | ||
end | ||
end | ||
end | ||
|
||
return nil | ||
end | ||
|
||
function mathx.shuffle(t, random_func) | ||
random_func = random_func or mathx.random | ||
-- since tables are passed by reference, this is an in-place shuffle | ||
-- it uses the Fisher-Yates algorithm, also known as Knuth shuffle | ||
assert(type(t) == "table", string.format("mathx.shuffle expects a table as parameter, got %s instead", type(t))) | ||
local length = #t | ||
for index = length, 2, -1 do | ||
local random = random_func(1, index) | ||
t[index], t[random] = t[random], t[index] | ||
end | ||
end | ||
|
||
wesnoth.random = wesnoth.deprecate_api('wesnoth.random', 'mathx.random', 1, nil, mathx.random) | ||
wesnoth.get_time_stamp = wesnoth.deprecate_api('wesnoth.get_time_stamp', 'mathx.current_timestamp', 1, nil, mathx.current_timestamp) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.