#  MOBO-OSD: Batch Multi-Objective Bayesian Optimization via Orthogonal Search Directions

## Overview

Implementation code for paper ***MOBO-OSD: Batch Multi-Objective Bayesian Optimization via Orthogonal Search Directions*** published in *The 39th Annual Conference on Neural Information Processing Systems (NeurIPS-2025)*. The manuscript will be available soon.

![illustration of boids](mobo-osd-illustration-github.png)

If you find our paper or this repo to be useful for your research, please consider citing:
```
@article{ngo2025moboosd,
  title={MOBO-OSD: Batch Multi-Objective Bayesian Optimization via Orthogonal Search Directions},
  author={Ngo, Lam and Ha, Huong and Chan, Jeffrey and Zhang, Hongyu},
  journal={Advances in neural information processing systems},
  year={2025}
}
```

## Requirement and dependencies
- Install Miniconda.
- Install all dependencies listed in ```env.yml``` file, or run the following to install via conda. This will create env ```mobo-osd``` in conda.
```
conda env create -f env.yml
```

## Getting started
The main file is ```test-mobo-osd.py```. To run the code for any problem, use the following syntax:
```
python test-mobo-osd.py -f <function_name> -d <input_dim> -m <number_of_objectives> -n <number_of_iterations>
```
The above command only list required arguments. Please check the following table for optional arguments, as well as possible values for each arguments.

| Flag &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;| Description |
| --- | --- | 
| -f | A string to specify the objective function. Examples from the paper include ```zdt1```, ```dtlz2```, ```vlmop2```, ```speed-reducer```, ```car-impact```, ```marine-design```, and ```water-planning```. See ```_test_functions/get_function.py``` for more options. |
| -d | An integer to specify the objective function input dimensionality. Only required for scalable synthetic functions, e.g., ```dtlz2```, ```zdt1```. See ```_test_functions/get_function.py``` for more options. |
| -m | An integer to specify the number of objectives. Only required for some synthetic functions, e.g., ```dtlz2```. See ```_test_functions/get_function.py``` for more options. |
| -n | An integer to specify the iteration budget. |
| -b | (Optional) An integer to specify the batch size. Default value is ```10```. |
| --n_beta | (Optional) An integer to specify the number of discretized points on the approximated CHIM. Default value is ```20```. |
| --n_init | (Optional) An integer to specify the number of random initialization. Default value is ```20```. |
| --seed | (Optional) An integer to specify the random seed for random number generator. Default is ```1```. |


## Results from paper
To produce the main experimental results in the paper (Figures 2, 3, 8 and 9), run the bash file ```experiments-from-paper.sh```.

# Acknowledgements

This code implementation uses materials from the following public repositories to implemenent the first order approximation step [1] and the qHVI acquisition function [2]. We thank the respective repository maintainers.

[1] DGEMO: Konakovic Lukovic, M., Tian, Y., & Matusik, W. (2020). Diversity-guided multi-objective bayesian optimization with batch evaluations. Advances in Neural Information Processing Systems, 33, (NeurIPS).
   Code repo: https://github.com/yunshengtian/DGEMO

[2] qEHVI: Daulton, S., Balandat, M., & Bakshy, E. (2020). Differentiable expected hypervolume improvement for parallel multi-objective Bayesian optimization. Advances in Neural Information Processing Systems, 33, (NeurIPS).
   Code repo: https://github.com/pytorch/botorch
