Getting Started with globalMOO
Welcome to the globalMOO API documentation. This guide will help you get started with using our API and SDKs.
Overview
globalMOO provides a powerful API for multi-objective optimization. With our API, you can:
Create and manage optimization models
Define objectives and constraints
Run optimization trials
Analyze results
Installation
Choose your preferred SDK:
pip install globalmoo-sdk
Quick Start
Here's a simple example to get you started:
"""
Example showing optimization of a simple linear system of equations.
This example demonstrates how to use globalMOO to find inputs that produce
specific outputs in a 3-input, 5-output linear system. It illustrates:
1. Setting up a model with proper input and output specifications
2. Creating a project with appropriate boundaries
3. Using percentage-based objectives for optimization
4. Running the inverse optimization process with customizable convergence criteria
5. Interpreting optimization results and solution quality
Linear systems are ideal for demonstrating globalMOO's capabilities since
they have clear mathematical relationships between inputs and outputs,
making it easier to understand the optimization process.
"""
from typing import List
from dotenv import load_dotenv
from globalmoo.client import Client
from globalmoo.request.create_model import CreateModel
from globalmoo.request.create_project import CreateProject
from globalmoo.request.load_output_cases import LoadOutputCases
from globalmoo.request.load_objectives import LoadObjectives
from globalmoo.request.suggest_inverse import SuggestInverse
from globalmoo.request.load_inversed_output import LoadInversedOutput
from globalmoo.enums.input_type import InputType
from globalmoo.enums.objective_type import ObjectiveType
from globalmoo.utils.console import (
print_satisfaction_status,
print_section_header,
print_values,
print_info,
print_success
)
def LinearTestFunction(input: List[float]) -> List[float]:
"""
Simple linear problem with 3 inputs and 5 outputs.
This function defines a system of linear equations where each output
is a linear combination of the inputs with different coefficients.
In real applications, this could represent:
- Chemical processes where reactant concentrations affect multiple product yields
- Financial models where investment allocations affect multiple performance metrics
- Engineering systems where control parameters affect multiple performance indicators
Args:
input (List[float]): List of 3 input values [v01, v02, v03]
Returns:
List[float]: List of 5 output values representing different linear combinations
"""
v01 = input[0]
v02 = input[1]
v03 = input[2]
# Each output is a distinct linear combination of inputs
# The coefficients represent different sensitivities to each input
o01 = 1.25 * v01 + 2.0 * v02 + 2.75 * v03
o02 = 1.19 * (v01 - 2.0) + 0.71 * (v02 - 2.0) + 0.51 * v03
o03 = 1.11 * (v01 - 2.0) + 0.65 * v02 + 0.56 * (v03 - 2.0)
o04 = 1.02 * v01 + 0.49 * (v02 - 2.0) + 0.62 * (v03 - 2.0)
o05 = 3.0 * v01 + 2.0 * v02 + 1.0 * v03
return [o01, o02, o03, o04, o05]
def main():
# Load environment variables
load_dotenv()
# Model configuration - matching SimpleExample
# These constants define the characteristics of our optimization problem
MODEL_NAME = "SimpleExample"
INPUT_COUNT = 3 # Number of input variables
OUTPUT_COUNT = 5 # Number of output variables
MIN_VALUES = [0.0, 0.0, 0.0] # Lower bounds for inputs
MAX_VALUES = [10.0, 10.0, 10.0] # Upper bounds for inputs
INPUT_TYPES = [InputType.FLOAT, InputType.FLOAT, InputType.FLOAT] # All inputs are floating-point
# Convergence criteria - how close we need to be to the target
# These define when the optimization is considered successful
PERCENT_BELOW = [-1.0, -1.0, -1.0, -1.0, -1.0] # Allow 1% below target
PERCENT_ABOVE = [ 1.0, 1.0, 1.0, 1.0, 1.0] # Allow 1% above target
# "Truth case" - the target input values we're trying to find
# In real applications, you would only know the desired outputs, not the inputs
TRUTHCASE = [5.4321, 5.4321, 5.4321]
# Calculate the target outputs from our truth case
# These are the output values we'll try to achieve through optimization
objectives = LinearTestFunction(TRUTHCASE)
# All objectives use percentage-based convergence criteria
OBJECTIVE_TYPES = [ObjectiveType.PERCENT] * OUTPUT_COUNT
# Define the starting point for your inverse solution process
# This is where the optimization algorithm will begin searching
INITIAL_INPUT = [5.0, 5.0, 5.0]
INITIAL_OUTPUT = LinearTestFunction(INITIAL_INPUT)
try:
# Initialize the client
client = Client()
print(client)
print_info("Successfully initialized globalMOO client")
# STEP 1: Create a model
# Models are the top-level containers for your optimization data
model = client.execute_request(CreateModel(
name=MODEL_NAME,
description="Demonstration of optimization for a simple linear system of equations"
))
print_info(f"Created model with ID: {model.id}")
# STEP 2: Create a project for the model
# Projects define the input and output characteristics
project = client.execute_request(CreateProject(
model_id=model.id,
name="Linear Model Project",
input_count=INPUT_COUNT,
minimums=MIN_VALUES,
maximums=MAX_VALUES,
input_types=INPUT_TYPES,
categories=[] # Set to empty list, no categorical variables
))
print_info(f"Created project with ID: {project.id}")
# Get input cases from the project
# globalMOO generates test points to explore the input space
input_cases = project.input_cases
print_info(f"Received {len(input_cases)} input cases")
# STEP 3: Run inputs locally to compute outputs
# In real applications, this might involve running simulations or experiments
output_cases = [LinearTestFunction(single_case) for single_case in input_cases]
print_info(f"Computed {len(output_cases)} output cases")
# STEP 4: Create trial by loading the output cases
# A trial represents a set of evaluations of your model
trial = client.execute_request(LoadOutputCases(
project_id=project.id,
output_count=OUTPUT_COUNT,
output_cases=output_cases
))
print_info(f"Successfully created trial with ID: {trial.id}")
# STEP 5: Initialize inverse with values matching SimpleExample
# This defines what outputs we're trying to achieve and how close we need to be
objective = client.execute_request(LoadObjectives(
trial_id=trial.id,
objectives=objectives, # Target output values
objective_types=OBJECTIVE_TYPES, # Type of objective for each output
initial_input=INITIAL_INPUT, # Starting point for optimization
initial_output=INITIAL_OUTPUT, # Output at starting point
minimum_bounds=PERCENT_BELOW, # Lower acceptable bounds
maximum_bounds=PERCENT_ABOVE, # Upper acceptable bounds
desired_l1_norm=0.0 # Target error (0 = perfect match)
))
print_info("Initialized inverse optimization")
# STEP 6: Run optimization loop
# This is where globalMOO iteratively suggests new inputs to try
max_iterations = 20
for iteration in range(max_iterations):
# Get next suggested experiment
inverse = client.execute_request(SuggestInverse(
objective_id=objective.id
))
print_info(f"Iteration {iteration + 1}: Received suggestion")
# Run the experiment (our test function)
# In real applications, this would be your experiment or simulation
next_output = LinearTestFunction(inverse.input)
# Load the experimental results
# This helps globalMOO improve its next suggestion
inverse = client.execute_request(LoadInversedOutput(
inverse_id=inverse.id,
output=next_output
))
# Log detailed results with nice formatting
print_section_header("Current solution details:")
print_values("Input", inverse.input)
print_values("Output", next_output)
print_values("Target", objective.objectives)
if inverse.results:
for i, result in enumerate(inverse.results):
print_satisfaction_status(i, result.satisfied, result.detail)
print_info(f" Type: {result.objective_type}")
print_info(f" Error: {result.error}")
# Check if we need to stop
# globalMOO will indicate when it has found a satisfactory solution
if inverse.should_stop():
print_info(f"Optimization stopped: {inverse.get_stop_reason().description()}")
break
print_info(f"Completed iteration {iteration + 1}")
# STEP 7: Report final results
print_section_header("Final Results")
if inverse.satisfied_at:
print_success("Solution satisfied all objectives!")
print_section_header("Satisfaction details:")
for i, (satisfied, detail) in enumerate(zip(inverse.get_satisfaction_status(), inverse.get_result_details())):
print_satisfaction_status(i, satisfied, detail)
else:
print_info("Solution did not satisfy all objectives")
print_section_header("Status per objective:")
for i, (satisfied, detail) in enumerate(zip(inverse.get_satisfaction_status(), inverse.get_result_details())):
print_satisfaction_status(i, satisfied, detail)
print_section_header("Final solution:")
print_values("Input values", inverse.input)
print_values("Output values", next_output)
print_values("Target values", objective.objectives)
print_values("Error values", inverse.get_objective_errors(), precision=6)
finally:
# Clean up resources
if 'client' in locals():
client.http_client.close()
print_info("Closed client connection")
if __name__ == "__main__":
main()
Interactive Tutorial
Try globalMOO directly in your browser with our interactive Google Colab notebook:
This notebook walks through a complete example of using globalMOO to optimize a simple linear system.
Next Steps
Learn about Authentication
Explore our Core Concepts
Check out the Quickstart Guide
Last updated