Skip to content

4. Contribution guide

Iannick Gagnon edited this page May 22, 2025 · 12 revisions

Introduction

Thank you for your interest in contributing to MDAF_benchmarks.

We welcome all kinds of contributions: bug reports, documentation improvements, new objective functions, or code enhancements.

To get started:

  1. Clone the repository:
> git clone https://github.com/iannickgagnon/MDAF_benchmarks.git
> cd MDAF_benchmarks
  1. Install in editable developer mode with dependencies:
> pip install -e .[dev]

This installs the required packages and developer tools (e.g., pre-commit, pytest, black, isort), and enables live editing without the need for reinstalls. You can execute the pre-commit run command, which will launch the hooks defined in pre-commit-config.yaml.

Code style

Your submission will be automatically checked by the repository's GitHub Actions, using the same rules defined in .pre-commit-config.yaml.

To run these checks locally before pushing:

> pip install pre-commit
> pre-commit install
> pre-commit run --all-files

This ensures your code passes formatting, linting, and static analysis checks before opening a pull request.

Docstrings

All public classes and functions must include docstrings in Google style [link].

Example:

class Ackley(of.ObjectiveFunction):
    """
    Ackley objective function implementation.

    This class implements the Ackley function, a widely used benchmark for evaluating optimization algorithms.
    The function is characterized by a nearly flat outer region and a steep central basin, making it challenging
    for algorithms to locate the global minimum.

    Attributes:
        parameters (dict): Dictionary containing the parameters 'A', 'B', and 'C' for the Ackley function.
        settings (DefaultSettings): Object containing the search space and other configuration values.

    Methods:
        __init__(parameters: dict = {}, settings: DefaultSettings = {}):
            Initializes the function with given parameters and settings, applying defaults if needed.
        evaluate(position: np.ndarray) -> float:
            Computes the function value at the given position.

    Reference:
        https://github.com/iannickgagnon/MDAF_benchmarks/wiki/Ackley
    """

Best practices

  • Prioritize readability and maintainability over cleverness.
  • Use clear variable names and modular functions.
  • Avoid overly complex one-liners or micro-optimizations.
  • Follow Python conventions from PEP 8.

Adding a new objective function

To add a new function, it is strongly recommended to start by looking at pre-existing ones.

Here are the general steps:

  1. Create a new file in src/MDAF_benchmarks/implementations/ named after the function in snake_case.py.
  2. (optional) Define default parameters using a dict as a top-level symbolic constant.
  3. Add default parameters and bounds using DefaultSettings as a top-level symbolic constant.
  4. Define a class with the same name in PascalCase, inheriting from ObjectiveFunction.
  5. Add the @ObjectiveFunction.constructor decorator to the constructor.
    • Call the self.validate_parameters() only if your function has mutable parameters.
    • Call the self.validate_settings() method.
  6. Implement the .evaluate() method, where the core logic of your function lives.
  7. Add your function to the top-level API by running dev/update_auto_imports.py.
  8. Add a demo image to doc/img/ using the function_name_demo.png format. It will be used in your function's Wiki entry.

Submitting a pull request

  1. Fork the repository and create a new branch:
> git checkout -b feature/my-new-function
  1. Make your changes, commit, and push:
> git commit -m "Add XYZ objective function"
> git push origin feature/my-new-function
  1. Open a pull request from your forked repository on GitHub.

Please describe your changes clearly and link any related issues.

Clone this wiki locally