Skip to content

Commit

Permalink
Refactor nlopt feature use
Browse files Browse the repository at this point in the history
  • Loading branch information
relf committed Oct 14, 2023
1 parent 2c59e05 commit 3ccf3da
Show file tree
Hide file tree
Showing 4 changed files with 125 additions and 181 deletions.
2 changes: 1 addition & 1 deletion ego/src/egor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -558,7 +558,7 @@ mod tests {
.q_points(2)
.qei_strategy(QEiStrategy::KrigingBeliever)
.doe(&doe)
.target(-5.508013)
.target(-5.5030)
.n_iter(30)
.run()
.expect("Egor minimization");
Expand Down
135 changes: 10 additions & 125 deletions ego/src/egor_solver.rs
Original file line number Diff line number Diff line change
Expand Up @@ -103,12 +103,8 @@ use crate::criteria::*;
use crate::egor_state::{find_best_result_index, EgorState, MAX_POINT_ADDITION_RETRY};
use crate::errors::{EgoError, Result};

#[cfg(feature = "nlopt")]
use crate::lhs_optimizer::LhsOptimizer;

use crate::mixint::*;

#[cfg(not(feature = "nlopt"))]
use crate::optimizer::*;

use crate::types::*;
Expand All @@ -121,10 +117,9 @@ use finitediff::FiniteDiff;
use linfa::ParamGuard;
use log::{debug, info, warn};
use ndarray::{
arr1, concatenate, s, Array, Array1, Array2, ArrayBase, ArrayView2, Axis, Data, Ix1, Ix2, Zip,
concatenate, s, Array, Array1, Array2, ArrayBase, ArrayView2, Axis, Data, Ix1, Ix2, Zip,
};
use ndarray_npy::{read_npy, write_npy};
use ndarray_rand::rand::SeedableRng;
use ndarray_stats::QuantileExt;

use rand_xoshiro::Xoshiro256Plus;
Expand Down Expand Up @@ -932,7 +927,6 @@ where
let (scale_infill_obj, scale_cstr, scale_wb2) =
self.compute_scaling(sampling, obj_model, cstr_models, *f_min);

#[cfg(not(feature = "nlopt"))]
let algorithm = match self.infill_optimizer {
InfillOptimizer::Slsqp => crate::optimizer::Algorithm::Slsqp,
InfillOptimizer::Cobyla => crate::optimizer::Algorithm::Cobyla,
Expand Down Expand Up @@ -1017,41 +1011,20 @@ where
}
})
.collect();
let cstr_refs: Vec<_> = cstrs.iter().map(|c| c.as_ref()).collect();

