diff --git a/spec/nubtest.ts b/spec/nubtest.ts
index 5ed87f706f82a99ead44bb06a76fc33ac4d3bb5f..5d67bff3d328e84158093a72f4e42adbad5f8408 100644
--- a/spec/nubtest.ts
+++ b/spec/nubtest.ts
@@ -1,6 +1,6 @@
 import { Result } from "../src/util/result";
 import { Nub } from "../src/nub";
-import { ComputeNodeType, ParamCalculability, ParamDefinition, ParamDomainValue, ParamsEquation } from "../src/param";
+import { ParamCalculability, ParamDefinition, ParamDomainValue, ParamsEquation } from "../src/param";
 
 class NubTestParams extends ParamsEquation {
     private _A: ParamDefinition;
@@ -9,9 +9,9 @@ class NubTestParams extends ParamsEquation {
 
     constructor() {
         super();
-        this._A = new ParamDefinition(ComputeNodeType.Test, "A", ParamDomainValue.POS_NULL, 1);
-        this._B = new ParamDefinition(ComputeNodeType.Test, "B", ParamDomainValue.POS_NULL, 2);
-        this._C = new ParamDefinition(ComputeNodeType.Test, "C", ParamDomainValue.POS_NULL, 3);
+        this._A = new ParamDefinition(undefined, "A", ParamDomainValue.POS_NULL, 1);
+        this._B = new ParamDefinition(undefined, "B", ParamDomainValue.POS_NULL, 2);
+        this._C = new ParamDefinition(undefined, "C", ParamDomainValue.POS_NULL, 3);
 
         this.addParamDefinition(this._A);
         this.addParamDefinition(this._B);
diff --git a/src/cond_distri.ts b/src/cond_distri.ts
index e4ebdbfef33486495a1a2010d0dce0147e3b930f..caab5cfd6a0c33cace2860fd2310aab7bafceacd 100644
--- a/src/cond_distri.ts
+++ b/src/cond_distri.ts
@@ -1,5 +1,5 @@
 import { Result } from "./util/result";
-import { ComputeNodeType, ParamDefinition, ParamDomain, ParamDomainValue, ParamCalculability, ParamsEquation } from "./param";
+import { ParamDefinition, ParamDomainValue, ParamCalculability, ParamsEquation, CalculatorType } from "./param";
 import { Nub } from "./nub";
 
 /**
@@ -23,11 +23,11 @@ export class ConduiteDistribParams extends ParamsEquation {
 
     constructor(rQ: number, rD: number, rJ: number, rLg: number, rNu: number) {
         super();
-        this.Q = new ParamDefinition(ComputeNodeType.CondDistri, 'Q', ParamDomainValue.POS, rQ);
-        this.D = new ParamDefinition(ComputeNodeType.CondDistri, 'D', ParamDomainValue.POS, rD);
-        this.J = new ParamDefinition(ComputeNodeType.CondDistri, 'J', ParamDomainValue.POS, rJ);
-        this.Lg = new ParamDefinition(ComputeNodeType.CondDistri, 'Lg', ParamDomainValue.POS, rLg);
-        this.Nu = new ParamDefinition(ComputeNodeType.CondDistri, 'Nu', ParamDomainValue.POS, rNu);
+        this.Q = new ParamDefinition(CalculatorType.ConduiteDistributrice, 'Q', ParamDomainValue.POS, rQ);
+        this.D = new ParamDefinition(CalculatorType.ConduiteDistributrice, 'D', ParamDomainValue.POS, rD);
+        this.J = new ParamDefinition(CalculatorType.ConduiteDistributrice, 'J', ParamDomainValue.POS, rJ);
+        this.Lg = new ParamDefinition(CalculatorType.ConduiteDistributrice, 'Lg', ParamDomainValue.POS, rLg);
+        this.Nu = new ParamDefinition(CalculatorType.ConduiteDistributrice, 'Nu', ParamDomainValue.POS, rNu);
 
         this.addParamDefinition(this.Q);
         this.addParamDefinition(this.D);
diff --git a/src/lechaptcalmon.ts b/src/lechaptcalmon.ts
index 39dd48c82b57b2845bfca23463863ab4775ce63e..f42e59ddc94c0866a64b7136cf7826397943cee3 100644
--- a/src/lechaptcalmon.ts
+++ b/src/lechaptcalmon.ts
@@ -1,5 +1,5 @@
 import { Result } from "./util/result";
-import { ComputeNodeType, ParamDefinition, ParamDomain, ParamDomainValue, ParamCalculability, ParamsEquation } from "./param";
+import { ParamDefinition, ParamDomainValue, ParamCalculability, ParamsEquation, CalculatorType } from "./param";
 import { Nub } from "./nub";
 
 /**
@@ -29,13 +29,13 @@ export class LechaptCalmonParams extends ParamsEquation {
 
     constructor(rQ: number, rD: number, rJ: number, rLg: number, rL: number, rM: number, rN: number) {
         super();
-        this._Q = new ParamDefinition(ComputeNodeType.LechaptCalmon, 'Q', ParamDomainValue.POS, rQ);
-        this._D = new ParamDefinition(ComputeNodeType.LechaptCalmon, 'D', ParamDomainValue.POS, rD);
-        this._J = new ParamDefinition(ComputeNodeType.LechaptCalmon, 'J', ParamDomainValue.POS, rJ);
-        this._Lg = new ParamDefinition(ComputeNodeType.LechaptCalmon, 'Lg', ParamDomainValue.POS, rLg);
-        this._L = new ParamDefinition(ComputeNodeType.LechaptCalmon, 'L', ParamDomainValue.POS, rL);
-        this._M = new ParamDefinition(ComputeNodeType.LechaptCalmon, 'M', ParamDomainValue.POS, rM);
-        this._N = new ParamDefinition(ComputeNodeType.LechaptCalmon, 'N', ParamDomainValue.POS, rN);
+        this._Q = new ParamDefinition(CalculatorType.LechaptCalmon, 'Q', ParamDomainValue.POS, rQ);
+        this._D = new ParamDefinition(CalculatorType.LechaptCalmon, 'D', ParamDomainValue.POS, rD);
+        this._J = new ParamDefinition(CalculatorType.LechaptCalmon, 'J', ParamDomainValue.POS, rJ);
+        this._Lg = new ParamDefinition(CalculatorType.LechaptCalmon, 'Lg', ParamDomainValue.POS, rLg);
+        this._L = new ParamDefinition(CalculatorType.LechaptCalmon, 'L', ParamDomainValue.POS, rL);
+        this._M = new ParamDefinition(CalculatorType.LechaptCalmon, 'M', ParamDomainValue.POS, rM);
+        this._N = new ParamDefinition(CalculatorType.LechaptCalmon, 'N', ParamDomainValue.POS, rN);
 
         this.addParamDefinition(this._Q);
         this.addParamDefinition(this._D);
diff --git a/src/pab/pab_dimension.ts b/src/pab/pab_dimension.ts
index 5c84d9fea338d98e12d7a6d180efa30d64ce7800..4a7dd26392bc7ca9bcdbf378d3dc992a73f20242 100644
--- a/src/pab/pab_dimension.ts
+++ b/src/pab/pab_dimension.ts
@@ -1,6 +1,5 @@
 import { Result } from "../util/result";
-import { ComputeNodeType, ParamDefinition, ParamDomain, ParamDomainValue, ParamCalculability, ParamsEquation } from "../param";
-import { NumericalString } from "../util/numericalstring";
+import { ParamDefinition, ParamDomainValue, ParamCalculability, ParamsEquation, CalculatorType } from "../param";
 import { Nub } from "../nub";
 
 export class PabDimensionParams extends ParamsEquation {
@@ -20,10 +19,10 @@ export class PabDimensionParams extends ParamsEquation {
 
     constructor(rL: number, rW: number, rY: number, rV: number = undefined) {
         super();
-        this._L = new ParamDefinition(ComputeNodeType.PabDimensions, 'L', ParamDomainValue.POS, rL);
-        this._W = new ParamDefinition(ComputeNodeType.PabDimensions, 'W', ParamDomainValue.POS, rW);
-        this._Y = new ParamDefinition(ComputeNodeType.PabDimensions, 'Y', ParamDomainValue.POS, rY);
-        this._V = new ParamDefinition(ComputeNodeType.PabDimensions, 'V', ParamDomainValue.POS, rV);
+        this._L = new ParamDefinition(CalculatorType.PabDimensions, 'L', ParamDomainValue.POS, rL);
+        this._W = new ParamDefinition(CalculatorType.PabDimensions, 'W', ParamDomainValue.POS, rW);
+        this._Y = new ParamDefinition(CalculatorType.PabDimensions, 'Y', ParamDomainValue.POS, rY);
+        this._V = new ParamDefinition(CalculatorType.PabDimensions, 'V', ParamDomainValue.POS, rV);
 
         this.addParamDefinition(this._L);
         this.addParamDefinition(this._W);
diff --git a/src/pab/pab_puissance.ts b/src/pab/pab_puissance.ts
index df65b5086619ca734b95f790505ccbe2468dc19e..a37e256df48287772d9c349fe84c21f57ee83036 100644
--- a/src/pab/pab_puissance.ts
+++ b/src/pab/pab_puissance.ts
@@ -1,6 +1,5 @@
 import { Result } from "../util/result";
-import { ComputeNodeType, ParamDefinition, ParamDomain, ParamDomainValue, ParamCalculability, ParamsEquation } from "../param";
-import { NumericalString } from "../util/numericalstring";
+import { ParamDefinition, ParamDomainValue, ParamCalculability, ParamsEquation, CalculatorType } from "../param";
 import { Nub } from "../nub";
 
 export class PabPuissanceParams extends ParamsEquation {
@@ -20,10 +19,10 @@ export class PabPuissanceParams extends ParamsEquation {
 
     constructor(rDH: number, rQ: number, rV: number, rPV: number = undefined) {
         super();
-        this._DH = new ParamDefinition(ComputeNodeType.PabPuissance, 'DH', ParamDomainValue.POS, rDH);
-        this._Q = new ParamDefinition(ComputeNodeType.PabPuissance, 'Q', ParamDomainValue.POS, rQ);
-        this._V = new ParamDefinition(ComputeNodeType.PabPuissance, 'V', ParamDomainValue.POS, rV);
-        this._Pv = new ParamDefinition(ComputeNodeType.PabPuissance, 'Pv', ParamDomainValue.POS, rPV);
+        this._DH = new ParamDefinition(CalculatorType.PabPuissance, 'DH', ParamDomainValue.POS, rDH);
+        this._Q = new ParamDefinition(CalculatorType.PabPuissance, 'Q', ParamDomainValue.POS, rQ);
+        this._V = new ParamDefinition(CalculatorType.PabPuissance, 'V', ParamDomainValue.POS, rV);
+        this._Pv = new ParamDefinition(CalculatorType.PabPuissance, 'Pv', ParamDomainValue.POS, rPV);
 
         this.addParamDefinition(this._DH);
         this.addParamDefinition(this._Q);
diff --git a/src/param.ts b/src/param.ts
index 77a641c1fa70aa771cfdc1990efbd4b8be9e866e..f1897697cca6cafb62ab9d06809c5180aa50fb4b 100644
--- a/src/param.ts
+++ b/src/param.ts
@@ -1,4 +1,3 @@
-// import { Debug, UndefinedError } from './base';
 import { Debug } from "./base";
 import { DefinedNumber } from "./util/definedvalue";
 import { Interval } from "./util/interval";
@@ -291,6 +290,11 @@ export class ParamDefinition extends BaseParam {
      */
     private _calc: ParamCalculability;
 
+    /**
+     * calculette parente
+     */
+    private _calculatorType: CalculatorType;
+
     /**
      * noeud de calcul parent
      */
@@ -299,8 +303,9 @@ export class ParamDefinition extends BaseParam {
     // private static _idGen: number = 0; // A VIRER
     // private _id: number; // A VIRER
 
-    constructor(nt: ComputeNodeType, s: string, d: ParamDomain | ParamDomainValue, val: number = undefined) {
+    constructor(ct: CalculatorType, s: string, d: ParamDomain | ParamDomainValue, val?: number, nt: ComputeNodeType = ComputeNodeType.None) {
         super(s, d, val);
+        this._calculatorType = ct;
         this._computeNodeType = nt;
 
         this._calc = undefined;
@@ -358,9 +363,8 @@ export class ParamDefinition extends BaseParam {
     }
 
     public clone(): ParamDefinition {
-        const res = new ParamDefinition(this._computeNodeType, this.symbol, this.getDomain().clone());
+        const res = new ParamDefinition(this._calculatorType, this.symbol, this.getDomain().clone(), this.uncheckedValue, this._computeNodeType);
         res._calc = this._calc;
-        res.value = this.uncheckedValue;
         return res;
     }
 }
@@ -444,20 +448,26 @@ export abstract class ParamsEquation implements Iterable<ParamDefinition> {
     }
 }
 
+/** 
+ * type de calculette
+ */
+export enum CalculatorType {
+    ConduiteDistributrice, LechaptCalmon, SectionParametree, RegimeUniforme, CourbeRemous,
+    PabDimensions, // passe à bassin rectangulaire
+    PabPuissance, // passe à bassin : puissance dissipée
+    Structure,  // ouvrages hydrauliques simples
+    ParallelStructure  // ouvrages hydrauliques en parallèle
+}
+
 /**
- * type de noeud de calcul
+ * type de noeud de calcul (sous type de calculette)
  */
 export enum ComputeNodeType {
-    CondDistri, LechaptCalmon,
-    SectionParametree, // paramètres communs à toutes les sections paramétrées
+    None,
+    // types de sections
     SectionTrapeze, SectionRectangle, SectionCercle, SectionPuissance,
-    RegimeUniforme, // paramètres communs à toutes les sections paramétrées
-    RegimeUniformeTrapeze, RegimeUniformeRectangle, RegimeUniformeCercle, RegimeUniformePuissance,
-    CourbeRemous, // paramètres communs à toutes les courbes de remous
-    CourbeRemousTrapeze, CourbeRemousRectangle, CourbeRemousCercle, CourbeRemousPuissance,
-    PabDimensions, // passe à bassin rectangulaire
-    PabPuissance, // passe à bassin : énergie dissipée
-    Test
+    // types d'ouvrages hydrauliques
+    StructureRectangle,
 }
 
 /**
diff --git a/src/parameters.ts b/src/parameters.ts
index d9db821236a22a1478d26dbefdd5b33d46fe696a..feb4081e49b4cb47cae88fc673f9cf06d1094c61 100644
--- a/src/parameters.ts
+++ b/src/parameters.ts
@@ -1,7 +1,7 @@
-import { ComputeNodeType, ParamsEquation } from "./param";
+import { ComputeNodeType, ParamsEquation, CalculatorType, ParamDefinition } from "./param";
 import { ConduiteDistribParams, ConduiteDistrib } from "./cond_distri";
 import { LechaptCalmonParams, LechaptCalmon } from "./lechaptcalmon";
-import { ParamsSection, acSection } from "./section/section_type";
+import { acSection } from "./section/section_type";
 import { ParamsSectionTrapez, cSnTrapez } from "./section/section_trapez";
 import { ParamsSectionRectang, cSnRectang } from "./section/section_rectang";
 import { ParamsSectionCirc, cSnCirc } from "./section/section_circulaire";
@@ -10,11 +10,17 @@ import { RegimeUniforme } from "./regime_uniforme";
 import { CourbeRemous, CourbeRemousParams } from "./remous";
 import { PabDimensionParams, PabDimension } from "./pab/pab_dimension";
 import { PabPuissanceParams, PabPuissance } from "./pab/pab_puissance";
+import { HashTable } from "./util/hashtable";
+
 
 export class ComputeNodeParameters {
     private static _instance: ComputeNodeParameters;
 
-    private constructor() { }
+    private _nodes: HashTable;
+
+    private constructor() {
+        this._nodes = new HashTable();
+    }
 
     public static getInstance() {
         if (ComputeNodeParameters._instance == undefined)
@@ -22,152 +28,90 @@ export class ComputeNodeParameters {
         return ComputeNodeParameters._instance;
     }
 
-    public getComputeNodeParameters(type: ComputeNodeType): ParamsEquation {
-        switch (type) {
-            case ComputeNodeType.CondDistri:
-                {
-                    let cn = new ConduiteDistribParams(undefined, undefined, undefined, undefined, undefined);
-                    let n = new ConduiteDistrib(cn); // pour initialiser la calculabilité des paramètres
-                    return cn;
-                }
-
-            case ComputeNodeType.LechaptCalmon:
-                {
-                    let cn = new LechaptCalmonParams(undefined, undefined, undefined, undefined, undefined, undefined, undefined);
-                    let n = new LechaptCalmon(cn); // pour initialiser la calculabilité des paramètres
-                    return cn;
-                }
-
+    private createSection(nt: ComputeNodeType): acSection {
+        switch (nt) {
+            case ComputeNodeType.None: // pour les paramètres communs, n'importe quelle section convient
             case ComputeNodeType.SectionTrapeze:
                 {
-                    let cn = new ParamsSectionTrapez(undefined, undefined, undefined, undefined,
-                        undefined, undefined, undefined, undefined, undefined, undefined);
+                    let cn = new ParamsSectionTrapez(1, 0.5, undefined, undefined,
+                        1, undefined, 0.1, 1);
                     let n = new cSnTrapez(cn); // pour initialiser la calculabilité des paramètres
-                    return cn;
+                    return n;
                 }
 
             case ComputeNodeType.SectionRectangle:
                 {
-                    let cn = new ParamsSectionRectang(undefined, undefined, undefined, undefined,
-                        undefined, undefined, undefined, undefined);
+                    let cn = new ParamsSectionRectang(undefined, 1, undefined, 1,
+                        undefined, 0.1, 1);
                     let n = new cSnRectang(cn); // pour initialiser la calculabilité des paramètres
-                    return cn;
+                    return n;
                 }
 
             case ComputeNodeType.SectionCercle:
                 {
-                    let cn = new ParamsSectionCirc(undefined, undefined, undefined, undefined,
-                        undefined, undefined, undefined, undefined, undefined);
+                    let cn = new ParamsSectionCirc(1, undefined, undefined, 1,
+                        undefined, 0.1, 1);
                     let n = new cSnCirc(cn); // pour initialiser la calculabilité des paramètres
-                    return cn;
+                    return n;
                 }
 
             case ComputeNodeType.SectionPuissance:
                 {
-                    let cn = new ParamsSectionPuiss(undefined, undefined, undefined, undefined,
-                        undefined, undefined, undefined, undefined, undefined, undefined);
+                    let cn = new ParamsSectionPuiss(0.5, undefined, 1, undefined,
+                        1, undefined, 0.1, 1);
                     let n = new cSnPuiss(cn); // pour initialiser la calculabilité des paramètres
-                    return cn;
+                    return n;
                 }
 
-            case ComputeNodeType.RegimeUniformeTrapeze:
-                {
-                    let cn = new ParamsSectionTrapez(undefined, undefined, undefined,
-                        undefined, undefined, undefined, undefined, undefined,
-                        ComputeNodeType.RegimeUniformeTrapeze,
-                        ComputeNodeType.RegimeUniforme);
-                    let n = new cSnTrapez(cn);
-                    let ru = new RegimeUniforme(n); // pour initialiser la calculabilité des paramètres
-                    return cn;
-                }
+            default:
+                throw new Error(`type de section ${ComputeNodeType[nt]} non pris en charge`);
+        }
+    }
 
-            case ComputeNodeType.RegimeUniformeRectangle:
+    private createComputeNodeParameters(calcType: CalculatorType, nodeType: ComputeNodeType): ParamsEquation {
+        switch (calcType) {
+            case CalculatorType.ConduiteDistributrice:
                 {
-                    let cn = new ParamsSectionRectang(undefined, undefined, undefined,
-                        undefined, undefined, undefined, undefined,
-                        ComputeNodeType.RegimeUniforme);
-                    let n = new cSnRectang(cn);
-                    let ru = new RegimeUniforme(n); // pour initialiser la calculabilité des paramètres
+                    const cn = new ConduiteDistribParams(undefined, undefined, undefined, undefined, undefined);
+                    const n = new ConduiteDistrib(cn); // pour initialiser la calculabilité des paramètres
                     return cn;
                 }
 
-            case ComputeNodeType.RegimeUniformeCercle:
+            case CalculatorType.LechaptCalmon:
                 {
-                    let cn = new ParamsSectionCirc(undefined, undefined, undefined,
-                        undefined, undefined, undefined, undefined,
-                        ComputeNodeType.RegimeUniformeCercle,
-                        ComputeNodeType.RegimeUniforme);
-                    let n = new cSnCirc(cn);
-                    let ru = new RegimeUniforme(n); // pour initialiser la calculabilité des paramètres
+                    const cn = new LechaptCalmonParams(undefined, undefined, undefined, undefined, undefined, undefined, undefined);
+                    const n = new LechaptCalmon(cn); // pour initialiser la calculabilité des paramètres
                     return cn;
                 }
 
-            case ComputeNodeType.RegimeUniformePuissance:
+            case CalculatorType.SectionParametree:
                 {
-                    let cn = new ParamsSectionPuiss(undefined, undefined, undefined,
-                        undefined, undefined, undefined, undefined, undefined,
-                        ComputeNodeType.RegimeUniformePuissance,
-                        ComputeNodeType.RegimeUniforme);
-                    let n = new cSnPuiss(cn);
-                    let ru = new RegimeUniforme(n); // pour initialiser la calculabilité des paramètres
-                    return cn;
+                    const sect: acSection = this.createSection(nodeType);
+                    return sect.prms;
                 }
 
-            case ComputeNodeType.CourbeRemousCercle:
-                {
-                    let cn = new ParamsSectionCirc(1, undefined, undefined, 1, undefined,
-                        0.001, 1,
-                        ComputeNodeType.CourbeRemousCercle,
-                        ComputeNodeType.CourbeRemous);
-                    let n = new cSnCirc(cn);
-                    let crp = new CourbeRemousParams(n, undefined, undefined, undefined, undefined, undefined);
-                    let ru = new CourbeRemous(crp); // pour initialiser la calculabilité des paramètres
-                    return crp
-                }
+            case CalculatorType.RegimeUniforme:
+                const sect: acSection = this.createSection(nodeType);
+                const ru = new RegimeUniforme(sect); // pour initialiser la calculabilité des paramètres
+                return sect.prms;
 
-            case ComputeNodeType.CourbeRemousPuissance:
-                {
-                    let cn = new ParamsSectionPuiss(1, undefined, 1, undefined, 1,
-                        undefined, 0.001, 1,
-                        ComputeNodeType.CourbeRemousPuissance,
-                        ComputeNodeType.CourbeRemous);
-                    let n = new cSnPuiss(cn);
-                    let crp = new CourbeRemousParams(n, undefined, undefined, undefined, undefined, undefined);
-                    let ru = new CourbeRemous(crp); // pour initialiser la calculabilité des paramètres
-                    return crp;
-                }
 
-            case ComputeNodeType.CourbeRemousRectangle:
+            case CalculatorType.CourbeRemous:
                 {
-                    let cn = new ParamsSectionRectang(undefined, 1, undefined, 1, undefined,
-                        0.001, 1,
-                        ComputeNodeType.CourbeRemous);
-                    let n = new cSnRectang(cn);
-                    let crp = new CourbeRemousParams(n, undefined, undefined, undefined, undefined, undefined);
-                    let ru = new CourbeRemous(crp); // pour initialiser la calculabilité des paramètres
+                    const sect: acSection = this.createSection(nodeType);
+                    const crp = new CourbeRemousParams(sect, undefined, undefined, undefined, undefined, undefined);
+                    const ru = new CourbeRemous(crp); // pour initialiser la calculabilité des paramètres
                     return crp;
                 }
 
-            case ComputeNodeType.CourbeRemousTrapeze:
-                {
-                    let cn = new ParamsSectionTrapez(1, 1, undefined, undefined, 1,
-                        undefined, 0.001, 1,
-                        ComputeNodeType.CourbeRemousTrapeze,
-                        ComputeNodeType.CourbeRemous);
-                    let n = new cSnTrapez(cn);
-                    let crp = new CourbeRemousParams(n, undefined, undefined, undefined, undefined, undefined);
-                    let ru = new CourbeRemous(crp); // pour initialiser la calculabilité des paramètres
-                    return crp;
-                }
-
-            case ComputeNodeType.PabDimensions:
+            case CalculatorType.PabDimensions:
                 {
                     let cn = new PabDimensionParams(undefined, undefined, undefined);
                     let n = new PabDimension(cn); // pour initialiser la calculabilité des paramètres
                     return cn;
                 }
 
-            case ComputeNodeType.PabPuissance:
+            case CalculatorType.PabPuissance:
                 {
                     let cn = new PabPuissanceParams(undefined, undefined, undefined);
                     let n = new PabPuissance(cn); // pour initialiser la calculabilité des paramètres
@@ -175,7 +119,18 @@ export class ComputeNodeParameters {
                 }
 
             default:
-                throw "ComputeNodeParameters.getComputeNodeParameters() : noeud de calcul '" + ComputeNodeType[type] + "' non pris en charge";
+                throw "ComputeNodeParameters.getComputeNodeParameters() : noeud de calcul '" + ComputeNodeType[nodeType] + "' non pris en charge";
         }
     }
+
+    public getComputeNodeParameter(calcType: CalculatorType, nodeType: ComputeNodeType, symbol: string): ParamDefinition {
+        const key = { calcType, nodeType };
+        let params = this._nodes.get(key);
+        if (params == undefined) {
+            params = this.createComputeNodeParameters(calcType, nodeType);
+            this._nodes.put(key, params);
+        }
+
+        return params.map[symbol];
+    }
 }
diff --git a/src/remous.ts b/src/remous.ts
index 69e51b9635d28c5e34d13e2557bb65827f968fe4..53704c8f136cf381d23b0feab2521dc8e6d9a15b 100644
--- a/src/remous.ts
+++ b/src/remous.ts
@@ -1,7 +1,7 @@
 import { round, XOR } from "./base";
 import { Dichotomie } from "./dichotomie";
 import { Nub } from "./nub";
-import { ComputeNodeType, ParamCalculability, ParamDefinition, ParamDomainValue, ParamsEquation } from "./param";
+import { ComputeNodeType, ParamCalculability, ParamDefinition, ParamDomainValue, ParamsEquation, CalculatorType } from "./param";
 import { acSection, ParamsSection } from "./section/section_type";
 import { cLog } from "./util/log";
 import { Message, MessageCode } from "./util/message";
@@ -55,10 +55,10 @@ export class CourbeRemousParams extends ParamsEquation {
     constructor(s: acSection, rYamont: number, rYAval: number, rLong: number, rDx: number, meth: MethodeResolution) {
         super();
         this._section = s;
-        this._Yamont = new ParamDefinition(ComputeNodeType.CourbeRemous, "Yamont", ParamDomainValue.POS, rYamont);
-        this._Yaval = new ParamDefinition(ComputeNodeType.CourbeRemous, "Yaval", ParamDomainValue.POS, rYAval);
-        this._Long = new ParamDefinition(ComputeNodeType.CourbeRemous, "Long", ParamDomainValue.POS, rLong);
-        this._Dx = new ParamDefinition(ComputeNodeType.CourbeRemous, "Dx", ParamDomainValue.POS, rDx);
+        this._Yamont = new ParamDefinition(CalculatorType.CourbeRemous, "Yamont", ParamDomainValue.POS, rYamont);
+        this._Yaval = new ParamDefinition(CalculatorType.CourbeRemous, "Yaval", ParamDomainValue.POS, rYAval);
+        this._Long = new ParamDefinition(CalculatorType.CourbeRemous, "Long", ParamDomainValue.POS, rLong);
+        this._Dx = new ParamDefinition(CalculatorType.CourbeRemous, "Dx", ParamDomainValue.POS, rDx);
         this._methodeResolution = meth;
 
         this.addParamDefinition(this._Yamont);
diff --git a/src/section/section_circulaire.ts b/src/section/section_circulaire.ts
index 942dc121bace709f1c1c86fccb8877428e2a6398..874e42715d241190efd90f186eea692d006290fb 100644
--- a/src/section/section_circulaire.ts
+++ b/src/section/section_circulaire.ts
@@ -1,4 +1,4 @@
-import { ComputeNodeType, ParamDefinition, ParamDomainValue, ParamCalculability } from "../param";
+import { ComputeNodeType, ParamDefinition, ParamDomainValue, ParamCalculability, CalculatorType } from "../param";
 import { acSection, ParamsSection } from "./section_type";
 import { Message, MessageCode } from "../util/message";
 import { Result } from "../util/result";
@@ -7,11 +7,9 @@ import { randomBytes } from "crypto";
 export class ParamsSectionCirc extends ParamsSection {
         private _D: ParamDefinition;          // Diamètre du cercle
 
-        constructor(rD: number, rY: number, rKs: number, rQ: number, rIf: number, rPrec: number, rYB: number,
-                nodeType: ComputeNodeType = ComputeNodeType.SectionCercle,
-                defaultNodeType: ComputeNodeType = ComputeNodeType.SectionParametree) {
-                super(rY, undefined, rKs, rQ, rIf, rPrec, rYB, defaultNodeType);
-                this._D = new ParamDefinition(nodeType, 'D', ParamDomainValue.POS, rD);
+        constructor(rD: number, rY: number, rKs: number, rQ: number, rIf: number, rPrec: number, rYB: number) {
+                super(rY, undefined, rKs, rQ, rIf, rPrec, rYB, ComputeNodeType.None);
+                this._D = new ParamDefinition(CalculatorType.SectionParametree, 'D', ParamDomainValue.POS, rD, ComputeNodeType.SectionCercle);
 
                 this.addParamDefinition(this._D);
         }
diff --git a/src/section/section_puissance.ts b/src/section/section_puissance.ts
index 5179b9db26c148a4ab8e4ec3841925bffe6bf1c4..4c894eaf30342df6543324e3690a20b567032c91 100644
--- a/src/section/section_puissance.ts
+++ b/src/section/section_puissance.ts
@@ -1,4 +1,4 @@
-import { ComputeNodeType, ParamDefinition, ParamDomain, ParamDomainValue, ParamCalculability } from "../param";
+import { ComputeNodeType, ParamDefinition, ParamDomain, ParamDomainValue, ParamCalculability, CalculatorType } from "../param";
 import { acSection, ParamsSection } from "./section_type";
 import { Result } from "../util/result";
 
@@ -8,11 +8,9 @@ import { Result } from "../util/result";
 export class ParamsSectionPuiss extends ParamsSection {
         private _k: ParamDefinition; // Coefficient de forme compris entre 0 et 1
 
-        constructor(rk: number, rY: number, rLargeurBerge: number, rKs: number, rQ: number, rIf: number, rPrec: number, rYB: number,
-                nodeType: ComputeNodeType = ComputeNodeType.SectionPuissance,
-                defaultNodeType: ComputeNodeType = ComputeNodeType.SectionParametree) {
-                super(rY, rLargeurBerge, rKs, rQ, rIf, rPrec, rYB, defaultNodeType);
-                this._k = new ParamDefinition(nodeType, 'k', new ParamDomain(ParamDomainValue.INTERVAL, 0, 1), rk);
+        constructor(rk: number, rY: number, rLargeurBerge: number, rKs: number, rQ: number, rIf: number, rPrec: number, rYB: number) {
+                super(rY, rLargeurBerge, rKs, rQ, rIf, rPrec, rYB, ComputeNodeType.None);
+                this._k = new ParamDefinition(CalculatorType.SectionParametree, 'k', new ParamDomain(ParamDomainValue.INTERVAL, 0, 1), rk, ComputeNodeType.SectionPuissance);
 
                 this.addParamDefinition(this._k);
         }
diff --git a/src/section/section_rectang.ts b/src/section/section_rectang.ts
index b566b23b545b0aadcef8716fd4d9bda6c7d4076c..c29befdd995cdb13873924e27952417e32f9f433 100644
--- a/src/section/section_rectang.ts
+++ b/src/section/section_rectang.ts
@@ -3,11 +3,10 @@ import { ComputeNodeType } from "../param";
 import { Result } from "../util/result";
 
 export class ParamsSectionRectang extends ParamsSection {
-        constructor(rY: number, rLargeurFond: number, rKs: number, rQ: number, rIf: number, rPrec: number, rYB: number,
-                defaultNodeType: ComputeNodeType = ComputeNodeType.SectionParametree) {
+        constructor(rY: number, rLargeurFond: number, rKs: number, rQ: number, rIf: number, rPrec: number, rYB: number) {
                 super(rY,
                         rLargeurFond, // LargeurBerge=LargeurFond
-                        rKs, rQ, rIf, rPrec, rYB, defaultNodeType);
+                        rKs, rQ, rIf, rPrec, rYB, ComputeNodeType.SectionRectangle);
         }
 }
 
diff --git a/src/section/section_trapez.ts b/src/section/section_trapez.ts
index f415776cb960cf1e5384e4ce6d3c9efcd23237a4..eb11032649035b779ea86d10f41cf56428cfb6af 100644
--- a/src/section/section_trapez.ts
+++ b/src/section/section_trapez.ts
@@ -1,4 +1,4 @@
-import { ComputeNodeType, ParamDefinition, ParamDomainValue, ParamCalculability } from "../param";
+import { ComputeNodeType, ParamDefinition, ParamDomainValue, ParamCalculability, CalculatorType } from "../param";
 import { acSection, ParamsSection } from "./section_type";
 import { Result } from "../util/result";
 
@@ -6,12 +6,10 @@ export class ParamsSectionTrapez extends ParamsSection {
         private _LargeurFond: ParamDefinition; // Largeur au fond
         private _Fruit: ParamDefinition; // Fruit des berges
 
-        constructor(rLargeurFond: number, rFruit: number, rY: number, rKs: number, rQ: number, rIf: number, rPrec: number, rYB: number,
-                nodeType: ComputeNodeType = ComputeNodeType.SectionTrapeze,
-                defaultNodeType: ComputeNodeType = ComputeNodeType.SectionParametree) {
-                super(rY, undefined, rKs, rQ, rIf, rPrec, rYB, defaultNodeType);
-                this._LargeurFond = new ParamDefinition(nodeType, 'LargeurFond', ParamDomainValue.POS_NULL, rLargeurFond);
-                this._Fruit = new ParamDefinition(nodeType, 'Fruit', ParamDomainValue.POS_NULL, rFruit);
+        constructor(rLargeurFond: number, rFruit: number, rY: number, rKs: number, rQ: number, rIf: number, rPrec: number, rYB: number) {
+                super(rY, undefined, rKs, rQ, rIf, rPrec, rYB, ComputeNodeType.None);
+                this._LargeurFond = new ParamDefinition(CalculatorType.SectionParametree, 'LargeurFond', ParamDomainValue.POS_NULL, rLargeurFond, ComputeNodeType.SectionTrapeze);
+                this._Fruit = new ParamDefinition(CalculatorType.SectionParametree, 'Fruit', ParamDomainValue.POS_NULL, rFruit, ComputeNodeType.SectionTrapeze);
 
                 this.addParamDefinition(this._LargeurFond);
                 this.addParamDefinition(this._Fruit);
diff --git a/src/section/section_type.ts b/src/section/section_type.ts
index 1e910e39e41c2237ee4fac5f05150342d85eb76f..dcb11e66dfa101c6e28ce6a32cfa4eaff7026adc 100644
--- a/src/section/section_type.ts
+++ b/src/section/section_type.ts
@@ -1,5 +1,5 @@
 import { MessageCode, Message } from "../util/message";
-import { ComputeNodeType, ComputeNode, ParamDefinition, ParamDomainValue, ParamCalculability, ParamsEquation } from "../param";
+import { ComputeNodeType, ComputeNode, ParamDefinition, ParamDomainValue, ParamCalculability, ParamsEquation, CalculatorType } from "../param";
 import { cHautCritique, cHautNormale, cHautCorrespondante, cHautConjuguee } from "./hauteur";
 import { Result } from "../util/result";
 
@@ -16,14 +16,14 @@ export abstract class cParamsCanal extends ParamsEquation {
         private _iPrec: ParamDefinition;  // Précision en nombre de décimales
         private _YB: ParamDefinition;  // Hauteur de berge
 
-        constructor(nodeType: ComputeNodeType, rKs: number, rQ: number, rIf: number, rPrec: number, rYB: number) {
+        constructor(calcType: CalculatorType, rKs: number, rQ: number, rIf: number, rPrec: number, rYB: number) {
                 super();
-                this._Ks = new ParamDefinition(nodeType, 'Ks', ParamDomainValue.POS, rKs);
-                this._Q = new ParamDefinition(nodeType, 'Q', ParamDomainValue.POS_NULL, rQ);
-                this._If = new ParamDefinition(nodeType, 'If', ParamDomainValue.ANY, rIf);
-                this._Prec = new ParamDefinition(nodeType, 'Prec', ParamDomainValue.POS, rPrec);
-                this._iPrec = new ParamDefinition(nodeType, 'iPrec', ParamDomainValue.ANY, Math.round(-Math.log(rPrec) / Math.log(10)));
-                this._YB = new ParamDefinition(nodeType, 'YB', ParamDomainValue.POS, rYB);
+                this._Ks = new ParamDefinition(calcType, 'Ks', ParamDomainValue.POS, rKs);
+                this._Q = new ParamDefinition(calcType, 'Q', ParamDomainValue.POS_NULL, rQ);
+                this._If = new ParamDefinition(calcType, 'If', ParamDomainValue.ANY, rIf);
+                this._Prec = new ParamDefinition(calcType, 'Prec', ParamDomainValue.POS, rPrec);
+                this._iPrec = new ParamDefinition(calcType, 'iPrec', ParamDomainValue.ANY, Math.round(-Math.log(rPrec) / Math.log(10)));
+                this._YB = new ParamDefinition(calcType, 'YB', ParamDomainValue.POS, rYB);
 
                 this.addParamDefinition(this._Ks);
                 this.addParamDefinition(this._Q);
@@ -81,11 +81,17 @@ export abstract class ParamsSection extends cParamsCanal {
         private _Y: ParamDefinition;          // Tirant d'eau
         private _LargeurBerge: ParamDefinition; // largeur au débordement
 
-        constructor(rY: number, rLargeurBerge: number, rKs: number, rQ: number, rIf: number, rPrec: number, rYB: number,
-                nodeType: ComputeNodeType = ComputeNodeType.SectionParametree) {
-                super(nodeType, rKs, rQ, rIf, rPrec, rYB);
-                this._Y = new ParamDefinition(nodeType, 'Y', ParamDomainValue.POS_NULL, rY);
-                this._LargeurBerge = new ParamDefinition(nodeType, 'LargeurBerge', ParamDomainValue.POS_NULL, rLargeurBerge);
+        constructor(rY: number,
+                rLargeurBerge: number,
+                rKs: number,
+                rQ: number,
+                rIf: number,
+                rPrec: number,
+                rYB: number,
+                nodeType: ComputeNodeType) {
+                super(CalculatorType.SectionParametree, rKs, rQ, rIf, rPrec, rYB);
+                this._Y = new ParamDefinition(CalculatorType.SectionParametree, 'Y', ParamDomainValue.POS_NULL, rY, nodeType);
+                this._LargeurBerge = new ParamDefinition(CalculatorType.SectionParametree, 'LargeurBerge', ParamDomainValue.POS_NULL, rLargeurBerge, nodeType);
 
                 this.addParamDefinition(this._Y);
                 this.addParamDefinition(this._LargeurBerge);
diff --git a/src/structure/parallel_structure_params.ts b/src/structure/parallel_structure_params.ts
index c7d556dbfc0eb1b920e3da8ea900491eecd8023c..8c03ecf5530537cb2934da0957e07ce6aeae609a 100644
--- a/src/structure/parallel_structure_params.ts
+++ b/src/structure/parallel_structure_params.ts
@@ -1,5 +1,5 @@
 import { Nub } from "../nub";
-import { ComputeNodeType, ParamDefinition, ParamDomainValue, ParamsEquation } from "../param";
+import { ComputeNodeType, ParamDefinition, ParamDomainValue, ParamsEquation, CalculatorType } from "../param";
 
 /**
  * Common parameters of hydraulic structure equations
@@ -22,11 +22,11 @@ export class ParallelStructureParams extends ParamsEquation {
      */
     constructor(rQ: number, rZ1: number, rZ2: number) {
         super();
-        this.Q = new ParamDefinition(ComputeNodeType.CondDistri, "Q", ParamDomainValue.ANY, rQ);
+        this.Q = new ParamDefinition(CalculatorType.ParallelStructure, "Q", ParamDomainValue.ANY, rQ);
         this.addParamDefinition(this.Q);
-        this.Z1 = new ParamDefinition(ComputeNodeType.CondDistri, "Z1", ParamDomainValue.ANY, rZ1);
+        this.Z1 = new ParamDefinition(CalculatorType.ParallelStructure, "Z1", ParamDomainValue.ANY, rZ1);
         this.addParamDefinition(this.Z1);
-        this.Z2 = new ParamDefinition(ComputeNodeType.CondDistri, "Z2", ParamDomainValue.ANY, rZ2);
+        this.Z2 = new ParamDefinition(CalculatorType.ParallelStructure, "Z2", ParamDomainValue.ANY, rZ2);
         this.addParamDefinition(this.Z2);
     }
 }
diff --git a/src/structure/rectangular_structure_params.ts b/src/structure/rectangular_structure_params.ts
index 485d540bdfa2b17d1d4363d1edcac93da1be0ff4..8eb455bfb7eac65774784670860fbb1642dbbaa3 100644
--- a/src/structure/rectangular_structure_params.ts
+++ b/src/structure/rectangular_structure_params.ts
@@ -1,4 +1,4 @@
-import { ComputeNodeType, ParamCalculability, ParamDefinition, ParamDomainValue, ParamsEquation } from "../param";
+import { ComputeNodeType, ParamCalculability, ParamDefinition, ParamDomainValue, ParamsEquation, CalculatorType } from "../param";
 import { Structure } from "./structure";
 import { StructureParams } from "./structure_params";
 
@@ -25,9 +25,9 @@ export class RectangularStructureParams extends StructureParams {
      */
     constructor(rQ: number, rZDV: number, rZ1: number, rZ2: number, rL: number, rCd: number, rW: number = Infinity) {
         super(rQ, rZDV, rZ1, rZ2, rW);
-        this.L = new ParamDefinition(ComputeNodeType.CondDistri, "L", ParamDomainValue.POS, rL);
+        this.L = new ParamDefinition(CalculatorType.Structure, "L", ParamDomainValue.POS, rL, ComputeNodeType.StructureRectangle);
         this.addParamDefinition(this.L);
-        this.Cd = new ParamDefinition(ComputeNodeType.CondDistri, "Cd", ParamDomainValue.POS, rCd);
+        this.Cd = new ParamDefinition(CalculatorType.Structure, "Cd", ParamDomainValue.POS, rCd, ComputeNodeType.StructureRectangle);
         this.addParamDefinition(this.Cd);
     }
 }
diff --git a/src/structure/structure_params.ts b/src/structure/structure_params.ts
index 468fd6a43cb48b9e032dcdb416ea052a0723e533..1e90cb2523f1bf53b2411ba2168f120c6d525acd 100644
--- a/src/structure/structure_params.ts
+++ b/src/structure/structure_params.ts
@@ -1,5 +1,5 @@
 import { Nub } from "../nub";
-import { ComputeNodeType, ParamDefinition, ParamDomainValue, ParamsEquation } from "../param";
+import { ComputeNodeType, ParamDefinition, ParamDomainValue, ParamsEquation, CalculatorType } from "../param";
 
 /**
  * Common parameters of hydraulic structure equations
@@ -36,23 +36,23 @@ export class StructureParams extends ParamsEquation {
      * @param rZ2 Cote de l'eau aval (m)
      * @param rW Ouverture de vanne (m) (infinity pour un seuil)
      */
-    constructor(rQ: number, rZDV: number, rZ1: number, rZ2: number, rW: number = Infinity ) {
+    constructor(rQ: number, rZDV: number, rZ1: number, rZ2: number, rW: number = Infinity) {
         super();
-        this.Q = new ParamDefinition(ComputeNodeType.CondDistri, "Q", ParamDomainValue.ANY, rQ);
+        this.Q = new ParamDefinition(CalculatorType.Structure, "Q", ParamDomainValue.ANY, rQ);
         this.addParamDefinition(this.Q);
-        this.ZDV = new ParamDefinition(ComputeNodeType.CondDistri, "ZDV", ParamDomainValue.ANY, rZDV);
+        this.ZDV = new ParamDefinition(CalculatorType.Structure, "ZDV", ParamDomainValue.ANY, rZDV);
         this.addParamDefinition(this.ZDV);
-        this.Z1 = new ParamDefinition(ComputeNodeType.CondDistri, "Z1", ParamDomainValue.ANY, rZ1);
+        this.Z1 = new ParamDefinition(CalculatorType.Structure, "Z1", ParamDomainValue.ANY, rZ1);
         this.addParamDefinition(this.Z1);
-        this.Z2 = new ParamDefinition(ComputeNodeType.CondDistri, "Z2", ParamDomainValue.ANY, rZ2);
+        this.Z2 = new ParamDefinition(CalculatorType.Structure, "Z2", ParamDomainValue.ANY, rZ2);
         this.addParamDefinition(this.Z2);
-        this.h1 = new ParamDefinition(ComputeNodeType.CondDistri, "h1", ParamDomainValue.POS_NULL,
+        this.h1 = new ParamDefinition(CalculatorType.Structure, "h1", ParamDomainValue.POS_NULL,
             Math.max(0, this.Z1.v - this.ZDV.v));
         this.addParamDefinition(this.h1);
-        this.h2 = new ParamDefinition(ComputeNodeType.CondDistri, "h2", ParamDomainValue.POS_NULL,
+        this.h2 = new ParamDefinition(CalculatorType.Structure, "h2", ParamDomainValue.POS_NULL,
             Math.max(0, this.Z2.v - this.ZDV.v));
         this.addParamDefinition(this.h2);
-        this.W = new ParamDefinition(ComputeNodeType.CondDistri, "W", ParamDomainValue.POS_NULL, rW);
+        this.W = new ParamDefinition(CalculatorType.Structure, "W", ParamDomainValue.POS_NULL, rW);
         this.addParamDefinition(this.W);
     }
 
diff --git a/src/util/hashtable.ts b/src/util/hashtable.ts
new file mode 100644
index 0000000000000000000000000000000000000000..5a57337c95c1dd5d5b9a743792e4788878040301
--- /dev/null
+++ b/src/util/hashtable.ts
@@ -0,0 +1,15 @@
+export class HashTable {
+    private _hashes: { [key: string]: any };
+
+    constructor() {
+        this._hashes = {};
+    }
+
+    public get(key: any): any {
+        return this._hashes[JSON.stringify(key)];
+    }
+
+    public put(key: any, value: any) {
+        this._hashes[JSON.stringify(key)] = value;
+    }
+}