The code of minimize_constrained
starts checking if the first argument is a symbolic expression. If this were the case, it gets the variables on which such an expression depends. Then the code generates a function whose argument is a vector, needed for any subsequent computation; each variable of the expression is replaced by a component of the vector. For example, if the expression is x^2+y
, the variables are x
and y
. The code defines a function whose argument is a vector, say p
, which yields p[0]^2+p[1]
.
When $f(x,y)=x$, the expression f(x,y)
has only one variable, which is x
, and so the function defined inside minimize_constrained
does not depend on a vector with two components, as required, raising errors.
To use minimize_constrained
, I would advise to directly define Python functions depending on vectors, either with def
or lambda
. For example, for $f(x,y)=x+y$, we can write
def f(x): return x[0] + x[1]
def c(x): return 1 - x[0]^2 - x[1]^2
or also
f = lambda x: x[0] + x[1]
c = lambda x: 1 - x[0]^2 - x[1]^2
In both cases, we get:
sage: minimize_constrained(f, c, [0,0])
(-0.7071774954004159, -0.7070360740443554)
Likewise, for $f(x,y)=x$, we have:
sage: f = lambda x: x[0]
sage: c = lambda x: 1 - x[0]^2 - x[1]^2
sage: minimize_constrained(f, c, [0,0])
(-1.0000000049989504, 9.999999987505248e-05)
which is the expected result.
If, for clarity, you prefer to explicitly define functions in terms of x
and y
, you can still do that:
sage: f = lambda x,y: x
sage: c = lambda x,y: 1 - x^2 - y^2
sage: ff = lambda p: f(*p)
sage: cc = lambda p: c(*p)
sage: minimize_constrained(ff, cc, [0,0])
(-1.0000000049989504, 9.999999987505248e-05)
This is a bug, indeed. Comes from using "f.variables()" in
minimize_constrained
.I have created https://trac.sagemath.org/ticket/31065