MathGroup Archive 2008

[Date Index] [Thread Index] [Author Index]

Search the Archive

Re: Re: Solving nonlinear inequality constraints

  • To: mathgroup at smc.vnet.net
  • Subject: [mg91405] Re: [mg91243] Re: [mg91209] Solving nonlinear inequality constraints
  • From: "Stuart Nettleton" <Stuart.Nettleton at uts.edu.au>
  • Date: Wed, 20 Aug 2008 06:22:17 -0400 (EDT)
  • Organization: University of Technology, Sydney

Daniel's suggestions have led me to refine my notebook (below), which has  
reduced memory usage slightly and thereby allowed a marginally increased  
projection period from 9 to 10 periods:
1. Introducing a function for mu[t_] - this has not been achieved. Perhaps  
I am missing something very major but I cannot see how this can be done!  
As soon as mu[1], mu[2] are generated in variables, they are immediately  
evaluated by the arbitrary function (such as mu[t_]:=0.5). The effect of  
providing functions for all the variables is to evaluate the objective and  
constraints. Therefore, NMinimize merely has a numeric value for the  
objective function, a set of true and false for the constraints, and no  
variables for optimising. The notebook below shows that not only mu[t] but  
also variables like k[t] and s[t] need to be "freed" for optimization (as  
in the standard Nordhaus model), which I can only see means that variables  
cannot be given their own functions.
2. Removing Hold - the need for Hold is removed by using _?NumberQ in  
functions to prevent the symbolic evaluation that would otherwise occur.  
The first notebook below has this feature. The second notebook continues  
to use Holds, which are eliminated before the NMinimize function. I have  
some preference for the Hold approach because answers with small numbers  
of periods can be different than when _?NumberQ is used and I tend to  
think symbolic answers are more accurate.
3. Using the Hold approach (ie. without using _?NumberQ in functions)  
provides the following performance and memory usage on an intel 64bit/16Gb:
Projection    Compilation    Total             Memory
Periods         Time                 Minutes        Mb
5                    1.0 sec               1.2                234
6                    2.4 secs             2.4                 535
7                    8.9 secs            24.8**         1234
8                    0.5 mins           12.8              2572
9                    2.3 mins           40.9              4943
10                  9.4  mins          66.3              8908
11                  33.5 mins*      runs out of memory
*   10.5Gb used in compilation phase
** looks odd but retested and this was the same result, so perhaps its due  
to the shape of the curve
Usually at 6 periods and upwards there were one or two complaints that  
"NMinimize::incst: NMinimize was unable to generate any initial points \
satisfying the inequality constraints" but the function kept running to a  
final solution.

4. As previously observed, the result using _?NumberQ in functions is  
surprisingly similar to that with Hold. There is a shorter compilation  
phase of 1 minute offset by longer optimisation phase of 1.5 minutes,  
resulting in a slightly longer calculation period. The comparative  
statistics for 10 periods are:
Approach      Compilation    Total             Memory
                       Minutes           Minutes        Mb
Hold              9.4  mins          66.3             8908
_?NumberQ  8.3 mins           66.8             8901

Conclusion:
It is some success that the number of projection periods has increased  
 from 8 to 10.
However, I still need to ramp-up to 60 periods and would like to achive  
this in less than an hour if possible.
The continued interest of Daniel and participants on this list is warmly  
appreciated!

Thanks,
Stuart

**** Notebook using _?NumberQ ****

(*AppendTo[$Echo,"stdout"];*)
(*SetOptions["stdout",PageWidth->110] ; \
*)
(* Nordhaus Brief Climate Change Policy Model May 2008 *)
(* \
Stuart Nettleton July 2008 *)

starttime = AbsoluteTime[];
periods = 5; (* projection periods *)
maxit = 5000; (* maximum \
iterations *)

(* objective function *)
(* program always minimises, so negative for \
maximisation *)
obj = {-cumu[periods]};

(* optimisation variables: topolology leaves *)
(* .. for NMinimize \
provide both upper and lower bounds *)
(* .. for FindMinimum provide \
a single start estimate *)
(* hold function prevents premature \
evaluation *)
(*opt = {{\[Mu][t],0.001,1},{k[t],100,10000}};*)

opt = {{\[Mu][t], 0.001, 1}};