info!("Optimize infill criterion...");
let obj_data = ObjData {
scale_infill_obj,
scale_cstr: scale_cstr.to_owned(),
scale_wb2,
};
while !success && n_optim <= n_max_optim {
let x_start = sampling.sample(self.n_start);

if let Some(seed) = lhs_optim_seed {
let obj_data = ObjData {
scale_infill_obj,
scale_cstr: scale_cstr.to_owned(),
scale_wb2,
};
// let cstr_refs: Vec<&(dyn crate::types::ObjFn<ObjData<f64>> + Sync)> =
// cstrs.iter().map(|c| c.as_ref()).collect();
// let (x_opt, _) = LhsOptimizer::new(&self.xlimits, &obj, cstr_refs, &obj_data)
// .with_rng(Xoshiro256Plus::seed_from_u64(seed))
// .minimize()
// .unwrap();
// let (_, x_opt) =
// Optimizer::new(Algorithm::Lhs, &obj, cstr_refs, &obj_data, &self.xlimits)
// .seed(seed)
// .minimize();
#[cfg(feature = "nlopt")]
let cstr_refs: Vec<_> = cstrs.iter().map(|c| c.as_ref()).collect();
#[cfg(feature = "nlopt")]
let (_, x_opt) = LhsOptimizer::new(&self.xlimits, &obj, &cstr_refs, &obj_data)
.with_rng(Xoshiro256Plus::seed_from_u64(seed))
.minimize();

#[cfg(not(feature = "nlopt"))]
let cstr_refs: Vec<
&(dyn crate::types::ObjFn<ObjData<f64>> + Sync),
> = cstrs.iter().map(|c| c.as_ref()).collect();
#[cfg(not(feature = "nlopt"))]
let (_, x_opt) =
Optimizer::new(Algorithm::Lhs, &obj, cstr_refs, &obj_data, &self.xlimits)
Optimizer::new(Algorithm::Lhs, &obj, &cstr_refs, &obj_data, &self.xlimits)
.seed(seed)
.minimize();

Expand All @@ -1060,85 +1033,15 @@ where
success = true;
} else {
let dim = x_data.ncols();

let res = (0..self.n_start)
.into_par_iter()
.map(|i| {
#[cfg(feature = "nlopt")]
{
use nlopt::*;
let algorithm = match self.infill_optimizer {
InfillOptimizer::Slsqp => nlopt::Algorithm::Slsqp,
InfillOptimizer::Cobyla => nlopt::Algorithm::Cobyla,
};
let mut optimizer = Nlopt::new(
algorithm,
dim,
obj,
Target::Minimize,
ObjData {
scale_infill_obj,
scale_cstr: scale_cstr.to_owned(),
scale_wb2,
},
);
let lower = self.xlimits.column(0).to_owned();
optimizer
.set_lower_bounds(lower.as_slice().unwrap())
.unwrap();
let upper = self.xlimits.column(1).to_owned();
optimizer
.set_upper_bounds(upper.as_slice().unwrap())
.unwrap();
optimizer.set_maxeval(200).unwrap();
optimizer.set_ftol_rel(1e-4).unwrap();
optimizer.set_ftol_abs(1e-4).unwrap();
cstrs.iter().enumerate().for_each(|(i, cstr)| {
optimizer
.add_inequality_constraint(
cstr,
ObjData {
scale_infill_obj,
scale_wb2,
scale_cstr: scale_cstr.to_owned(),
},
self.cstr_tol / scale_cstr[i],
)
.unwrap();
});

let mut x_opt = x_start.row(i).to_vec();
match optimizer.optimize(&mut x_opt) {
Ok((_, opt)) => (opt, arr1(&x_opt)),
Err((err, code)) => {
debug!("Nlopt Err: {:?} (y_opt={})", err, code);
(f64::INFINITY, arr1(&x_opt))
}
}
}

#[cfg(not(feature = "nlopt"))]
{
let cstr_refs: Vec<&(dyn crate::types::ObjFn<ObjData<f64>> + Sync)> =
cstrs.iter().map(|c| c.as_ref()).collect();

Optimizer::new(
algorithm,
&obj,
cstr_refs,
&ObjData {
scale_infill_obj,
scale_cstr: scale_cstr.to_owned(),
scale_wb2,
},
&self.xlimits,
)
Optimizer::new(algorithm, &obj, &cstr_refs, &obj_data, &self.xlimits)
.xinit(&x_start.row(i))
.max_eval(200)
.ftol_rel(1e-4)
.ftol_abs(1e-4)
.minimize()
}
})
.reduce(
|| (f64::INFINITY, Array::ones((dim,))),
Expand All @@ -1155,26 +1058,8 @@ where

if n_optim == n_max_optim && best_x.is_none() {
info!("All optimizations fail => Trigger LHS optimization");
let obj_data = ObjData {
scale_infill_obj,
scale_cstr: scale_cstr.to_owned(),
scale_wb2,
};

#[cfg(feature = "nlopt")]
let cstr_refs: Vec<_> = cstrs.iter().map(|c| c.as_ref()).collect();
#[cfg(feature = "nlopt")]
let (_, x_opt) = LhsOptimizer::new(&self.xlimits, &obj, &cstr_refs, &obj_data)
.with_rng(Xoshiro256Plus::from_entropy())
.minimize();

#[cfg(not(feature = "nlopt"))]
let cstr_refs: Vec<
&(dyn crate::types::ObjFn<ObjData<f64>> + Sync),
> = cstrs.iter().map(|c| c.as_ref()).collect();
#[cfg(not(feature = "nlopt"))]
let (_, x_opt) =
Optimizer::new(Algorithm::Lhs, &obj, cstr_refs, &obj_data, &self.xlimits)
Optimizer::new(Algorithm::Lhs, &obj, &cstr_refs, &obj_data, &self.xlimits)
.minimize();

info!("LHS optimization best_x {}", x_opt);
Expand Down
4 changes: 1 addition & 3 deletions ego/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -194,10 +194,8 @@ mod errors;
mod mixint;
mod types;

#[cfg(not(feature = "nlopt"))]
mod optimizer;

mod lhs_optimizer;
mod optimizer;
mod sort_axis;
mod utils;

Expand Down
Loading

0 comments on commit 3ccf3da

Please sign in to comment.