calling ``vector().set_local()`` on a Function to be used as an upper or lower bound breaks the code.
Issue #92
new
Hi there,
I need to specify optimization bounds per vertex, so I create a two Functions, one for the upper bound and one for the lower bound, iterate through the dofs, and change the bound appropriately.
Calling ::dolfin_adjoint.Function.vector().set_local()
on the bounds breaks the optimization. I'm using dolfin 2017.2.0 and dolfin_adjoint 2017.2.0.
To illustrate the problem I'm experiencing, here is minimal code:
from dolfin import *
from dolfin_adjoint import *
set_log_level(ERROR)
# Create mesh
nx = 9
mesh = UnitSquareMesh(nx, nx)
# Define function space
V = FunctionSpace(mesh, "CG", 1)
def forward(f):
"""
forward model
"""
u = Function(V, name='State')
v = TestFunction(V)
F = inner(grad(u), grad(v)) * dx - f * v *dx
bc = DirichletBC(V, 0.0, "on_boundary")
solve(F == 0, u, bc)
return u
f = Function(V)
f.vector()[:] = 10.0
# run forward model once
u = forward(f)
# define target functional
J = Functional(-inner(u, u) * dx)
# create ReducedFunctional object
rf = ReducedFunctional(J, Control(f))
# form bounds :
upper = Function(V)
lower = Function(V)
upper.vector()[:] = 100.0
lower.vector()[:] = 0.0
upper_v = upper.vector().get_local()
lower_v = lower.vector().get_local()
# FIXME: comment this out to get working optimization :
upper.vector().set_local(upper_v)
upper.vector().apply('insert')
lower.vector().set_local(upper_v)
lower.vector().apply('insert')
method = None#'ipopt'
if method == 'ipopt':
parameters = {"tol" : 1e-8,
"acceptable_tol" : 1e-6,
"maximum_iterations" : 10,
"print_level" : 5,
"linear_solver" : "ma97"}
problem = MinimizationProblem(rf, bounds = (lower,upper))
solver = IPOPTSolver(problem, parameters=parameters)
f_opt = solver.solve()
else:
f_opt = minimize(rf, bounds=(lower, upper), tol=1.0e-10)
print f_opt.vector().min(), f_opt.vector().max()
adj_reset()
which produces the output:
RUNNING THE L-BFGS-B CODE
* * *
Machine precision = 2.220D-16
N = 100 M = 10
The initial X is infeasible. Restart with its projection.
At X0 100 variables are exactly at the bounds
At iterate 0 f= -1.59878D+01 |proj g|= 0.00000D+00
* * *
Tit = total number of iterations
Tnf = total number of function evaluations
Tnint = total number of segments explored during Cauchy searches
Skip = number of BFGS updates skipped
Nact = number of active bounds at final generalized Cauchy point
Projg = norm of the final projected gradient
F = final function value
* * *
N Tit Tnf Tnint Skip Nact Projg F
100 0 1 0 0 0 0.000D+00 -1.599D+01
F = -15.987807497724067
CONVERGENCE: NORM_OF_PROJECTED_GRADIENT_<=_PGTOL
Cauchy time 0.000E+00 seconds.
Subspace minimization time 0.000E+00 seconds.
Line search time 0.000E+00 seconds.
Total User time 0.000E+00 seconds.
100.0 100.0
Commenting the FIXME
section out produces:
RUNNING THE L-BFGS-B CODE
* * *
Machine precision = 2.220D-16
N = 100 M = 10
At X0 0 variables are exactly at the bounds
At iterate 0 f= -1.59878D-01 |proj g|= 9.04155D-04
At iterate 1 f= -1.59896D-01 |proj g|= 9.04208D-04
ys=-1.049E-09 -gs= 1.825E-05 BFGS update SKIPPED
At iterate 2 f= -7.17258D+00 |proj g|= 6.15390D-03
ys=-1.039E+01 -gs= 1.816E+00 BFGS update SKIPPED
At iterate 3 f= -7.18906D+00 |proj g|= 5.44786D-03
ys=-1.891E-05 -gs= 1.647E-02 BFGS update SKIPPED
At iterate 4 f= -8.47734D+00 |proj g|= 5.87717D-03
ys=-1.063E-01 -gs= 1.235E+00 BFGS update SKIPPED
At iterate 5 f= -8.52797D+00 |proj g|= 5.26093D-03
ys=-1.516E-04 -gs= 5.056E-02 BFGS update SKIPPED
At iterate 6 f= -9.48446D+00 |proj g|= 5.43945D-03
ys=-5.149E-02 -gs= 9.307E-01 BFGS update SKIPPED
At iterate 7 f= -9.62768D+00 |proj g|= 4.70543D-03
ys=-1.092E-03 -gs= 1.427E-01 BFGS update SKIPPED
At iterate 8 f= -1.09256D+01 |proj g|= 4.95639D-03
ys=-8.367E-02 -gs= 1.256E+00 BFGS update SKIPPED
At iterate 9 f= -1.10076D+01 |proj g|= 4.49719D-03
ys=-3.148E-04 -gs= 8.181E-02 BFGS update SKIPPED
At iterate 10 f= -1.16506D+01 |proj g|= 4.46099D-03
ys=-1.898E-02 -gs= 6.335E-01 BFGS update SKIPPED
At iterate 11 f= -1.18359D+01 |proj g|= 3.54869D-03
ys=-1.554E-03 -gs= 1.845E-01 BFGS update SKIPPED
At iterate 12 f= -1.28820D+01 |proj g|= 3.45171D-03
ys=-4.731E-02 -gs= 1.022E+00 BFGS update SKIPPED
At iterate 13 f= -1.32101D+01 |proj g|= 2.97406D-03
ys=-4.428E-03 -gs= 3.259E-01 BFGS update SKIPPED
At iterate 14 f= -1.39678D+01 |proj g|= 2.99354D-03
ys=-2.247E-02 -gs= 7.465E-01 BFGS update SKIPPED
At iterate 15 f= -1.40594D+01 |proj g|= 2.78691D-03
ys=-3.221E-04 -gs= 9.137E-02 BFGS update SKIPPED
At iterate 16 f= -1.42940D+01 |proj g|= 2.61152D-03
ys=-2.148E-03 -gs= 2.335E-01 BFGS update SKIPPED
At iterate 17 f= -1.44692D+01 |proj g|= 2.20336D-03
ys=-1.247E-03 -gs= 1.746E-01 BFGS update SKIPPED
At iterate 18 f= -1.47621D+01 |proj g|= 1.91682D-03
ys=-3.587E-03 -gs= 2.911E-01 BFGS update SKIPPED
At iterate 19 f= -1.49303D+01 |proj g|= 1.31439D-03
ys=-1.334E-03 -gs= 1.676E-01 BFGS update SKIPPED
At iterate 20 f= -1.51642D+01 |proj g|= 9.48153D-04
ys=-2.288E-03 -gs= 2.327E-01 BFGS update SKIPPED
At iterate 21 f= -1.53658D+01 |proj g|= 5.53753D-04
ys=-1.648E-03 -gs= 2.007E-01 BFGS update SKIPPED
At iterate 22 f= -1.57489D+01 |proj g|= 5.31741D-04
ys=-5.158E-03 -gs= 3.806E-01 BFGS update SKIPPED
At iterate 23 f= -1.57890D+01 |proj g|= 5.28557D-04
ys=-5.674E-05 -gs= 4.009E-02 BFGS update SKIPPED
At iterate 24 f= -1.57937D+01 |proj g|= 4.41902D-04
ys=-7.983E-07 -gs= 4.667E-03 BFGS update SKIPPED
At iterate 25 f= -1.58701D+01 |proj g|= 4.35916D-04
ys=-2.275E-04 -gs= 7.626E-02 BFGS update SKIPPED
At iterate 26 f= -1.58756D+01 |proj g|= 2.96303D-04
ys=-1.330E-06 -gs= 5.496E-03 BFGS update SKIPPED
At iterate 27 f= -1.59483D+01 |proj g|= 2.88718D-04
ys=-2.592E-04 -gs= 7.257E-02 BFGS update SKIPPED
At iterate 28 f= -1.59520D+01 |proj g|= 1.05300D-04
ys=-1.023E-06 -gs= 3.771E-03 BFGS update SKIPPED
At iterate 29 f= -1.59863D+01 |proj g|= 1.01328D-04
ys=-8.783E-05 -gs= 3.421E-02 BFGS update SKIPPED
At iterate 30 f= -1.59878D+01 |proj g|= 0.00000D+00
* * *
Tit = total number of iterations
Tnf = total number of function evaluations
Tnint = total number of segments explored during Cauchy searches
Skip = number of BFGS updates skipped
Nact = number of active bounds at final generalized Cauchy point
Projg = norm of the final projected gradient
F = final function value
* * *
N Tit Tnf Tnint Skip Nact Projg F
100 30 216 30 29 94 0.000D+00 -1.599D+01
F = -15.987807497724067
CONVERGENCE: NORM_OF_PROJECTED_GRADIENT_<=_PGTOL
Cauchy time 0.000E+00 seconds.
Subspace minimization time 0.000E+00 seconds.
Line search time 0.000E+00 seconds.
Total User time 0.000E+00 seconds.
10.0 100.0