(* exogenous parameters *)
   pop0 = 6514;
   popg = 0.35;
   popa = 8600;
   dela = 0.001;
   d\[Sigma]1 = 0.003;
   d\[Sigma]2 = 0.000;
   pback = 1.17;
   backrat = 2;
   gback = 0.05;
   \[Rho] = 0.015;
   fex0 = -0.06;
   fex1 = 0.30;
   \[Kappa]1 = 1;
   \[Kappa]2 = 1;
   \[Kappa]21 = 1;
   d\[Kappa] = 0;
   \[Theta] = 2.8;
   sr = 0.22;

(* exogenous variables *)

gfacpop[t_] :=
   gfacpop[t] = (Exp[popg*(t - 1)] - 1)/Exp[popg*(t - 1)];
   l[t_] := l[t] = pop0*(1 - gfacpop[t]) + gfacpop[t]*popa;
   ga[t_] := ga[t] = ga[0]*Exp[-dela*10*(t - 1)];
   a[t_] := a[t] = a[t - 1]/(1 - ga[t - 1]);
   g\[Sigma][t_] :=
   g\[Sigma][t] =
    g\[Sigma][0]*
     Exp[-d\[Sigma]1*10*(t - 1) - d\[Sigma]2*10*(t - 1)^2];
   \[Sigma][t_] := \[Sigma][t] = \[Sigma][t - 1]/(1 - g\[Sigma][t]);
   \[CapitalTheta][
    t_] := \[CapitalTheta][
     t] = (pback*\[Sigma][t]/\[Theta])*((backrat - 1 +
         Exp[-gback*(t - 1)])/backrat);
   eland[t_] := eland[t] = eland[0]*(1 - 0.1)^(t - 1);
   r[t_] := r[t] = 1/(1 + \[Rho])^(10*(t - 1));
   fex[t_] :=
   fex[t] = fex0 + If[t < 12, 0.1*(fex1 - fex0)*(t - 1), 0.36];
   \[Kappa][t_] := \[Kappa][t] =
    If[t >= 25, \[Kappa]21, \[Kappa]21 + (\[Kappa]2 - \[Kappa]21)*
       Exp[-d\[Kappa]*(t - 2)]];
   \[CapitalPi][t_] := \[CapitalPi][t] = \[Kappa][t]^(1 - \[Theta]);
   (*s[t_]:= s[t] =sr;*)

(* initial values of exogenous variables *)
ga[0] = 0.092;
a[1] = a[0] = 0.02722;
g\[Sigma][0] = -0.0730;
\[Sigma][1] = \[Sigma][0] = 0.13418;
eland[0] = 11;
\[Kappa][1] = \[Kappa][0] = 0.25372;

(* endogenous parameters *)
\[Alpha] = 2.0;
\[Gamma] = .30;
\[Delta] = 0.1;
\[Eta] = 3.8;
t2xco2 = 3;
\[Psi]1 = 0.00000;
\[Psi]2 = 0.0028388;
\[Psi]3 = 2.00;
\[Xi]1 = 0.220;
\[Xi]2 = \[Eta]/t2xco2;
\[Xi]3 = 0.300;
\[Xi]4 = 0.050;
\[Phi]12 = 0.189288;
\[Phi]12a = 0.189288;
\[Phi]11 = 1 - \[Phi]12a;
\[Phi]23 = 0.05;
\[Phi]23a = 0.05;
\[Phi]21 = 587.473*\[Phi]12a/1143.894;
\[Phi]22 = 1 - \[Phi]21 - \[Phi]23a;
\[Phi]32 = 1143.894*\[Phi]23a/18340;
\[Phi]33 = 1 - \[Phi]32;
mat1750 = 596.4;
k0 = 137;
y0 = 61.1;
c0 = 30;
mat0 = 808.9;
mup0 = 1255;
mlo0 = 18365;
tat0 = 0.7307;
tlo0 = 0.0068;
\[Mu]0 = 0.005;
ceind0 = 0;
cumu0 = 381800;
scale1 = 194;

(* endogenous equality constraints*)

ceind[t_?NumberQ] := eind[t - 1] + ceind[t - 1];
eind[t_?NumberQ] :=
   10 *\[Sigma][t] *(1 - \[Mu][t]) *ygr[t] + eland[t];
for[t_?NumberQ] := \[Eta]*(Log[(matav[t] + 0.000001)/mat1750]/
       Log[2]) + fex[t];
