Skip to main content

Optimisations

Constant folding

Attention

Cette optimisation est encore expérimentale et contient encore des bugs mais également une marge d'amélioration importante. N'hésitez pas à nous faire des retours sur les problèmes rencontrés sur le dépôt @publicodes/tools.

Motivation

Les modèles de calculs écrits en Publicodes sont par design implémentés pour être le plus transparent et intelligible possible pour le plus grand nombre. Cela implique de détailler au maximum les calculs, ce qui peut conduire à une complexité importante des modèles. Cependant, cette complexité n'est justifiée que pour la documentation et non pour le calcul en lui-même.

Par exemple, considérons les règles suivantes :

nosgestesclimat/data/alimentation/déchets.publicodes
alimentation . déchets . gestes . bonus compostage biodéchets:
formule:
somme:
- omr . putrescibles . réduction compost
- (-1) * omr . putrescibles . compostés
unité: kgCO2e

alimentation . déchets . omr . putrescibles . réduction compost:
formule: omr . putrescibles * (gisement réduction / quantité réelle)
unité: kgCO2e

La règle alimentation . déchets . omr . putrescibles . réduction compost dépends de 18 autres règles pour être calculée. Cependant, la valeur ne dépend pas de l'utilisateur·ice et pourrait être calculée à l'avance (c'est une constante). C'est l'objectif de l'optimisation par constant folding : calculer toutes les valeurs qui ne dépendent pas de l'utilisateur à l'avance et remplacer les règles directement par leur valeur.

Ainsi, après optimisation on obtient :

alimentation . déchets . gestes . bonus compostage biodéchets:
formule:
somme:
- 11.505999999999998
- (-0.4949999999999999)

Usage

tip

An API documentation is available in English here.

L'optimisation par constant folding est disponible dans le module @publicodes/tools/optims via la fonction constantFolding qui prend en paramètre :

  • un moteur Publicodes (instancié avec le jeu de règles à optimiser)
  • un prédicat qui prend en paramètre un couple (nom de la règle, noeud de la règle) et retourne true si la règle doit être conservée après optimisation
  • un objet de paramètres :
    • isFoldedAttr : le nom de l'attribut à utiliser pour marquer une règle comme optimisée (par défaut optimized)

Exemple

import Engine from 'publicodes'
import { constantFolding } from '@publicodes/tools/optims'

const optimizedRules = constantFolding(
// A publicode engine instantiated with the rules to optimize.
new Engine(baseRules),
{
// A predicate returning true if the rule needs to be kept.
toKeep: (rule) => {
return (
['root', 'root . bis'].includes(rule.dottedName) ||
!!rule.rawNode['to keep']
)
},
},
)
info

Nos Gestes Climat utilise cette optimisation pour réduire le temps d'instanciation du moteur dans le client :

  • voir le code source
  • voir la PR qui a permis de réduire le temps d'instanciation et d'évaluation de plus de 50%.