Skip to main content

GPU runner: binary/grid search over experiment configs with GPU scheduling

Project description

gpusweep

A Python framework to run binary and grid search over experiment pydrafig configurations with GPU resource management.

Features

  • Binary Search: Run a binary search over parameters of experiment configs
  • Grid Search: Run a grid search over parameters of experiment configs

Installation

Install (editable, best for development):

pip install -e .

Install from PyPI:

pip install gpusweep

Quick Start

1. Define Your Experiment

Create an experiment configuration and run function. Experiment configs must inherit from BaseExperimentConfig:

from pydrafig import pydraclass, main
from gpusweep.configs.base_experiment_config import BaseExperimentConfig

@pydraclass
class DummyExperimentConfig(BaseExperimentConfig):
    name: str = "dummy_experiment"
    num_parameters: int = 10
    seed: int = 42

def run_experiment(config: DummyExperimentConfig):
    # Your experiment logic here
    result = perform_training(config)
    return result

@main(DummyExperimentConfig)
def main(config: DummyExperimentConfig):
    run_experiment(config)

2. Binary Search

Find the optimal value for a hyperparameter using binary search:

from gpusweep.binary_search import run_binary_searches
from gpusweep.configs.search_configs import BinarySearchConfig
from examples.dummy_experiment import run_experiment, DummyExperimentConfig
import copy
import numpy as np

@pydraclass
class ExperimentBinarySearchConfig(BinarySearchConfig):
    def get_experiment_config_and_base_dir(self, num_parameters: int, seed: int):
        config = copy.deepcopy(self.base_experiment_config)
        config.num_parameters = num_parameters
        config.seed = seed
        config.base_dir = f"{self.base_dir}/num_parameters_{num_parameters}_seed_{seed}"
        config.finalize()
        return config, config.base_dir

    def run_experiment_config(self, config):
        return run_experiment(config)

    def agg_results(self, results: list[GPUJobResult]) -> tuple[bool, Any]:
        # Aggregate results across seeds
        results = [r for r in results if r.success]
        if len(results) == 0:
            return False, None
        best_idx = np.argmax([r.result for r in results])
        result = results[best_idx]
        # Return (success, result) - success is True if result >= threshold
        return result.result >= 0.5, result

# Run binary search
configs = [ExperimentBinarySearchConfig(
    base_dir="./results/binary_search",
    prop="num_parameters",  # Property to search over
    range=(10, 100),         # Search range
    precision=1,             # Precision for stopping
    success_direction_lower=True,  # True if lower values are better
    sweep_props={"seed": [42, 43, 44, 45]},  # Other properties to sweep (these will get aggregated in agg_results!)
    base_experiment_config=DummyExperimentConfig(name="experiment_1"),
)]

run_binary_searches(configs, max_gpus=4, simultaneous_jobs_per_gpu=2)

3. Grid Search

Exhaustively search all combinations of hyperparameters:

from gpusweep.grid_search import run_grid_searches
from gpusweep.configs.search_configs import GridSearchConfig
from examples.dummy_experiment import run_experiment, DummyExperimentConfig
import copy
import numpy as np

@pydraclass
class ExperimentGridSearchConfig(GridSearchConfig):
    def get_experiment_config_and_base_dir(self, num_parameters: int, seed: int):
        config = copy.deepcopy(self.base_experiment_config)
        config.num_parameters = num_parameters
        config.seed = seed
        config.base_dir = f"{self.base_dir}/num_parameters_{num_parameters}_seed_{seed}"
        config.finalize()
        return config, config.base_dir

    def run_experiment_config(self, config):
        return run_experiment(config)

    def agg_results(self, results: list[GPUJobResult]):
        # Aggregate results across all sweep_props points
        results = [r for r in results if r.success]
        if len(results) == 0:
            return None
        # Return best result
        best_idx = np.argmax([r.result for r in results])
        return results[best_idx]

# Run grid search
configs = [ExperimentGridSearchConfig(
    base_dir=f"./results/grid_search_{num_parameters}",
    sweep_props={
        "seed": [42, 43, 44, 45]
    },
    base_experiment_config=DummyExperimentConfig(name="experiment_1", num_parameters=num_parameters),
) for num_parameters in [10, 20, 30, 40]]

run_grid_searches(configs, max_gpus=4, simultaneous_jobs_per_gpu=2)

Running Examples

The examples/ directory contains complete working examples that demonstrate how to use the framework:

Basic Experiment

Run a simple experiment:

cd examples
python dummy_experiment.py

Binary Search Example

Run the binary search example:

cd examples
python example_binary_search.py

This will run multiple binary searches in parallel, finding optimal values for num_parameters across different experiment configurations.

Grid Search Example

Run the grid search example:

cd examples
python example_grid_search.py

This will run multiple grid searches, exhaustively testing combinations of hyperparameters.

Note: Make sure you have the package installed (pip install -e .) and that you're running from the project root or have the proper Python path configured.

Architecture

Configuration System

The framework uses a strict configuration system based on dataclasses with the @pydraclass decorator:

  • Strict Validation: Prevents typos by validating attribute names
  • Nested Configs: Support for nested configuration objects
  • Finalization: Automatic recursive finalization of configs
  • CLI Support: Built-in CLI argument parsing
  • Base Experiment Config: All experiment configs must inherit from BaseExperimentConfig, which provides the base_dir field

See configs/README.md for detailed documentation on the configuration system.

GPU Scheduling

The GPUScheduler manages GPU resources:

  • Round-robin Assignment: Jobs are distributed across available GPUs
  • Concurrent Execution: Multiple jobs can run simultaneously on each GPU
  • Process Isolation: Each job runs in a separate process with proper CUDA device isolation
  • Error Handling: Failed jobs are tracked and reported

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

gpusweep-0.0.1.tar.gz (9.7 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

gpusweep-0.0.1-py3-none-any.whl (10.1 kB view details)

Uploaded Python 3

File details

Details for the file gpusweep-0.0.1.tar.gz.

File metadata

  • Download URL: gpusweep-0.0.1.tar.gz
  • Upload date:
  • Size: 9.7 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.7

File hashes

Hashes for gpusweep-0.0.1.tar.gz
Algorithm Hash digest
SHA256 a07791aa28b08e46690e9da0f3ba8ca9b71c8f99bd28ea76fb183a0b8f79c5b5
MD5 344d788e83986a2ef725519ffe94da4c
BLAKE2b-256 18c336a59856de980d4a5905bc40f0bb1ca1569076d1a59794779a72fd355e43

See more details on using hashes here.

File details

Details for the file gpusweep-0.0.1-py3-none-any.whl.

File metadata

  • Download URL: gpusweep-0.0.1-py3-none-any.whl
  • Upload date:
  • Size: 10.1 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.7

File hashes

Hashes for gpusweep-0.0.1-py3-none-any.whl
Algorithm Hash digest
SHA256 5e07c0a822533814e34e3cf3defa238460c28db88ae772a9a1c1f2a61a921aab
MD5 2cc4b3c046020ae447f98e8422537384
BLAKE2b-256 40ecf0150140a0b0885d0f41feb708a2cf14b4762c3056414628113307c48024

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page