mat[t_?NumberQ] :=
   eind[t - 1] + \[Phi]11*mat[t - 1] + \[Phi]21*mup[t - 1];
matav[t_?NumberQ] := (mat[t] + mat[t + 1])/2;
mlo[t_?NumberQ] := \[Phi]23*mup[t - 1] + \[Phi]33*mlo[t - 1];
mup[t_?NumberQ] := \[Phi]12*mat[t - 1] + \[Phi]22*
     mup[t - 1] + \[Phi]32*mlo[t - 1];
tat[t_?NumberQ] :=
   tat[t - 1] + \[Xi]1*(for[t] - \[Xi]2*
        tat[t - 1] - \[Xi]3*(tat[t - 1] - tlo[t - 1]));
tlo[t_?NumberQ] := tlo[t - 1] + \[Xi]4*(tat[t - 1] - tlo[t - 1]);
ygr[t_?NumberQ] := a[t]* k[t]^\[Gamma] *l[t]^(1 - \[Gamma]);
dam[t_?NumberQ] :=
   ygr[t]*(1 - 1/(1 + \[Psi]1*tat[t] + \[Psi]2*(tat[t]^\[Psi]3)));
\[CapitalLambda][t_?NumberQ] :=
   ygr[t] *\[CapitalPi][t] *\[CapitalTheta][t] *\[Mu][t]^\[Theta];
y[t_?NumberQ] :=
   ygr[t]*(1 - \[CapitalPi][t]*\[CapitalTheta][
         t]*\[Mu][t]^\[Theta])/(1 + \[Psi]1*
        tat[t] + \[Psi]2*(tat[t]^\[Psi]3));
inv[t_?NumberQ] := (y[t] + 0.001)*s[t];
(*k[t_?NumberQ]:=10*inv[t-1]+((1-\[Delta])^10)*k[t-1];*)

ri[t_?NumberQ] := \[Gamma]*y[t]/k[t] - (1 - (1 - \[Delta])^10)/10;
c[t_?NumberQ] := y[t] - inv[t];
u[t_?NumberQ] := ((c[t]/l[t])^(1 - \[Alpha]) - 1)/(1 - \[Alpha]);
cumu[t_?NumberQ] := cumu[t - 1] + (l[t]*u[t]*r[t]*10)/scale1;
cpc[t_?NumberQ] := c[t]*1000/l[t];
pcy[t_?NumberQ] := y[t]*1000/l[t];

(* initial values of endogenous variables *)

cumu[1] = cumu[0] = cumu0;
ceind[1] = ceind[0] = ceind0;
mat[1] = mat[0] = mat0;
mlo[1] = mlo[0] = mlo0;
mup[1] = mup[0] = mup0;
tat[1] = tat[0] = tat0;
tlo[1] = tlo[0] = tlo0;
y[0] = y0;
k[1] = k[0] = k0;
c[0] = c0;
\[Mu][1] = \[Mu][0] = \[Mu]0;

(* endogenous inequality constraints*)
endog = {
    k[t] <= 10*inv[t - 1] + ((1 - \[Delta])^10)*k[t - 1],
    0.02*k[periods] <= inv[periods],
    100 <= k[t],
    20 <= c[t],
    10 <= mat[t],
    100 <= mup[t],
    1000 <= mlo[t],
    -1 <= tlo[t] <= 20,
    0 <= tat[t] <= 20,
    ceind[t] <= 6000,
    0 <= y[t],
    0 <= inv[t],
    0 <= ygr[t],
    0 <= eind[t],
    0 <= matav[t],
    0 <= \[Mu][t]
    };

(* processing ... *)

