Changes
Undid revision 586573269 by Mr. Stradivarius (talk) the code refactor broke some existing modules - revert for now while I work out the extent of the problem
]]
local z = {}
end
Usage:
{{#invoke: Math | order | value }}
]]
function wrapz.order(argsframe) local input_string = (frame.args[1] or frame.args.x or '0'); local input_number; input_number = pz._cleanNumber(frame, input_string); if input_number == nil then return err('order <strong class="error">Formatting error: Order of magnitude input appears non-numeric</strong>') else return pz._order(input_number) end
end
function pz._order(x) if x == 0 then return 0 end return math.floor(math.log10(math.abs(x)))
end
Usage:
{{ #invoke: Math | precision | value }}
]]
function wrapz.precision(argsframe ) local input_string = (frame.args[1] or frame.args.x or '0'); local trap_fraction = frame.args.check_fractionor false; local input_number; if yesnotype(trap_fraction, true) == 'string' then -- Returns true for all input except nil, trap_fraction = trap_fraction:lower(); if trap_fraction == 'false, "' or trap_fraction == '0' or trap_fraction == 'no", "n", "0" and a few others. See [[Module:Yesno]].' or trap_fraction == '' then trap_fraction = false; else trap_fraction = true; end end if trap_fraction then local pos = string.find(input_string, '/', 1, true); if pos ~= nil then if string.find(input_string, '/', pos + 1, true) == nil then local denominator = string.sub(input_string, pos+1, -1); local denom_value = tonumber(denominator); if denom_value ~= nil then return math.log10(denom_value); end end end end input_number, input_string = pz._cleanNumber(frame, input_string); if input_string == nil then return err('precision <strong class="error">Formatting error: Precision input appears non-numeric</strong>') else return pz._precision(input_string) end
end
function z._precision( x )
x = string.upper( x )
end
Usage:
{{#invoke:Math| max | value1 | value2 | ... }}OR {{#invoke:Math| max }}
When used with no arguments, it takes its input from the parentframe. Note, any values that do not evaluate to numbers are ignored.
]]
function wrapz.max(argsframe ) return p local args = frame._max(unpackNumberArgs(args));end if args[1] == nil thenfunction p._max(...) local function maxOfTwoparent = frame:getParent(a, b); if a > b then args = parent.args; return a end else local max_value = nil; return b end local i = 1; end while args[i] ~= nil do local max_value val = applyFuncToArgsz._cleanNumber(maxOfTwoframe, ...args[i] ); if val ~= nil then if max_value == nil or val > max_value then return max_value= val; end end i = i + 1; end return max_value
end
Usage:
{{#invoke:Math| min | value1 | value2 | ... }}
OR
{{#invoke:Math| min }}
When used with no arguments, it takes its input from the parent
frame. Note, any values that do not evaluate to numbers are ignored.
]]
function wrapz.min(argsframe ) return p local args = frame._min(unpackNumberArgs(args));end if args[1] == nil thenfunction p._min(...) local function minOfTwoparent = frame:getParent(a, b); if a < b then args = parent.args; return a end else local min_value = nil; return b end local i = 1; end while args[i] ~= nil do local min_value val = applyFuncToArgsz._cleanNumber(minOfTwoframe, ...args[i] ); if val ~= nil then if min_value == nil or val < min_value then return min_value= val; end end i = i + 1; end return min_value
end
--[[
average
Finds the average
Usage:
{{#invoke:Math| average | value1 | value2 | ... }}
OR
{{#invoke:Math| average }} When used with no arguments, it takes its input from the parentframe. Note, any values that do not evaluate to numbers are ignored.
]]
function wrapz.average(argsframe ) return p local args = frame._average(unpackNumberArgs(args));end function p._average(...) if args[1] == nil then local function getSumparent = frame:getParent(a, b); return a + b args = parent.args; end local sum, = 0; local count = applyFuncToArgs0; local i = 1; while args[i] ~= nil do local val = z._cleanNumber(getSumframe, ...args[i] ); if not val ~= nil then sum = sum then+ val count = count + 1 end i = i + 1; return 0 end else return (count == 0 and 0 or sum / count end)
end
Usage:
{{#invoke:Math | round | value | precision }} --]] function wrap.round(args) local value = p._cleanNumber(args[1] or args.value or 0) local precision = p._cleanNumber(args[2] or args.precision or 0) if value == nil or precision == nil then return err('round input appears non-numeric') else return p._round(value, precision) end end function p._round(value, precision) local rescale = math.pow(10, precision or 0); return math.floor(value * rescale + 0.5) / rescale;end --[[mod Implements the modulo operator Usage:{{#invoke:Math | mod | x | y }} --]] function wrap.mod(args) local x = p._cleanNumber(args[1]) local y = p._cleanNumber(args[2]) if not x then return err('first argument to mod appears non-numeric') elseif not y then return err('second argument to mod appears non-numeric') else return p._mod(x, y) end end function p._mod(x, y) local ret = x % y if not (0 <= ret and ret < y) then ret = 0 end return retend --[[gcd Calculates the greatest common divisor of multiple numbers Usage:{{#invoke:Math | gcd | value 1 | value 2 | value 3 | ... }}
--]]
function z.round(frame)function wrap local value, precision; value = z.gcd_cleanNumber(frame, frame.args[1] or frame.args.value or 0 ); return p precision = z._gcd(unpackNumberArgs_cleanNumber(frame, frame.args[2] or frame.args.precision or 0 ); if value == nil or precision == nil then return '<strong class="error">Formatting error: Round input appears non-numeric</strong>' else return z._round( value, precision ); end
end
function pz._gcd_round(...value, precision ) local function findGcdrescale = math.pow(a10, bprecision ); local r = b local oldr = a while r ~= 0 do local quotient = return math.floor(oldr / r) oldr, r = r, oldr - quotient value * r end if oldr < rescale + 0 then oldr = oldr * -1 end return oldr end local result, count = applyFuncToArgs(findGcd, ...5 ) return result/ rescale;
end
Usage:
{{#invoke: Math | precision_format | number | precision }}
]]
function z.precision_format( frame )
-- For access to Mediawiki built-in formatter.
local lang = mw.getContentLanguage();
local value_string, value, precision;
value, value_string = z._cleanNumber( frame, frame.args[1] or 0 );
precision = z._cleanNumber( frame, frame.args[2] or 0 );
-- Check for non-numeric input
if value == nil or precision == nil then
return '<strong class="error">Formatting error: invalid input when rounding</strong>'
end
local current_precision = z._precision( value );
end
]]
function pz._cleanNumber(frame, number_string) if type(number_string) == 'number' then -- We were passed a number, so we don't need to do any processing. return number_string, tostring(number_string) elseif type(number_string) ~= 'string' nil or not number_string:findlen('%S') == 0 then -- We were passed a non-string or a blank string, so exit. return nil, nil; end -- Attempt basic conversion local number = tonumber(number_string) -- If failed, attempt to evaluate input as an expression if number == nil then local frame = mw.getCurrentFrame() local attempt = frame:preprocess('{{#expr: ' .. number_string .. '}}'); attempt = tonumber(attempt); if attempt ~= nil then number = attempt; number_string = tostring(number); else number = nil; number_string = nil; end else number_string = number_string:match("^%s*(.-)%s*$") -- String is valid but may contain padding, clean it. number_string = number_string:match("^%+s*(.-)%s*)$") or number_string -- Trim any leading + signs. if number_string:find('^%-?0[xX]') then -- Number is using 0xnnn notation to indicate base 16; use the number that Lua detected instead. number_string = tostring(number) end end return number, number_stringend --[[Wrapper function that does basic argument processing. This ensures that all functions from #invoke can use either the currentframe or the parent frame, and it also trims whitespace for all arguments and removes blank arguments.]] local function makeWrapper(funcName) return function (frame) local args = getArgs(frame) -- Argument processing is left to Module:Arguments. Whitespace is trimmed and blank arguments are removed. return wrap[funcName](args) endend for funcName in pairs(wrap) do p[funcName] = makeWrapper(funcName);
end
return pz