Modul:Sorterbart tall
Utseende
Moduldokumentasjon
Denne modulen inneholder noen funksjoner for å lage sorteringsnøkler og sorterbare strenger av et tall. Den implementerer funksjonalitet tilsvarende malene {{st}}/{{nts}}/{{Sorterbart tall}} og {{sts}}/{{Sorterbart tall skjult}}. Modulen kan både brukes direkte fra maler og fra andre moduler.
Oversikt
[rediger kilde]Funksjoner tilgjengelig fra moduler:
-- Returns the magnitude of a number defined as the integer part of log10 of the absolute value of the number
-- Equivalent to [[Mal:Magnitude]]
function magnitude(number)
-- Returns a sorting key for a number
function sortableNumber(number)
-- Returns a sortable string of a number (but without the number)
-- Argument displayCode is optional
-- Equivalent to [[Mal:Sorterbart tall skjult]]
function sortableNumberFormat1(number, displayCode)
-- Returns a sortable string with a formatted number
-- Arguments preStr, postStr, positiveSign, decimals and displayCode are optional
-- Equivalent to [[Mal:Sorterbart tall]]
function p.sortableNumberFormat2(number, preStr, postStr, positiveSign, decimals, displayCode)
Fra maler kan man bruke:
-- To be used from a template. Uses args from parent to template
-- Arguments from parent:
-- 1 The number
-- 2 Optional boolean: If true then display the code generated
-- Returns a sortable string of a number (but without the number)
-- Equivalent to [[Mal:Sorterbart tall skjult]]
function formatHidden(frame)
-- To be used from a template. Uses args from parent to template
-- Arguments from parent:
-- 1 The number
-- 2 Optional prefix
-- 3 Optional postfix
-- 4 Optional boolean: If true then display the code generated
-- Returns a sortable string with a formatted number
-- Equivalent to [[Mal:Sorterbart tall]]
function format(frame)
Eksempel på bruk i mal:
{{#invoke:Sorterbart tall | format | 4222 | tallet er | omtrent}}
tallet er 4 222 omtrent
(eller egentlig
)3&503&4222&
tallet er 4 222 omtrent
local getArgs = require('Module:Arguments').getArgs
local yesno = require('Module:Yesno')
local languageEnglish = mw.getLanguage('en')
-- local languageNorwegian = mw.getLanguage('no')
local languageNorwegian = mw.getContentLanguage()
local p = {}
-- Returns the magnitude of a number defined as the integer part of log10 of the absolute value of the number
-- Equivalent to [[Mal:Magnitude]]
function p.magnitude(number)
if number == 0 then return nil end
return math.floor(math.log10(math.abs(number)))
end
-- Returns a sorting key for a number
function p.sortableNumber(number)
local result = ''
if number > 0 then
result = result .. '3&' .. tostring(500 + p.magnitude(number))
elseif number < 0 then
result = result .. '1&' .. tostring(500 - p.magnitude(number))
else -- 0
result = result .. '2'
end
if number >= 0 then
result = result .. '&' .. tostring(number)
else -- negative
result = result .. '&' .. tostring(100000 * (10 + number / 10 ^ p.magnitude(number)))
end
return result .. '&';
end
-- Returns a sortable string of a number (but without the number)
-- Argument displayCode is optional
-- Equivalent to [[Mal:Sorterbart tall skjult]]
function p.sortableNumberFormat1(number, displayCode)
if number == nil then return '' end
local result = '<span data-sort-value="' .. p.sortableNumber(number) .. '">'
if displayCode then
result = result .. '<code>' .. p.sortableNumber(number) .. '</code> '
end
return result
end
-- Returns number of decimals in a numeric string
local function numberOfDecimals(numstr)
local idx1, idx2, decStr = string.find(numstr, '.*[,%.](.*)') -- Find last occurence of ',' or '.' (the decimal separation sign)
if not decStr then return 0 end
return #decStr
end
-- Returns a sortable string with a formatted number
-- Arguments preStr, postStr, positiveSign, decimals and displayCode are optional
-- Equivalent to [[Mal:Sorterbart tall]]
function p.sortableNumberFormat2(number, preStr, postStr, positiveSign, decimals, displayCode)
if number == nil then return '' end
local preStr_ = preStr or ''
local postStr_ = postStr or ''
local formattedNumber = languageNorwegian:formatNum(number)
formattedNumber = string.gsub(formattedNumber, '-', '−') -- Replace hyphen with minus
local expIdx = string.find(formattedNumber, 'E')
if expIdx then
local base = string.sub(formattedNumber, 1, expIdx - 1)
local exp = string.sub(formattedNumber, expIdx + 1)
exp = string.gsub(exp, '+', '') -- Remove plus sign in exponent
formattedNumber = base .. ' · 10<sup>' .. exp .. '</sup>'
elseif decimals and decimals > 0 then -- Only try to maintain number of decimals if not on exponential format
local decimalsInOutput = numberOfDecimals(formattedNumber)
local diffDecimals = decimals - decimalsInOutput
if diffDecimals > 0 then -- Pad output with zeros in order to maintain number of decimals
if decimalsInOutput == 0 then -- No decimals in output: Add decimal separation character
formattedNumber = formattedNumber .. ','
end
formattedNumber = formattedNumber .. string.rep('0', diffDecimals)
end
end
if positiveSign and number > 0 then -- Display plus sign for positive numbers?
formattedNumber = '+' .. formattedNumber
end
return p.sortableNumberFormat1(number, displayCode) .. preStr_ .. formattedNumber .. postStr_ .. '</span>'
end
-- Converts and returns a numeric string to a number.
-- Tries first to interpret the number as Norwegian then as English
-- Returns nil if no success
local function strToNumber(numstr)
if not numstr or #numstr == 0 then return nil end
local number = languageNorwegian:parseFormattedNumber(numstr) -- Try first Norwegian formatting
if not number then -- Not recognized as Norwegian, try English
number = languageEnglish:parseFormattedNumber(numstr)
end
if not number then
number = tonumber(numstr) -- This is a (very) long shot
end
if not number then
error('Uttrykksfeil: «' .. numstr .. '» blir ikke tolket som en numerisk verdi', 0)
end
return number
end
-- Converts numeric string to a number.
-- Checks if a positive number is prefixed with a plus sign
-- Returns number, state of sign and number of decimals in number
local function decodeNumberArg(numstr)
local number = strToNumber(numstr)
if not number then return nil, nil end
local positiveSign = false
if number > 0 then -- Check if numstr string begins with '+': Interpret this as sign for a positive number is wanted in output
positiveSign = string.match(numstr, '^%+') ~= nil
end
-- Check number of decimals in input in order to try to maintain same number of decimals in output
local decimals = numberOfDecimals(numstr)
return number, positiveSign, decimals
end
local function displayCodeParse(arg)
if not arg then return false end -- Missing arg: Default is hide
if #arg == 0 then return true end -- Empty arg: Interpret as display (due to legacy template)
if string.match(arg, 'display *: *none') then return false end -- Default arg from legacy template
return yesno(arg)
end
-- To be used from a template. Uses args from parent to template
-- Arguments from parent:
-- 1 The number
-- 2 Optional boolean: If true then display the code generated
-- Returns a sortable string of a number (but without the number)
-- Equivalent to [[Mal:Sorterbart tall skjult]]
function p.formatHidden(frame)
local args = getArgs(frame:getParent().args, {trim = true, removeBlanks = false, parentFirst = true})
return p.sortableNumberFormat1(strToNumber(args[1]), displayCodeParse(args[2])) .. '</span>'
end
-- Same as formatHidden, but should be used directly with #invoke
function p.formatHidden0(frame)
local args = getArgs(frame.args, {trim = true, removeBlanks = false, parentFirst = true})
return p.sortableNumberFormat1(strToNumber(args[1]), displayCodeParse(args[2])) .. '</span>'
end
-- To be used from a template. Uses args from parent to template
-- Arguments from parent:
-- 1 The number
-- 2 Optional prefix
-- 3 Optional postfix
-- 4 Optional boolean: If true then display the code generated
-- Returns a sortable string with a formatted number
-- Equivalent to [[Mal:Sorterbart tall]]
function p.format(frame)
local args = getArgs(frame:getParent().args, {trim = true, removeBlanks = false, parentFirst = true})
if not args[1] then error('Uttrykksfeil: Argument for tall mangler', 0) end
local numstr = string.gsub(args[1], ' ', '') -- Remove any spaces in number input
local number, positiveSign, decimals = decodeNumberArg(numstr)
if not number then return args[1] end
return p.sortableNumberFormat2(number, args[2], args[3], positiveSign, decimals, displayCodeParse(args[4]))
end
-- Same as format, but should be used directly with #invoke
function p.format0(frame)
local args = getArgs(frame.args, {trim = true, removeBlanks = false, parentFirst = true})
if not args[1] then error('Uttrykksfeil: Argument for tall mangler', 0) end
local numstr = string.gsub(args[1], ' ', '') -- Remove any spaces in number input
local number, positiveSign, decimals = decodeNumberArg(numstr)
if not number then return args[1] end
return p.sortableNumberFormat2(number, args[2], args[3], positiveSign, decimals, displayCodeParse(args[4]))
end
return p