Skip to main content
The evaluator is the only problem-specific code you write. It defines the optimization objective and provides feedback to guide the LLM.

Basic Structure

An evaluator is a Python file with an evaluate() function:
SkyDiscover calls evaluate() in an isolated process with timeout and retry. You don’t need to handle exceptions or timeouts yourself.

Return Format

Metrics

Numeric values that measure program quality:
Combined Score:
  • SkyDiscover maximizes this value
  • If omitted, averages all numeric metrics
  • Should be in range [0, 1] for best results

Artifacts

Textual feedback injected into the next LLM prompt:
Artifacts help the LLM:
  • Understand why the score is low
  • Identify specific issues to fix
  • Learn from failure patterns

Real Examples

Example 1: Circle Packing

Problem: Pack 26 circles in a unit square to maximize sum of radii.
Key Points:
  • Run in subprocess with timeout for safety
  • Validation checks (bounds, overlaps)
  • Normalize score to [0, 1] range
  • Provide actionable feedback in artifacts
Source: benchmarks/math/circle_packing/evaluator.py:184

Example 2: Cloud Broadcast Optimization

Problem: Minimize cost of broadcasting data across cloud regions.
Key Points:
  • Test on multiple configurations for robustness
  • Validate output structure before evaluation
  • Transform cost to score (lower cost → higher score)
  • Report detailed metrics for analysis
Source: benchmarks/ADRS/cloudcast/evaluator.py:122

Example 3: GPU Kernel Optimization

Problem: Optimize CUDA kernel performance.
Key Points:
  • Separate correctness from performance
  • Test multiple problem sizes
  • Compare against baseline
  • Normalize speedup to [0, 1] score
Source: benchmarks/gpu_mode/vecadd/evaluator.py

Cascade Evaluation

For expensive evaluations, use two-stage cascade to save time: Stage 1: Fast validation (syntax, basic tests)
Stage 2: Full evaluation (only if stage 1 passes threshold)
Configuration:
SkyDiscover automatically runs stage1 → threshold check → stage2 and merges metrics. Source: benchmarks/math/circle_packing/evaluator.py:279

Best Practices

1. Normalize Scores

Always normalize combined_score to [0, 1] range:

2. Provide Actionable Feedback

3. Handle Errors Gracefully

4. Use Subprocess for Safety

Isolate program execution to prevent crashes:

5. Report Multiple Metrics

Helps with analysis and multi-objective optimization:

6. Test on Multiple Cases

Common Patterns

Correctness + Performance

Cost Minimization

Multi-Objective

Configuration

Evaluator behavior is controlled via config.yaml:
See Configuration Guide for all options.

Debugging

Enable prompt logging to see what’s sent to the LLM:
Inspect evaluation errors:

Evolution Blocks

Control which code regions get evolved

Architecture

How evaluators integrate with the framework