From 7b58643a6f9f2a6e6992a13cef55153e343f8234 Mon Sep 17 00:00:00 2001
From: David Dorchies <david.dorchies@irstea.fr>
Date: Mon, 22 Jul 2019 19:06:35 +0200
Subject: [PATCH] =?UTF-8?q?#85=20Extension=20de=20l'utilisation=20de=20la?=
 =?UTF-8?q?=20classe=20Dichotomie=20=C3=A0=20d'autres=20fonctions=20que=20?=
 =?UTF-8?q?nub.Equation?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

---
 src/dichotomie.ts | 43 ++++++++++++++++++-------------------------
 src/nub.ts        | 13 +++++++++++++
 src/remous.ts     | 29 ++++++++++-------------------
 3 files changed, 41 insertions(+), 44 deletions(-)

diff --git a/src/dichotomie.ts b/src/dichotomie.ts
index 177159c2..377aac3f 100644
--- a/src/dichotomie.ts
+++ b/src/dichotomie.ts
@@ -89,12 +89,12 @@ class SearchInterval extends Interval {
     public updateTargets() {
         let t1 = this.targets.val1;
         if (t1 === undefined || isNaN(t1)) {
-            t1 = this._dicho.CalculX(this.val1).vCalc;
+            t1 = this._dicho.CalculX(this.val1);
         }
 
         let t2 = this.targets.val2;
         if (t2 === undefined || isNaN(t2)) {
-            t2 = this._dicho.CalculX(this.val2).vCalc;
+            t2 = this._dicho.CalculX(this.val2);
         }
         this.targets.setValues(t1, t2);
     }
@@ -136,19 +136,21 @@ export class Dichotomie extends Debug {
      */
     private _target: number;
 
+    private _func: () => number;
+
     /**
      * Construction de la classe.
      * @param nub Noeud de calcul contenant la méthode de calcul Equation
      * @param sVarCalc Nom de la variable à calculer
      * @param targetSymbol nom du paramètre calculé analytiquement par Equation()
      */
-    constructor(private nub: Nub, private sVarCalc: string, dbg: boolean = false, targetSymbol?: string) {
+    constructor(private nub: Nub, private sVarCalc: string, dbg: boolean = false, func?: () => number) {
         super(dbg);
         this._paramX = this.nub.getParameter(this.sVarCalc);
-        if (targetSymbol === undefined) {
-            this.analyticalSymbol = this.nub.getFirstAnalyticalParameter().symbol;
+        if (func !== undefined) {
+            this._func = func;
         } else {
-            this.analyticalSymbol = targetSymbol;
+            this._func = this.nub.EquationFirstAnalyticalParameter;
         }
     }
 
@@ -178,7 +180,7 @@ export class Dichotomie extends Debug {
         this._startIntervalMaxSteps = n;
     }
 
-    public CalculX(x: number): Result {
+    public CalculX(x: number): number {
         this.vX = x;
         return this.Calcul();
     }
@@ -246,12 +248,9 @@ export class Dichotomie extends Debug {
      * On utilise la première variable du tableau des variables pouvant être calculée analytiquement
      * Il faudra s'assurer que cette première variable correspond à la méthode de calcul la plus rapide
      */
-    private Calcul(): Result {
-        const r: Result = this.nub.Equation(this.analyticalSymbol);
-        // this.debug(
-        //     "dicho : Calcul(vX=" + this.sVarCalc + "=" + this.vX + ") -> " +
-        //     this.analyticalSymbol + "=" + r.vCalc);
-        return r;
+    private Calcul(): number {
+        // return this.nub.Equation(this.analyticalSymbol).vCalc;
+        return this._func.call(this.nub);
     }
 
     /**
@@ -264,8 +263,8 @@ export class Dichotomie extends Debug {
         const bounds = new Interval(x - epsilon, x + epsilon);
         bounds.setInterval(bounds.intersect(dom)); // au cas où l'on sorte du domaine de la variable de la fonction
 
-        const y1 = this.CalculX(bounds.min).vCalc;
-        const y2 = this.CalculX(bounds.max).vCalc;
+        const y1 = this.CalculX(bounds.min);
+        const y2 = this.CalculX(bounds.max);
         return y2 > y1;
     }
 
@@ -330,7 +329,7 @@ export class Dichotomie extends Debug {
         // sens de variation de la fonction
         const inc = this.isIncreasingFunction(rInit, intMax);
 
-        if (BoolIdentity(this.CalculX(rInit).vCalc > rTarget, inc)) {
+        if (BoolIdentity(this.CalculX(rInit) > rTarget, inc)) {
             intSearch1.reverse();
             // par ex, la fonction est croissante et la valeur initiale
             // de la variable a une image par la fonction > valeur cible
@@ -363,7 +362,7 @@ export class Dichotomie extends Debug {
 
             case ParamDomainValue.POS:
             case ParamDomainValue.POS_NULL:
-                const y = this.CalculX(1e-8).vCalc;
+                const y = this.CalculX(1e-8);
                 errDomain = inc && (rTarget < y);
                 break;
 
@@ -448,7 +447,7 @@ export class Dichotomie extends Debug {
         }
 
         // tslint:disable-next-line:variable-name
-        const Ymid = this.CalculX(Xmid).vCalc;
+        const Ymid = this.CalculX(Xmid);
         if (Ymin < Ymax) {
             // fonction croissante
 
@@ -468,13 +467,7 @@ export class Dichotomie extends Debug {
 
     private CalcZero(x: number): number {
         this.vX = x;
-        const r: Result = this.nub.Equation(this.analyticalSymbol);
-        if (r.ok) {
-            // this.debug(`CalcZero ${this.sVarCalc} = ${x} => ${this.analyticalSymbol} = ${r.vCalc}`);
-            return r.vCalc - this._target;
-        } else {
-            return undefined;
-        }
+        return this.Calcul() - this._target;
     }
 
     /**
diff --git a/src/nub.ts b/src/nub.ts
index 9756d293..61e6f636 100644
--- a/src/nub.ts
+++ b/src/nub.ts
@@ -176,6 +176,8 @@ export abstract class Nub extends ComputeNode implements IObservable {
     /** allows notifying of progress every X milliseconds only */
     private previousNotificationTimestamp = 0;
 
+    private _firstAnalyticalPrmSymbol: string;
+
     public constructor(prms: ParamsEquation, dbg: boolean = false) {
         super(prms, dbg);
         this._children = [];
@@ -260,6 +262,17 @@ export abstract class Nub extends ComputeNode implements IObservable {
      */
     public abstract Equation(sVarCalc: string): Result;
 
+    /**
+     * Run Equation with first analytical parameter to compute
+     * Returns the result in number form
+     */
+    public EquationFirstAnalyticalParameter(): number {
+        if (this._firstAnalyticalPrmSymbol === undefined) {
+            this._firstAnalyticalPrmSymbol = this.getFirstAnalyticalParameter().symbol;
+        }
+        return this.Equation(this._firstAnalyticalPrmSymbol).vCalc;
+    }
+
     /**
      * Calcul d'une équation quelle que soit l'inconnue à calculer; déclenche le calcul en
      * chaîne des modules en amont si nécessaire
diff --git a/src/remous.ts b/src/remous.ts
index 2b470dc3..56f47441 100644
--- a/src/remous.ts
+++ b/src/remous.ts
@@ -476,35 +476,26 @@ export class CourbeRemous extends SectionNub {
 
     public Calc(sVarCalc: string, rInit?: number): Result {
         if (sVarCalc === "Hs") {
-            return this.Equation(sVarCalc);
+            return this.Equation("Hs");
         }
         throw new Error("CourbeRemous.Calc() : parameter " + sVarCalc + " not allowed");
     }
 
     public Equation(sVarCalc: string): Result {
         if (sVarCalc === "Hs") {
-            // Equation de l'intégration par la méthode des trapèzes
-            this.Sn.Reset();  // pour forcer le calcul avec la nouvelle valeur de section.prms.Y
-
-            // let res: number = this.Sn.CalcSection('Hs') - this.Sn.CalcSection('J') / 2 * this.Dx;
-
-            const rHS = this.Sn.CalcSection("Hs");
-            if (!rHS.ok) {
-                return rHS;
-            }
-
-            const rJ = this.Sn.CalcSection("J");
-            if (!rJ.ok) {
-                return rJ;
-            }
-
-            const res: number = rHS.vCalc - rJ.vCalc / 2 * this.Dx;
-            return new Result(res, this);
+            const rHS: number = this.CalcHS();
+            return new Result(rHS);
         }
 
         throw new Error("CourbeRemous.Equation() : parameter " + sVarCalc + " not allowed");
     }
 
+    public CalcHS(): number {
+        // Equation de l'intégration par la méthode des trapèzes
+        this.Sn.Reset();  // pour forcer le calcul avec la nouvelle valeur de section.prms.Y
+        return this.Sn.CalcSection("Hs").vCalc - this.Sn.CalcSection("J").vCalc / 2 * this.Dx;
+    }
+
     public get Sn(): acSection {
         return this.section;
     }
@@ -714,7 +705,7 @@ export class CourbeRemous extends SectionNub {
             return new Result(new Message(MessageCode.WARNING_REMOUS_ARRET_CRITIQUE), this);
         }
 
-        const dicho = new Dichotomie(this, "Y", this._debugDicho, "Hs");
+        const dicho = new Dichotomie(this, "Y", this._debugDicho, this.CalcHS);
 
         // Calcul de H + J * \Delta x / 2
         // let Trapez_Fn = this.Sn.CalcSection('Hs', Y) + this.Sn.CalcSection('J', Y) / 2 * this.Dx
-- 
GitLab