| |
| |
| |
| |
| |
|
|
| """ |
| Efficiency Grader -- penalises excessive AND insufficient circuit complexity. |
| |
| Scores circuits based on how well their depth and gate count match |
| the expected complexity for the given task. Too-short circuits are penalized |
| because they likely haven't solved the task. |
| """ |
|
|
| import logging |
|
|
| logger = logging.getLogger(__name__) |
|
|
|
|
| class EfficiencyGrader: |
| """Evaluate circuit efficiency relative to task constraints.""" |
|
|
| @staticmethod |
| def grade( |
| depth: int, |
| gate_count: int, |
| max_depth: int, |
| max_gate_count: int, |
| min_expected_gates: int = 0, |
| ) -> float: |
| """ |
| Compute efficiency score. |
| |
| Penalizes both over-complexity (exceeding limits) and under-complexity |
| (circuits with fewer gates than the minimum expected for this task). |
| |
| Args: |
| depth: Current circuit depth. |
| gate_count: Current total gate count. |
| max_depth: Maximum allowed depth from task config. |
| max_gate_count: Maximum allowed gate count from task config. |
| min_expected_gates: Minimum number of gates expected for a correct |
| solution. Circuits below this are penalized. |
| |
| Returns: |
| Efficiency score in [0.0, 1.0]. |
| """ |
| if max_depth <= 0: |
| max_depth = 1 |
| if max_gate_count <= 0: |
| max_gate_count = 1 |
|
|
| |
| depth_ratio = depth / max_depth |
| if depth_ratio <= 1.0: |
| depth_score = 1.0 - depth_ratio * 0.5 |
| else: |
| depth_score = max(0.0, 1.0 - depth_ratio) |
|
|
| |
| gate_ratio = gate_count / max_gate_count |
| if gate_ratio <= 1.0: |
| gate_score = 1.0 - gate_ratio * 0.5 |
| else: |
| gate_score = max(0.0, 1.0 - gate_ratio) |
|
|
| score = (depth_score + gate_score) / 2.0 |
|
|
| logger.debug( |
| "Efficiency: depth=%d/%d (%.2f), gates=%d/%d (%.2f), " |
| "min_expected=%d, score=%.4f", |
| depth, max_depth, depth_score, |
| gate_count, max_gate_count, gate_score, |
| min_expected_gates, score, |
| ) |
|
|
| return float(max(0.0, min(1.0, score))) |
|
|