(*prepare the objective function*)
objvars = Simplify[obj];
objectimous =
   Simplify[
    Flatten[Union[Map[objvars /. t -> # &, Range[periods]]] /.
      x_Symbol[i_Integer /; i < 0] -> 0]];

(*prepare the endogenous constraints*)
endovars = Simplify[endog];
endogenous =
   Simplify[
    Flatten[Union[Map[endovars /. t -> # &, Range[periods]]] /.
      x_Symbol[i_Integer /; i < 0] -> 0]];

(*prepare the independent optimising variables*)

optvars = Simplify[opt];
optimous =
   Union[Cases[
     Flatten[Map[optvars /. t -> # &, Range[periods]],
      1], {x_Symbol[_Integer], _Integer | _Real} | \
{x_Symbol[_Integer], _Integer | _Real, _Integer | _Real} | \
{x_Symbol[_Integer], _Integer | _Real, _Integer | _Real, _Integer | \
_Real}, Infinity]];
optimousvars =
   Union[Cases[optimous, x_Symbol[i_Integer] -> x[i], Infinity]];

(*include any additional optimising variables arising from the \
endogenous constraints*)

primafacievars =
   Union[Cases[objectimous, x_Symbol[i_Integer] -> x[i], Infinity],
    Cases[endogenous, x_Symbol[i_Integer] -> x[i], Infinity]];
extendedvariables =
   Union[optimous, Complement[primafacievars, optimousvars]];

(*prepare optimising function*)

Print[Round[(AbsoluteTime[] - starttime), 0.01],
   " seconds compilation time, commencing optimisation ..."];

soln = NMinimize[Join[objectimous, endogenous], extendedvariables,
    MaxIterations -> maxit];

(*output results*)
Print["Solution: ", soln];
Print[Round[(AbsoluteTime[] - starttime)/60, 0.01],
   " minutes from start to completion"];
Print[Round[N[MaxMemoryUsed[]*10^-6], 0.1], " Mb memory used"];

**** Notebook using Hold ****

(*AppendTo[$Echo,"stdout"];*)
(*SetOptions["stdout",PageWidth->110] ; \
*)
(* Nordhaus Brief Climate Change Policy Model May 2008 *)
(* \
Stuart Nettleton July 2008 *)

starttime = AbsoluteTime[];
periods = 11; (* projection periods *)
maxit = 5000; (* maximum \
iterations *)

(* objective function *)
(* program always minimises, so negative for \
maximisation *)
obj = Hold[-cumu[periods]];
objvars = Apply[List, Map[Hold, obj]];

(* preferences for optimisation variables (topolology leaves) *)
(* .. \
for NMinimize provide both upper and lower bounds *)
(* .. for \
FindMinimum provide a single start estimate *)
(* hold function \
prevents premature evaluation *)
(*opt = \
Hold[{\[Mu][t],0.001,1},{k[t],100,10000}];*)

opt = Hold[{\[Mu][t], 0.001, 1}];
optvars = Apply[List, Map[Hold, opt]];

(* exogenous parameters *)
   pop0 = 6514;
   popg = 0.35;
   popa = 8600;
   dela = 0.001;
   d\[Sigma]1 = 0.003;
   d\[Sigma]2 = 0.000;
   pback = 1.17;
   backrat = 2;
   gback = 0.05;
   \[Rho] = 0.015;
   fex0 = -0.06;
   fex1 = 0.30;
   \[Kappa]1 = 1;
   \[Kappa]2 = 1;
   \[Kappa]21 = 1;
   d\[Kappa] = 0;
   \[Theta] = 2.8;
   sr = 0.22;

(* exogenous variables *)

gfacpop[t_] :=
   gfacpop[t] = (Exp[popg*(t - 1)] - 1)/Exp[popg*(t - 1)];
   l[t_] := l[t] = pop0*(1 - gfacpop[t]) + gfacpop[t]*popa;
   ga[t_] := ga[t] = ga[0]*Exp[-dela*10*(t - 1)];
   a[t_] := a[t] = a[t - 1]/(1 - ga[t - 1]);
   g\[Sigma][t_] :=
   g\[Sigma][t] =
    g\[Sigma][0]*
     Exp[-d\[Sigma]1*10*(t - 1) - d\[Sigma]2*10*(t - 1)^2];
   \[Sigma][t_] := \[Sigma][t] = \[Sigma][t - 1]/(1 - g\[Sigma][t]);
   \[CapitalTheta][
    t_] := \[CapitalTheta][
     t] = (pback*\[Sigma][t]/\[Theta])*((backrat - 1 +
         Exp[-gback*(t - 1)])/backrat);
   eland[t_] := eland[t] = eland[0]*(1 - 0.1)^(t - 1);
   r[t_] := r[t] = 1/(1 + \[Rho])^(10*(t - 1));
   fex[t_] :=
   fex[t] = fex0 + If[t < 12, 0.1*(fex1 - fex0)*(t - 1), 0.36];
   \[Kappa][t_] := \[Kappa][t] =
    If[t >=
      25, \[Kappa]21, \[Kappa]21 + (\[Kappa]2 - \[Kappa]21)*
       Exp[-d\[Kappa]*(t - 2)]];
   \[CapitalPi][t_] := \[CapitalPi][t] = \[Kappa][t]^(1 - \[Theta]);
   (*s[t_]:= s[t] =sr;*)

(* initial values of exogenous variables *)
ga[0] = 0.092;
a[1] = a[0] = 0.02722;
g\[Sigma][0] = -0.0730;
\[Sigma][1] = \[Sigma][0] = 0.13418;
eland[0] = 11;
\[Kappa][1] = \[Kappa][0] = 0.25372;

(* endogenous parameters *)
\[Alpha] = 2.0;
\[Gamma] = .30;
\[Delta] = 0.1;
\[Eta] = 3.8;
t2xco2 = 3;
\[Psi]1 = 0.00000;
\[Psi]2 = 0.0028388;
\[Psi]3 = 2.00;
\[Xi]1 = 0.220;
\[Xi]2 = \[Eta]/t2xco2;
\[Xi]3 = 0.300;
\[Xi]4 = 0.050;
\[Phi]12 = 0.189288;
\[Phi]12a = 0.189288;
\[Phi]11 = 1 - \[Phi]12a;
\[Phi]23 = 0.05;
\[Phi]23a = 0.05;
\[Phi]21 = 587.473*\[Phi]12a/1143.894;
\[Phi]22 = 1 - \[Phi]21 - \[Phi]23a;
\[Phi]32 = 1143.894*\[Phi]23a/18340;
\[Phi]33 = 1 - \[Phi]32;
mat1750 = 596.4;
k0 = 137;
y0 = 61.1;
c0 = 30;
mat0 = 808.9;
mup0 = 1255;
mlo0 = 18365;
tat0 = 0.7307;
tlo0 = 0.0068;
\[Mu]0 = 0.005;
ceind0 = 0;
cumu0 = 381800;
scale1 = 194;

(* endogenous equality constraints*)

ceind[t_] := eind[t - 1] + ceind[t - 1];
eind[t_] := 10 *\[Sigma][t] *(1 - \[Mu][t]) *ygr[t] + eland[t];
for[t_] := \[Eta]*(Log[(matav[t] + 0.000001)/mat1750]/Log[2]) +
    fex[t];
mat[t_] := eind[t - 1] + \[Phi]11*mat[t - 1] + \[Phi]21*mup[t - 1];
matav[t_] := (mat[t] + mat[t + 1])/2;
mlo[t_] := \[Phi]23*mup[t - 1] + \[Phi]33*mlo[t - 1];
mup[t_] := \[Phi]12*mat[t - 1] + \[Phi]22*mup[t - 1] + \[Phi]32*
     mlo[t - 1];
tat[t_] :=
   tat[t - 1] + \[Xi]1*(for[t] - \[Xi]2*
        tat[t - 1] - \[Xi]3*(tat[t - 1] - tlo[t - 1]));
tlo[t_] := tlo[t - 1] + \[Xi]4*(tat[t - 1] - tlo[t - 1]);
ygr[t_] := a[t]* k[t]^\[Gamma] *l[t]^(1 - \[Gamma]);
dam[t_] :=
   ygr[t]*(1 - 1/(1 + \[Psi]1*tat[t] + \[Psi]2*(tat[t]^\[Psi]3)));
\[CapitalLambda][t_] :=
   ygr[t] *\[CapitalPi][t] *\[CapitalTheta][t] *\[Mu][t]^\[Theta];
y[t_] :=
   ygr[t]*(1 - \[CapitalPi][t]*\[CapitalTheta][
         t]*\[Mu][t]^\[Theta])/(1 + \[Psi]1*
        tat[t] + \[Psi]2*(tat[t]^\[Psi]3));
inv[t_] := (y[t] + 0.001)*s[t];
(*k[t_]:=10*inv[t-1]+((1-\[Delta])^10)*k[t-1];*)

ri[t_] := \[Gamma]*y[t]/k[t] - (1 - (1 - \[Delta])^10)/10;
c[t_] := y[t] - inv[t];
u[t_] := ((c[t]/l[t])^(1 - \[Alpha]) - 1)/(1 - \[Alpha]);
cumu[t_] := cumu[t - 1] + (l[t]*u[t]*r[t]*10)/scale1;
cpc[t_] := c[t]*1000/l[t];
pcy[t_] := y[t]*1000/l[t];

(* initial values of endogenous variables *)

cumu[1] = cumu[0] = cumu0;
ceind[1] = ceind[0] = ceind0;
mat[1] = mat[0] = mat0;
mlo[1] = mlo[0] = mlo0;
mup[1] = mup[0] = mup0;
tat[1] = tat[0] = tat0;
tlo[1] = tlo[0] = tlo0;
y[0] = y0;
k[1] = k[0] = k0;
c[0] = c0;
\[Mu][1] = \[Mu][0] = \[Mu]0;

(* endogenous inequality constraints*)
endog = Hold[
    k[t] <= 10*inv[t - 1] + ((1 - \[Delta])^10)*k[t - 1],
    0.02*k[periods] <= inv[periods],
    100 <= k[t],
    20 <= c[t],
    10 <= mat[t],
    100 <= mup[t],
    1000 <= mlo[t],
    -1 <= tlo[t] <= 20,
    0 <= tat[t] <= 20,
    ceind[t] <= 6000,
    0 <= y[t],
    0 <= inv[t],
    0 <= ygr[t],
    0 <= eind[t],
    0 <= matav[t],
    0 <= \[Mu][t]
    ];
endovars = Apply[List, Map[Hold, endog]];


(* processing ... *)

(* prepare the objective function *)

objectimous =
   Simplify[
    Flatten[Apply[List,
       Map[ReleaseHold,
        Union[Map[objvars /. t -> # &, Range[periods ]]]]] /.
      x_Symbol[i_Integer /; i < 0] -> 0]];

(* prepare the endogenous constraints *)

endogenous =
   Simplify[
    Flatten[Apply[List,
       Map[ReleaseHold,
        Union[Map[endovars /. t -> # &, Range[periods ]]]]] /.
      x_Symbol[i_Integer /; i < 0] -> 0]];

(* prepare the independent optimising variables *)

optimous =
   Union[Cases[
     Apply[List,
      Map[ReleaseHold,
       Flatten[Map[optvars /. t -> # &, Range[periods]]]]],
     {x_Symbol[_Integer], _Integer | _Real} |
      {x_Symbol[_Integer], _Integer | _Real, _Integer | _Real} |
      {x_Symbol[_Integer], _Integer | _Real, _Integer | _Real, \
_Integer | _Real},
     Infinity]];
optimousvars =
   Union[Cases[optimous, x_Symbol[i_Integer] -> x[i], Infinity]];

(* include any additional optimising variables arising from the \
endogenous constraints *)

primafacievars =
   Union[Cases[objectimous, x_Symbol[i_Integer] -> x[i], Infinity],
    Cases[endogenous, x_Symbol[i_Integer] -> x[i], Infinity]] ;
extendedvariables =
   Union[optimous, Complement[primafacievars, optimousvars]];

(* prepare optimising function *)

Print[Round[(AbsoluteTime[] - starttime), 0.01],
   " seconds compilation time, commencing optimisation ..."];
soln = NMinimize[Join[objectimous, endogenous], extendedvariables,
    MaxIterations -> maxit];

(* output results *)
Print["Solution: ", soln];
Print[Round[(AbsoluteTime[] - starttime)/60, 0.01],
   " minutes from start to completion"];
Print[Round[N[MaxMemoryUsed[]*10^-6], 0.1], " Mb memory used"];

--
UTS CRICOS Provider Code:  00099F
DISCLAIMER: This email message and any accompanying attachments may contain
confidential information.  If you are not the intended recipient, do not
read, use, disseminate, distribute or copy this message or attachments.  If
you have received this message in error, please notify the sender
immediately and delete this message. Any views expressed in this message
are those of the individual sender, except where the sender expressly, and
with authority, states them to be the views the University of Technology,
Sydney. Before opening any attachments, please check them for viruses and
defects.


  • Prev by Date: Re: reconstruction of 3D grid with connectivity
  • Next by Date: Re: Re: Making parts of formulae blinking
  • Previous by thread: Re: Re: Solving nonlinear inequality constraints
  • Next by thread: Re: Re: Solving nonlinear inequality constraints