zerofunc.gms : Match unmatched vars with zero functions in VI

**Description**

If the feasible set is defined in terms of variables that don't appear in the VI function F, we should not need to mention these variables explicitly in a match. Any unmatched variable will be treated as matched to the zero function. The optimization analogy is variables that appear in the constraints but not in the objective. We test/define the proper behavior in this model. Contributor: Steven Dirkse, February 2009

**Small Model of Type : ** VI

**Category :** GAMS EMP library

**Main file :** zerofunc.gms

```
$title Match unmatched vars with zero functions in VI (ZEROFUNC,SEQ=18)
$ontext
If the feasible set is defined in terms of variables that don't appear
in the VI function F, we should not need to mention these variables
explicitly in a match. Any unmatched variable will be treated as
matched to the zero function. The optimization analogy is variables
that appear in the constraints but not in the objective. We
test/define the proper behavior in this model.
Contributor: Steven Dirkse, February 2009
$offtext
$ontext
First we define an NLP in two variables, then write down the MCP version,
then write down the VI version.
General case Specific case
NLP: min f(x) 1/3 y^3
s.t. g(x) >= 0 y >= sqr(z)
L <= x <= U y, z free
MCP: take derivatives of Lagrangian function wrt x,u
dfdx - u * dgdx perpto x y^2 - u*1 perpto y free
0 + u*2z perpto z free
g(x) perpto u >= 0 y - sqr(z) perpto u >= 0
VI: F(x) := dfdx, F_y := y^2
F_z := 0
X = {x:g(x) >= 0, L <= x <= U } y >= sqr(z), y, z in bounds
All of this to show/test that it is not necessary to include the pair
F_z.z in the model statement, and that since z is not mentioned
explicitly in a match, it is matched with the zero function.
$offtext
free variables y, z;
free variable obj;
equation objDef, gCons;
objDef.. obj =E= power(y,3) / 3;
gCons.. y =G= sqr(z);
model mNLP / objDef, gCons /;
solve mNLP min obj using nlp;
positive variable u 'explicit multiplier for MCP';
u.l = gCons.m;
equations
dLdy, dLdz,
dLdu;
dLdy.. sqr(y) - u =N= 0;
dLdz.. 0 - u*2*z =N= 0;
dLdu.. y - sqr(z) =N= 0;
model mMCP / dLdy.y, dLdz.z, dLdu.u /;
solve mMCP using mcp;
abort$[mMCP.iterusd > 0] 'should have started at MCP solution!';
equations
F_y 'dfdy'
F_z 'dfdz'
;
F_y.. sqr(y) =N= 0;
F_z.. 0 =N= 0;
model mVI / F_y, gCons /;
model mVI0 / F_z, F_y, gCons /;
$ontext
N.B.: we test 4 equivalent ways to specify the same VI. Each includes
the pair F_y.y, this is not optional.
1) minimal empinfo file giving required info only
assumes z is in the model and is perp to 0-func,
assumes gCons defines the feasible set for the VI
2) specify exlicitly that z is in the VI, assumed to be perp to 0-func,
assumes gCons defines the feasible set for the VI
3) specify exlicitly that z is in the VI and perp to F_z := 0,
assumes gCons defines the feasible set for the VI
4) specify exlicitly that z is in the VI and perp to F_z := 0,
explicitly that gCons defines the feasible set for the VI
For this trivial case of a single VI these differences are not
important, but when combining VI models and max/min models as
different agents in an equilibrium model the differences do matter.
$offtext
file myinfo / '%emp.info%' /;
* case 1)
putclose myinfo 'vi F_y y' /;
solve mVI using emp;
abort$[mVI.modelStat <> %MODELSTAT.LOCALLY OPTIMAL%] 'VI should solve OK';
abort$[mVI.solveStat <> %SOLVESTAT.NORMAL COMPLETION%] 'VI should solve OK';
abort$[mVI.iterusd > 0] 'should have started at VI solution!';
* case 2)
putclose myinfo 'vi z F_y y' /;
solve mVI using emp;
abort$[mVI.modelStat <> %MODELSTAT.LOCALLY OPTIMAL%] 'VI should solve OK';
abort$[mVI.solveStat <> %SOLVESTAT.NORMAL COMPLETION%] 'VI should solve OK';
abort$[mVI.iterusd > 0] 'should have started at VI solution!';
* case 3)
putclose myinfo 'vi F_z z F_y y' /;
solve mVI0 using emp;
abort$[mVI0.modelStat <> %MODELSTAT.LOCALLY OPTIMAL%] 'VI should solve OK';
abort$[mVI0.solveStat <> %SOLVESTAT.NORMAL COMPLETION%] 'VI should solve OK';
abort$[mVI0.iterusd > 0] 'should have started at VI solution!';
* case 4)
putclose myinfo 'vi F_z z F_y y gCons' /;
solve mVI0 using emp;
abort$[mVI0.modelStat <> %MODELSTAT.LOCALLY OPTIMAL%] 'VI should solve OK';
abort$[mVI0.solveStat <> %SOLVESTAT.NORMAL COMPLETION%] 'VI should solve OK';
abort$[mVI0.iterusd > 0] 'should have started at VI solution!';
```