Simplifie le calcul des variables manquantes (4)

pull/197/head
Laurent Bossavit 2018-04-10 14:13:37 +02:00
parent b6ca3fb0eb
commit 6ff8488265
3 changed files with 38 additions and 81 deletions

View File

@ -17,18 +17,16 @@ export let makeJsx = node =>
? node.jsx(node.nodeValue, node.explanation)
: node.jsx
export let collectNodeMissing = node =>
node.missingVariables ||
(node.collectMissing ? node.collectMissing(node) : [])
export let collectNodeMissing = node => node.missingVariables || []
export let evaluateNode = (cache, situationGate, parsedRules, node) =>
node.evaluate ? node.evaluate(cache, situationGate, parsedRules, node) : node
export let rewriteNode = (node, nodeValue, explanation, collectMissing = null) => ({
export let rewriteNode = (node, nodeValue, explanation, missingVariables) => ({
...node,
nodeValue,
explanation,
collectMissing
missingVariables
})
export let evaluateArray = (reducer, start) => (

View File

@ -153,14 +153,11 @@ let devariate = (recurse, k, v) => {
chain(collectNodeMissing, pluck('condition', explanation))
),
rightMissing = choice
? collectNodeMissing(choice)
? choice.missingVariables
: chain(collectNodeMissing, explanation),
missingVariables = concat(leftMissing, rightMissing)
missingVariables = concat(leftMissing, rightMissing || [])
return {
...rewriteNode(node, nodeValue, explanation),
missingVariables
}
return rewriteNode(node, nodeValue, explanation, missingVariables)
}
// TODO - find an appropriate representation
@ -224,10 +221,7 @@ export let mecanismOneOf = (recurse, k, v) => {
: any(equals(null), values) ? null : false,
missingVariables = nodeValue == null ? chain(collectNodeMissing, explanation) : []
return {
...rewriteNode(node, nodeValue, explanation),
missingVariables
}
return rewriteNode(node, nodeValue, explanation, missingVariables)
}
return {
@ -270,10 +264,7 @@ export let mecanismAllOf = (recurse, k, v) => {
: any(equals(null), values) ? null : true,
missingVariables = nodeValue == null ? chain(collectNodeMissing, explanation) : []
return {
...rewriteNode(node, nodeValue, explanation),
missingVariables
}
return rewriteNode(node, nodeValue, explanation, missingVariables)
}
return {
@ -313,12 +304,12 @@ export let mecanismNumericalSwitch = (recurse, k, v) => {
},
node.explanation
),
missingOnTheLeft = collectNodeMissing(explanation.condition),
missingOnTheLeft = explanation.condition.missingVariables,
investigate = explanation.condition.nodeValue !== false,
missingOnTheRight = investigate
? collectNodeMissing(explanation.consequence)
? explanation.consequence.missingVariables
: [],
missingVariables = concat(missingOnTheLeft, missingOnTheRight)
missingVariables = concat(missingOnTheLeft || [], missingOnTheRight || [])
return {
...node,
@ -364,13 +355,10 @@ export let mecanismNumericalSwitch = (recurse, k, v) => {
getFirst('nodeValue'),
choice = find(node => node.condValue, explanation),
missingVariables = choice
? collectNodeMissing(choice)
? choice.missingVariables
: chain(collectNodeMissing, explanation)
return {
...rewriteNode(node, nodeValue, explanation),
missingVariables
}
return rewriteNode(node, nodeValue, explanation, missingVariables)
}
let explanation = map(parseCondition, terms)
@ -492,10 +480,7 @@ export let mecanismInversion = dottedName => (recurse, k, v) => {
nodeValue = inversion.nodeValue,
missingVariables = inversion.inversionMissingVariables
let evaluatedNode = {
...rewriteNode(node, nodeValue, null),
missingVariables
}
let evaluatedNode = rewriteNode(node, nodeValue, null, missingVariables)
// rewrite the simulation cache with the definitive inversion values
toPairs(inversion.inversionCache).map(([k, v]) => (cache[k] = v))
@ -966,12 +951,9 @@ export let mecanismSelection = (recurse, k, v) => {
? Number.parseFloat(last(sortedSubValues)[1]) / 100
: 0
: null,
missingVariables = collectNodeMissing(explanation)
missingVariables = explanation.missingVariables
return {
...rewriteNode(node, nodeValue, explanation),
missingVariables
}
return rewriteNode(node, nodeValue, explanation, missingVariables)
}
let SelectionView = buildSelectionView(dataTargetName)

View File

@ -55,14 +55,12 @@ import {
import {
evaluateNode,
rewriteNode,
collectNodeMissing,
makeJsx
} from './evaluation'
import {
anyNull,
val,
undefOrTrue,
applyOrEmpty
undefOrTrue
} from './traverse-common-functions'
let nearley = () => new Parser(Grammar.ParserRules, Grammar.ParserStart)
@ -154,16 +152,13 @@ let fillVariableNode = (rules, rule, filter) => parseResult => {
missingVariables = nodeValue != null // notamment si situationValue != null
? []
: variableIsCalculable
? collectNodeMissing(parsedRule)
? parsedRule.missingVariables
: [dottedName]
if (cached) {
return cached
} else {
cache[cacheName] = {
...rewriteNode(node, nodeValue, explanation),
missingVariables
}
cache[cacheName] = rewriteNode(node, nodeValue, explanation, missingVariables)
return cache[cacheName]
}
}
@ -203,10 +198,7 @@ let buildNegatedVariable = variable => {
nodeValue = explanation.nodeValue == null ? null : !explanation.nodeValue,
missingVariables = explanation.missingVariables
return {
...rewriteNode(node, nodeValue, explanation),
missingVariables
}
return rewriteNode(node, nodeValue, explanation, missingVariables)
}
let jsx = (nodeValue, explanation) => (
@ -310,13 +302,11 @@ let treat = (rules, rule) => rawNode => {
value1 == null || value2 == null
? null
: operatorFunction(value1, value2),
missingVariables = chain(collectNodeMissing, explanation)
missingVariables = concat(
explanation[0].missingVariables || [],
explanation[1].missingVariables || [])
return {
...rewriteNode(node, nodeValue, explanation),
missingVariables
}
return rewriteNode(node, nodeValue, explanation, missingVariables)
}
let fillFiltered = parseResult =>
@ -457,7 +447,7 @@ export let treatRuleRoot = (rules, rule) => {
Ces mécanismes variables sont descendues à leur tour grâce à `treat()`.
Lors de ce traitement, des fonctions 'evaluate' et `jsx` sont attachés aux objets de l'AST
*/
let evaluate = (cache, situationGate, parsedRules, r) => {
let evaluate = (cache, situationGate, parsedRules, node) => {
let evolveRule = curry(evaluateNode)(cache, situationGate, parsedRules),
evaluated = evolve(
{
@ -465,7 +455,7 @@ export let treatRuleRoot = (rules, rule) => {
'non applicable si': evolveRule,
'applicable si': evolveRule
},
r
node
),
formuleValue = val(evaluated['formule']),
isApplicable = do {
@ -481,32 +471,26 @@ export let treatRuleRoot = (rules, rule) => {
},
nodeValue = computeRuleValue(formuleValue, isApplicable)
return { ...evaluated, nodeValue, isApplicable }
}
let collectMissing = rule => {
let {
formule,
isApplicable,
'non applicable si': notApplicable,
'applicable si': applicable
} = rule
} = evaluated
let condMissing =
val(notApplicable) === true
? []
: val(applicable) === false
? []
: [
...applyOrEmpty(collectNodeMissing)(notApplicable),
...applyOrEmpty(collectNodeMissing)(applicable)
],
: concat(
(notApplicable && notApplicable.missingVariables) || [],
(applicable && applicable.missingVariables) || []
),
collectInFormule = isApplicable !== false,
formMissing = applyOrEmpty(() =>
applyOrEmpty(collectNodeMissing)(formule)
)(collectInFormule)
formMissing = (collectInFormule && formule.missingVariables) || [],
missingVariables = concat(condMissing, formMissing)
return concat(condMissing, formMissing)
return { ...evaluated, nodeValue, isApplicable, missingVariables }
}
let parsedRoot = evolve({
@ -525,12 +509,9 @@ export let treatRuleRoot = (rules, rule) => {
node.explanation
),
nodeValue = explanation.nodeValue,
missingVariables = collectNodeMissing(explanation)
missingVariables = explanation.missingVariables
return {
...rewriteNode(node, nodeValue, explanation),
missingVariables
}
return rewriteNode(node, nodeValue, explanation, missingVariables)
}
let child = treat(rules, rule)(value)
@ -553,7 +534,6 @@ export let treatRuleRoot = (rules, rule) => {
// Pas de propriété explanation et jsx ici car on est parti du (mauvais) principe que 'non applicable si' et 'formule' sont particuliers, alors qu'ils pourraient être rangé avec les autres mécanismes
...parsedRoot,
evaluate,
collectMissing,
parsed: true
}
}
@ -567,12 +547,9 @@ let evolveCond = (name, rule, rules) => value => {
node.explanation
),
nodeValue = explanation.nodeValue,
missingVariables = collectNodeMissing(explanation)
missingVariables = explanation.missingVariables
return {
...rewriteNode(node, nodeValue, explanation),
missingVariables
}
return rewriteNode(node, nodeValue, explanation, missingVariables)
}
let child = treat(rules, rule)(value)