Մոդուլ:Statistical
Արտաքին տեսք
Documentation for this module may be created at Մոդուլ:Statistical/doc
local p = {}
local Regions = mw.loadData("Մոդուլ:Statistical/Regions")
bit32 = require( 'bit32' )
local function LimitDouble(Val)
local MaxNumber = 2147483648
return Val - (math.floor(Val / MaxNumber) * MaxNumber)
end
local function shl(Val, Shift)
if Shift > 0 then
return LimitDouble(Val * (2 ^ Shift))
else
return Value
end
end
local function shr(Val, Shift)
if Shift > 0 then
return math.floor(Val / (2 ^ Shift))
else
return Val
end
end
local function MakeHash(PlaceName)
local dataLength = mw.ustring.len(PlaceName)
if dataLength == 0 then return 0 end
local hash = dataLength
local remainingBytes = math.fmod(dataLength, 2)
local numberOfLoops = math.floor(dataLength / 2)
local currentIndex = 0
local tmp = 0
while (numberOfLoops > 0) do
hash = LimitDouble(hash + mw.ustring.codepoint(PlaceName, currentIndex + 1))
tmp = bit32.bxor(shl(mw.ustring.codepoint(PlaceName, currentIndex + 2), 11), hash)
hash = bit32.bxor(shl(hash, 16), tmp)
hash = LimitDouble(hash + shr(hash, 11))
currentIndex = currentIndex + 2
numberOfLoops = numberOfLoops - 1
end
if remainingBytes == 1 then
hash = LimitDouble(hash + mw.ustring.codepoint(PlaceName, currentIndex + 1))
hash = bit32.bxor(hash, shl(hash, 10))
hash = LimitDouble(hash + shr(hash, 1))
end
hash = bit32.bxor(hash, shl(hash, 3))
hash = LimitDouble(hash + shr(hash, 5))
hash = bit32.bxor(hash, shl(hash, 4))
hash = LimitDouble(hash + shr(hash, 17))
hash = bit32.bxor(hash, shl(hash, 25))
hash = LimitDouble(hash + shr(hash, 6))
return hash
end
local function First_less_Second(a, b)
local LenA = mw.ustring.len(a)
local LenB = mw.ustring.len(b)
for i = 1, (LenA < LenB) and LenA or LenB do
if mw.ustring.codepoint(a, i, i) ~= mw.ustring.codepoint(b, i, i) then
return mw.ustring.codepoint(a, i, i) < mw.ustring.codepoint(b, i, i)
end
end
return LenA < LenB
end
function GetHashData(PlaceHash)
local NumPage = math.floor((PlaceHash - 1) / 33554432 + 2)
if NumPage == 2 and (PlaceHash - 1) < 16777216 then NumPage = 1 end
local templatename
if NumPage < 10 then templatename = "ՌԴբնակչություն/STA-00"..NumPage else templatename = "ՌԴբնակչություն/STA-0"..NumPage end
local page = mw.title.new(templatename, 10)
local RawData = page:getContent()
HashData = RawData:match("|" .. PlaceHash .. "=([^\n<]+)")
if (HashData=="") then HashData=nil
elseif (tonumber(HashData)~=nil) then HashData=tonumber(HashData) end
return HashData
end
function p.GenerateAndReturnHash(frame)
local args = frame:getParent().args
if args == nil then return "Մուտքագրեք վարչատարածքային միավորի անվանումը" end
local PlaceName = args[1]
if PlaceName == nil then return "Մուտքագրեք վարչատարածքային միավորի անվանումը" end
PlaceName = mw.text.trim(PlaceName)
local PlaceHash = MakeHash(PlaceName)
local NumPage = math.floor((PlaceHash - 1) / 33554432 + 2)
if NumPage == 2 and (PlaceHash - 1) < 16777216 then NumPage = 1 end
local templatename
if NumPage < 10 then templatename = "ՌԴբնակչություն/STA-00"..NumPage else templatename = "ՌԴբնակչություն/STA-0"..NumPage end
return PlaceHash..' → '..'[[Կաղապար:'..templatename..']]'
end
function p.GetStat(frame)
local args = frame:getParent().args
if args == nil then return "Մուտքագրեք վարչատարածքային միավորի անվանումը" end
local PlaceName = args[1]
local Format = mw.text.trim ( (args[2] or "Աղյուսակ"))
if PlaceName == nil then return "Մուտքագրեք վարչատարածքային միավորի անվանումը" end
PlaceName = mw.text.trim(PlaceName)
local Region = args['Ռեգիոն'] or ''
local check = args['check'] or ''
if check == '' or check == '0' or check == 'false' then
check = false;
else
check = true;
end
local PlaceHash = MakeHash(PlaceName)
local function FormatH()
return PlaceHash
end
local PlaceData = nil
local RegionData = nil
local test = PlaceName:match("%((%P+)%)")
if Region=='' and test~='' then
-- Եթե բնակավայրի անվանման մեջ առկա է ճշգրտում ռեգիոնի անվանմամբ, ապա կարելի է չօգտվել ինդեքսային աղյուսակից, այսինքն չգործարկել GetHashData-ն
local value = Regions[test]
if(value) then
RegionData = mw.loadData("Մոդուլ:Statistical/"..value)
PlaceData = RegionData[PlaceHash]
end
elseif Region ~= "" then
-- թույլ է տալիս մատնանշել ոչ միայն ինդեքսը, այլև ուղղակի արժեքը
Region = Regions[Region] or Region
RegionData = mw.loadData("Մոդուլ:Statistical/"..Region)
PlaceData = RegionData[PlaceHash]
end
if PlaceData == nil then
local RegionPage = GetHashData(PlaceHash)
if RegionPage == 0 then return "#տվյալներ չկան"..frame:callParserFunction{name = '#tag:ref', args = {PlaceName .." > Հեշերի համընկնում։ Նշե՛ք ռեգիոնը, օրինակ՝ <code><nowiki>{{ ՌԴբնակչություն | " .. PlaceName .. " | " .. Format .." | Ռեգիոն = Краснодарский край }}</nowiki></code>" .. ((args.nocat and "") or "[[Կատդգորիա:ՌԴբնակչություն կաղապարի սխալ պարամետրերով հոդվածներ]]")}} end
if RegionPage ~= nil then
if type(tonumber(RegionPage)) == "number" then
-- շատ վատ գործիք է, քանի որ GetHashData-ն հիշողություն խժռող ֆունկցիա է
PlaceHash=tonumber(RegionPage)
RegionPage = GetHashData(PlaceHash)
end
if type(RegionPage) == "table" then RegionPage = RegionPage[PlaceName] end
if RegionPage ~= nil then
RegionData = mw.loadData("Մոդուլ:Statistical/"..RegionPage)
if RegionData ~= nil then PlaceData = RegionData[PlaceHash] end
end
end
end
if PlaceData == nil then
if check then
return 0;
elseif Format == 'Հեշ' or Format == 'հեշ' then
return FormatH()
else
return "#տվյալներ չկան"..frame:callParserFunction{name = '#tag:ref', args = {PlaceName .." > Տվյալներ չեն գտնվել։ Միգուցե էջն անվանափոխվել է։ Ստուգե՛ք տեղեկատուն։".. ((args.nocat and "") or "[[Կատեգորիա:ՌԴբնակչություն կաղապարի սխալ պարամետրերով հոդվածներ]]")}}
end
end
if check then
return 1;
end
local LastRecord = 0
for k in pairs(PlaceData) do LastRecord = LastRecord + 1 end
local NumRecord = LastRecord
local function FormatY()
return PlaceData[NumRecord][1]
end
local function FormatN()
return PlaceData[NumRecord][2]
end
local function FormatS(SourceType)
if ( PlaceData[NumRecord][3] == nil or PlaceData[NumRecord][3] == '' ) then
return ""
else
local Source1
local Source2
if string.find(PlaceData[NumRecord][3],"%d+[A-Z]+")==1 then
if RegionData['Աղբյուրներ'][PlaceData[NumRecord][3]] ~= nil then
Source1 = RegionData['Աղբյուրներ'][PlaceData[NumRecord][3]][1]
Source2 = PlaceData[NumRecord][3]
else
Source1 = PlaceData[NumRecord][3] .. '[[Կատեգորիա:Statistical մոդուլում սխալ աղբյուրներով հոդվածներ]]'
Source2 = ""
end
else
Source1 = PlaceData[NumRecord][3]
Source2 = ""
end
if string.find(Source1, "https?://")==1 then
Source1 = '['..Source1..']'
end
if SourceType == "ա" then
return Source1
end
if Source2 == "" then
return frame:callParserFunction{name = '#tag:ref', args = {Source1}}
else
return frame:callParserFunction{name = '#tag:ref', args = {Source1, name = Source2}}
end
end
end
local function FormatF()
local lang = mw.language.getContentLanguage()
return lang:formatNum( PlaceData[NumRecord][2] )
end
local function FormatT()
if NumRecord > 1 then
if PlaceData[NumRecord][2] > PlaceData[NumRecord - 1][2] then
return "<span style='color: #0c0; font-weight:bold; font-size: larger;'>↗</span>"
elseif PlaceData[NumRecord][2] < PlaceData[NumRecord - 1][2] then
return "<span style='color: red; font-weight:bold; font-size: larger;'>↘</span>"
else
return "<span style='color:#0AF;'>→</span>"
end
else
return ""
end
end
if Format == 'Տարեթիվ' or Format == 'տ' then
return FormatY()
elseif Format == 'Չֆորմատ' or Format == 'Թիվ' or Format == 'չ' then
return FormatN()
elseif Format == 'Հղում' or Format == 'հ' then
return FormatS("հ")
elseif Format == 'Աղբյուր' or Format == 'ա' then
return FormatS("ա")
elseif Format == 'Ֆորմատ' or Format == 'ֆ' then
return FormatF()
elseif Format == 'ՖորմատՏարեթիվ' or Format == 'ֆտ' then
return FormatF().." ("..FormatY()..")"
elseif Format == 'ՖորմատՀղում' or Format == 'ֆհ' then
return FormatF()..FormatS()
elseif Format == 'ՖորմատՀղումՏարեթիվ' or Format == 'ֆհտ' then
return FormatF()..FormatS().." ("..FormatY()..")"
elseif Format == 'Միտում' or Format == 'մ' then
return FormatT()..FormatF()
elseif Format == 'Արժեք' or Format == 'ՄիտումՀղում' or Format == 'մհ' then
return FormatT()..FormatF()..FormatS()
elseif Format == 'ՄիտումՀղումՏարեթիվ' or Format == 'մհտ' then
return FormatT()..FormatF()..FormatS().." ("..FormatY()..")"
elseif Format == 'Հեշ' or Format == 'հեշ' then
return FormatH()
elseif Format == 'Դիագրամ' or Format == 'դիագրամ' then
local tempHeight = 320
local tempWidth = 800
local tempMod = math.fmod (LastRecord, 5)
if LastRecord < 40 then
tempHeight = 200 + 170 * (LastRecord - 1) / 40
tempWidth = 200 + 600 * (LastRecord - 1) / 40
end
local tempGroup = ""
local tempTooltip = ""
local tempLegend = ""
for k in pairs(PlaceData) do
NumRecord = k
tempGroup = tempGroup .. FormatN() .. ":"
tempTooltip = tempTooltip .. FormatF() .. " (" .. FormatY() .. "):"
if LastRecord < 5 or math.fmod (k, 5) == tempMod then tempLegend = tempLegend .. FormatY() end
tempLegend = tempLegend .. ":"
end
tempGroup = string.sub (tempGroup, 1, string.len (tempGroup)-1)
tempTooltip = string.sub (tempTooltip, 1, string.len (tempTooltip)-1)
tempLegend = string.sub (tempLegend, 1, string.len (tempLegend)-1)
local barChart = require('Մոդուլ:Chart')['bar chart'];
local Diagram = {
['height'] = tempHeight,
['width'] = tempWidth,
['group 1'] = tempGroup,
['tooltip 1'] = tempTooltip,
['colors'] = "#B0C4DE",
['x legends'] = tempLegend,
['group names'] = 'Բնակչության թվաքանակը',
['default color'] = '#1E90FF'
}
local cframe = mw.getCurrentFrame();
return barChart(cframe:newChild{ title=cframe.title, args = Diagram})
elseif Format == 'Գրաֆիկ' or Format == 'գրաֆիկ' then
local csv = "year,population\\n"
for k in pairs(PlaceData) do
NumRecord = k
csv = csv .. FormatY() .. "," .. FormatN() .. "\\n"
end
local json = [[{
"version": 2,
"width": 400,
"height": 200,
"data": [
{
"name": "table",
"values": "]] .. csv .. [[",
"format": {
"parse": {"year": "integer", "population": "integer"},
"type": "csv"
},
// Convert year integer (2016) into a date object (2016-01-01)
"transform": [{ "type": "formula", "field": "date", "expr": "datetime(datum.year,0,1)" }]
}
],
"scales": [
// The dates are scaled to the "x" axis - the width of the graph
{
"name": "x",
"type": "time",
"range": "width",
"domain": {"data": "table", "field": "date"}
},
// The population are scaled to the "y" axis - the height of the graph
{
"name": "y",
"type": "linear",
"range": "height",
"domain": {"data": "table", "field": "population"}
}
],
// Simple axis with horizontal grid lines
"axes": [
{"type": "x", "scale": "x", "ticks": 5},
{"type": "y", "scale": "y", "ticks": 5, "grid": true, "orient": "right", "format": "d"}
],
// The graph is drawn with two elements a thick line at the top, and a semi-transparent area below
"marks": [
{
"type": "area",
"from": {"data": "table"},
"properties": {
"enter": {
"x": {"scale": "x", "field": "date"},
"y": {"scale": "y", "value": 0},
"y2": {"scale": "y", "field": "population"},
"fill": {"value": "#99B2CC"},
"fillOpacity": {"value": 0.35},
"interpolate": {"value": "linear"}
}
}
},
{
"type": "line",
"from": {"data": "table"},
"properties": {
"enter": {
"x": {"scale": "x", "field": "date"},
"y": {"scale": "y", "field": "population"},
"stroke": {"value": "#99B2CC"},
"strokeWidth": {"value": 3},
"interpolate": {"value": "linear"}
}
}
},
{
"type": "symbol",
"from": {"data": "table"},
"properties": {
"enter": {
"x": {"scale": "x", "field": "date"},
"y": {"scale": "y", "field": "population"},
"stroke": {"value": "#99B2CC"},
"fill": {"value": "#fff"},
"size": {"value": 10}
}
}
}
]
}]]
local cframe = mw.getCurrentFrame()
return cframe:callParserFunction( '#tag:graph', json )
else
-- HTML-աղյուսակի ձևավորում
local HTML = mw.html.create('table')
local MaxData
if args['Սյունակներ'] then
Column = tonumber(args['Սյունակներ'])
else
Column = 7
end
if Column > LastRecord then Column = LastRecord end
if args['Ձևավորում'] ~= nil then
HTML:attr('class', args['Ձևավորում'])
else
HTML:attr('class', 'standard')
end
local TempRow
local NumRow = 0
TempRow = HTML:tag('th'):attr('colspan', Column):wikitext(args['Վերնագիր'] or 'Բնակչության թվաքանակը')
for i = 1, math.ceil(LastRecord / Column) do
TempRow = HTML:tag('tr'):addClass("bright")
for j = 1, Column do
NumRecord = (i - 1) * Column + j
if PlaceData[NumRecord] == nil then
TempRow:tag('th'):wikitext("")
else
TempRow:tag('th'):wikitext(FormatY()..FormatS("с"))
end
end
TempRow = HTML:tag('tr'):attr('align', 'center')
for j = 1, Column do
NumRecord = (i - 1) * Column + j
if PlaceData[NumRecord] == nil then
TempRow:tag('td'):wikitext("")
else
TempRow:tag('td'):wikitext(FormatT()..FormatF())
end
end
end
return tostring(HTML)
end
return 1, Format
end
return p