「モジュール:Wd」の版間の差分

en:Module:Wd 2017年3月19日 (日) 09:32(UTC)より
template>K-iczn
(en:Module:Wd 2017年3月18日 (土) 20:02(UTC)より)
template>K-iczn
(en:Module:Wd 2017年3月19日 (日) 09:32(UTC)より)
112行目: 112行目:
stt.conf = cfg
stt.conf = cfg
stt.outPreferred = {}
stt.results = {}
stt.outNormal = {}
stt.outDeprecated = {}
stt.parsedFormat = {}
stt.parsedFormat = {}
517行目: 515行目:
end
end


-- sorts the claims based on ranks, which is done to increase performance in certain cases;
-- e.g. with flags "normal+|best" given and claims stored in order "normal, normal, preferred",
-- then the "normal" claims would be fully processed first while the "preferred" one might be the only one returned;
-- after sorting, this would be "preferred, normal, normal" and the "normal" claims won't be processed
function sortOnRank(claims)
function sortOnRank(claims)
local rankPos
local rankPos
local ranks = {{}, {}, {}}  -- preferred, normal, deprecated
local ranks = {{}, {}, {}, {}}  -- preferred, normal, deprecated, (default)
local sorted = {}
local sorted = {}
1,185行目: 1,179行目:
return matches, rankPos
return matches, rankPos
end
function State:appendOutput(result, rankPos)
local done = false
-- a rankPos should only apply to complete claims, NOT to its individual qualifiers or references;
-- for the latter two, no rankPos should be given and their default rankPos must be the highest possible (i.e. 1)
if rankPos then
-- must NOT be reached when appending individual qualifiers or references
if self.conf.foundRank > rankPos then
self.conf.foundRank = rankPos  -- must NOT be overwritten when appending individual qualifiers or references
if self.conf.bestRank or self.singleValue then
-- found a better rank, reset worse rank outputs
if self.conf.foundRank == 1 then
self.outNormal = {}
self.outDeprecated = {}
elseif self.conf.foundRank == 2 then
self.outDeprecated = {}
end
end
end
else
-- must be reached when appending individual qualifiers or references
rankPos = 1  -- must be the highest possible (i.e. 1)
end
if rankPos == 1 then
-- must always be reached when appending individual qualifiers or references
self.outPreferred[#self.outPreferred + 1] = result
if self.singleValue then
done = true
end
elseif rankPos == 2 then
self.outNormal[#self.outNormal + 1] = result
if self.singleValue and not self.conf.ranks[1] then
done = true
end
elseif rankPos == 3 then
self.outDeprecated[#self.outDeprecated + 1] = result
if self.singleValue and not self.conf.ranks[1] and not self.conf.ranks[2] then
done = true
end
end
return done
end
end


function State:out()
function State:out()
local result  -- collection of arrays with value objects
local valuesArray  -- array with value objects
local sep = ""
local out = {}  -- array with value objects
local out = {}  -- array with value objects
1,265行目: 1,213行目:
end
end
local function prepend(results)
-- iterate through the results from back to front, so that we know when to add separators
local sep = ""
for i = #self.results, 1, -1 do
local result -- collection of arrays with value objects
result = self.results[i]
local valuesArray  -- array with value objects
-- iterate from back to front, so that we know when to add separators
-- if there is already some output, then add the separators
for i = #results, 1, -1 do
if #out > 0 then
result = results[i]
sep = self.separator[1]  -- fixed separator
result[parameters.separator] = { {self.movSeparator[1]} }  -- movable separator
-- if there is already some output, then add the separators
else
if #out > 0 then
sep = ""
sep = self.separator[1]  -- fixed separator
result[parameters.separator] = { {self.puncMark[1]} }  -- optional punctuation mark
result[parameters.separator] = { {self.movSeparator[1]} }  -- movable separator
end
else
sep = ""
valuesArray = walk(self.parsedFormat, result)
result[parameters.separator] = { {self.puncMark[1]} }  -- optional punctuation mark
end
if #valuesArray > 0 then
valuesArray[#valuesArray + 1] = {sep}
valuesArray = walk(self.parsedFormat, result)
out = mergeTables(valuesArray, out)
if #valuesArray > 0 then
valuesArray[#valuesArray + 1] = {sep}
out = mergeTables(valuesArray, out)
end
end
end
end
end
prepend(self.outDeprecated)
prepend(self.outNormal)
prepend(self.outPreferred)
-- reset state before next iteration
-- reset state before next iteration
self.outDeprecated = {}
self.results = {}
self.outNormal = {}
self.outPreferred = {}
return out
return out
1,494行目: 1,430行目:
matchHook = matchHook or alwaysTrue
matchHook = matchHook or alwaysTrue
local done = false
local matches = false
local matches = false
local rankPos = nil
local rankPos = nil
local result, numValues, doAppend, gotRequired
local result, gotRequired
for i, v in ipairs(statements) do
for i, v in ipairs(statements) do
-- rankPos will be nil for non-claim statements (e.g. qualifiers, references, etc.),
-- rankPos will be nil for non-claim statements (e.g. qualifiers, references, etc.)
-- but let appendOutput handle that
matches, rankPos = matchHook(self, v)
matches, rankPos = matchHook(self, v)
if matches then
if matches then
result = {count = 0}  -- collection of arrays with value objects
result = {count = 0}  -- collection of arrays with value objects
doAppend = true
-- if we need to return a single value, check if we don't have one already
local function walk(formatTable)
if self.singleValue then
local miss
if not rankPos or rankPos == 1 then
numValues = #self.outPreferred
elseif rankPos == 2 then
numValues = #self.outNormal
elseif rankPos == 3 then
numValues = #self.outDeprecated
end
if numValues > 0 then
for i2, v2 in pairs(formatTable.req) do
doAppend = false
-- call a hook, adding its return value to the result
end
miss = self:callHook(i2, hooks, v, result)
end
if doAppend then
local function walk(formatTable)
local miss
for i2, v2 in pairs(formatTable.req) do
if miss then
-- call a hook, adding its return value to the result
-- we miss a required value for this level, so return false
miss = self:callHook(i2, hooks, v, result)
return false
if miss then
-- we miss a required value for this level, so return false
return false
end
if result.count == hooks.count then
-- we're done if all hooks have been called;
-- returning at this point breaks the loop
return true
end
end
end
for i2, v2 in ipairs(formatTable) do
if result.count == hooks.count then
if result.count == hooks.count then
-- we're done if all hooks have been called;
-- we're done if all hooks have been called;
-- returning at this point breaks the loop
-- returning at this point prevents further childs from being processed
return true
return true
end
end
end
if v2.child then
for i2, v2 in ipairs(formatTable) do
walk(v2.child)
if result.count == hooks.count then
end
-- we're done if all hooks have been called;
-- returning at this point prevents further childs from being processed
return true
end
end
return true
if v2.child then
walk(v2.child)
end
end
end
gotRequired = walk(self.parsedFormat)
-- only append the result if we got values for all required parameters on the root level
return true
if gotRequired then
end
done = self:appendOutput(result, rankPos)
gotRequired = walk(self.parsedFormat)
if done then
break
-- only append the result if we got values for all required parameters on the root level
end
if gotRequired then
-- if we have a rankPos (only with matchHook() for complete claims), then update the foundRank
if rankPos and self.conf.foundRank > rankPos then
self.conf.foundRank = rankPos
end
-- append the result
self.results[#self.results + 1] = result
-- break if we only need a single value
if self.singleValue then
break
end
end
end
end
1,776行目: 1,700行目:
if _.entity and _.entity.claims then claims = _.entity.claims[_.propertyID] end
if _.entity and _.entity.claims then claims = _.entity.claims[_.propertyID] end
if claims then
if claims then
-- first sort the claims on ranks for better performance
-- first sort the claims on rank to pre-define the order of output (preferred first, then normal, then deprecated)
claims = sortOnRank(claims)
claims = sortOnRank(claims)
匿名利用者