FAILURE MAP
← Case archive

FA-65436 / Ecological population dynamics / Open access

Holling functional response consumption: type II handling term · case 01

Intake saturates at the wrong prey density.

Verified by executionVariant 1 · 7 checks per implementationDownload source bundle ↓JSON ↗

ROOT CAUSE

The attack rate is missing from the handling-time denominator.

VERIFIED REPAIR

Restore the type II handling term rule: `a * prey / (1 + a * h * prey)`.

Unsuccessful approach: Omitting prey density from the denominator removes saturation.

Case contract

Per-predator intake f: type 1 = a*N capped at 1/h (uncapped when h==0), type 2 = aN/(1+ahN), type 3 = aN^2/(1+ahN^2); eaten = min(f*predators*duration, N); return [f rounded 6, eaten rounded 4]; None for negative parameters or unknown kind.

Why this case matters

Population projections set harvest quotas, conservation status and pest-control timing; a wrong update order, boundary or rate conversion silently changes management advice.

1 / The failure

Exit 1
"""Failure Map reference implementation. Python standard library only."""
import json
import math
N = 1
observations = []
def solve(kind, a, h, prey, predators, duration):
    if a < 0 or h < 0 or prey < 0:
        return None
    if kind == 1:
        f = a * prey if h == 0 else min(a * prey, 1 / h)
    elif kind == 2:
        f = a * prey / (1 + h * prey)
    elif kind == 3:
        f = a * prey ** 2 / (1 + a * h * prey ** 2)
    else:
        return None
    eaten = min(f * predators * duration, prey)
    return [round(f, 6), round(eaten, 4)]
def check(label, actual, expected):
    observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[('control: type 1 saturated filter feeder', (1, 0.5, 0.25, 20, 2, 1), [4.0, 8.0]),
  ('control: type 1 unsaturated', (1, 0.1, 0.5, 10, 1, 2), [1.0, 2.0]),
  ('control: type 1 no handling', (1, 0.3, 0.0, 40, 1, 1), [12.0, 12.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: type 3 prey switching', (3, 0.05, 0.2, 12, 2, 3), [2.95082, 12]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752])],
 [('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: type 3 prey switching', (3, 0.05, 0.2, 12, 2, 3), [2.95082, 12]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752]),
  ('regression: depletion cap', (2, 2.0, 0.05, 10, 20, 5), [10.0, 10]),
  ('control: unknown kind', (4, 0.1, 0.1, 10, 1, 1), None),
  ('control: no prey', (2, 0.5, 0.5, 0, 2, 1), [0.0, 0.0])],
 [('control: type 1 saturated filter feeder', (1, 0.5, 0.25, 20, 2, 1), [4.0, 8.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752]),
  ('regression: depletion cap', (2, 2.0, 0.05, 10, 20, 5), [10.0, 10]),
  ('control: unknown kind', (4, 0.1, 0.1, 10, 1, 1), None),
  ('control: no prey', (2, 0.5, 0.5, 0, 2, 1), [0.0, 0.0]),
  ('control: invalid negative handling', (2, 0.5, -0.1, 10, 1, 1), None)],
 [('control: type 1 saturated filter feeder', (1, 0.5, 0.25, 20, 2, 1), [4.0, 8.0]),
  ('control: type 1 unsaturated', (1, 0.1, 0.5, 10, 1, 2), [1.0, 2.0]),
  ('control: type 1 no handling', (1, 0.3, 0.0, 40, 1, 1), [12.0, 12.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: no prey', (2, 0.5, 0.5, 0, 2, 1), [0.0, 0.0]),
  ('control: invalid negative handling', (2, 0.5, -0.1, 10, 1, 1), None)],
 [('control: type 1 unsaturated', (1, 0.1, 0.5, 10, 1, 2), [1.0, 2.0]),
  ('control: type 1 no handling', (1, 0.3, 0.0, 40, 1, 1), [12.0, 12.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: type 3 prey switching', (3, 0.05, 0.2, 12, 2, 3), [2.95082, 12]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752]),
  ('regression: depletion cap', (2, 2.0, 0.05, 10, 20, 5), [10.0, 10])]]
for label, args, expected in fixtures[N - 1]:
    check(label, solve(*args), expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
Boundary fixtureActualExpectedOutcome
control: type 1 saturated filter feeder[4.0, 8.0][4.0, 8.0]Passed
control: type 1 unsaturated[1.0, 2.0][1.0, 2.0]Passed
control: type 1 no handling[12.0, 12.0][12.0, 12.0]Passed
regression: type 2 wolves on moose[1.5, 9.0][1.846154, 11.0769]Failed
regression: type 2 low density[0.461538, 0.4615][0.566038, 0.566]Failed
control: type 3 prey switching[2.95082, 12][2.95082, 12]Passed
control: type 3 high density[2.475248, 2.4752][2.475248, 2.4752]Passed

SHA-256 / b551e35fcefee7852f8a8997b61a8fbd89c59d14428efb4e4fcb01c951618bcf

2 / The unsuccessful fix

Exit 1
"""Failure Map reference implementation. Python standard library only."""
import json
import math
N = 1
observations = []
def solve(kind, a, h, prey, predators, duration):
    if a < 0 or h < 0 or prey < 0:
        return None
    if kind == 1:
        f = a * prey if h == 0 else min(a * prey, 1 / h)
    elif kind == 2:
        f = a * prey / (1 + a * h)
    elif kind == 3:
        f = a * prey ** 2 / (1 + a * h * prey ** 2)
    else:
        return None
    eaten = min(f * predators * duration, prey)
    return [round(f, 6), round(eaten, 4)]
def check(label, actual, expected):
    observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[('control: type 1 saturated filter feeder', (1, 0.5, 0.25, 20, 2, 1), [4.0, 8.0]),
  ('control: type 1 unsaturated', (1, 0.1, 0.5, 10, 1, 2), [1.0, 2.0]),
  ('control: type 1 no handling', (1, 0.3, 0.0, 40, 1, 1), [12.0, 12.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: type 3 prey switching', (3, 0.05, 0.2, 12, 2, 3), [2.95082, 12]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752])],
 [('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: type 3 prey switching', (3, 0.05, 0.2, 12, 2, 3), [2.95082, 12]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752]),
  ('regression: depletion cap', (2, 2.0, 0.05, 10, 20, 5), [10.0, 10]),
  ('control: unknown kind', (4, 0.1, 0.1, 10, 1, 1), None),
  ('control: no prey', (2, 0.5, 0.5, 0, 2, 1), [0.0, 0.0])],
 [('control: type 1 saturated filter feeder', (1, 0.5, 0.25, 20, 2, 1), [4.0, 8.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752]),
  ('regression: depletion cap', (2, 2.0, 0.05, 10, 20, 5), [10.0, 10]),
  ('control: unknown kind', (4, 0.1, 0.1, 10, 1, 1), None),
  ('control: no prey', (2, 0.5, 0.5, 0, 2, 1), [0.0, 0.0]),
  ('control: invalid negative handling', (2, 0.5, -0.1, 10, 1, 1), None)],
 [('control: type 1 saturated filter feeder', (1, 0.5, 0.25, 20, 2, 1), [4.0, 8.0]),
  ('control: type 1 unsaturated', (1, 0.1, 0.5, 10, 1, 2), [1.0, 2.0]),
  ('control: type 1 no handling', (1, 0.3, 0.0, 40, 1, 1), [12.0, 12.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: no prey', (2, 0.5, 0.5, 0, 2, 1), [0.0, 0.0]),
  ('control: invalid negative handling', (2, 0.5, -0.1, 10, 1, 1), None)],
 [('control: type 1 unsaturated', (1, 0.1, 0.5, 10, 1, 2), [1.0, 2.0]),
  ('control: type 1 no handling', (1, 0.3, 0.0, 40, 1, 1), [12.0, 12.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: type 3 prey switching', (3, 0.05, 0.2, 12, 2, 3), [2.95082, 12]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752]),
  ('regression: depletion cap', (2, 2.0, 0.05, 10, 20, 5), [10.0, 10])]]
for label, args, expected in fixtures[N - 1]:
    check(label, solve(*args), expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
Boundary fixtureActualExpectedOutcome
control: type 1 saturated filter feeder[4.0, 8.0][4.0, 8.0]Passed
control: type 1 unsaturated[1.0, 2.0][1.0, 2.0]Passed
control: type 1 no handling[12.0, 12.0][12.0, 12.0]Passed
regression: type 2 wolves on moose[17.142857, 30][1.846154, 11.0769]Failed
regression: type 2 low density[0.588235, 0.5882][0.566038, 0.566]Failed
control: type 3 prey switching[2.95082, 12][2.95082, 12]Passed
control: type 3 high density[2.475248, 2.4752][2.475248, 2.4752]Passed

SHA-256 / 8cf11b8209ba1d7a688120b727f5c21d8d7e587f87f0c9358dc0a14c86922247

3 / The verified repair

Exit 0
"""Failure Map reference implementation. Python standard library only."""
import json
import math
N = 1
observations = []
def solve(kind, a, h, prey, predators, duration):
    if a < 0 or h < 0 or prey < 0:
        return None
    if kind == 1:
        f = a * prey if h == 0 else min(a * prey, 1 / h)
    elif kind == 2:
        f = a * prey / (1 + a * h * prey)
    elif kind == 3:
        f = a * prey ** 2 / (1 + a * h * prey ** 2)
    else:
        return None
    eaten = min(f * predators * duration, prey)
    return [round(f, 6), round(eaten, 4)]
def check(label, actual, expected):
    observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[('control: type 1 saturated filter feeder', (1, 0.5, 0.25, 20, 2, 1), [4.0, 8.0]),
  ('control: type 1 unsaturated', (1, 0.1, 0.5, 10, 1, 2), [1.0, 2.0]),
  ('control: type 1 no handling', (1, 0.3, 0.0, 40, 1, 1), [12.0, 12.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: type 3 prey switching', (3, 0.05, 0.2, 12, 2, 3), [2.95082, 12]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752])],
 [('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: type 3 prey switching', (3, 0.05, 0.2, 12, 2, 3), [2.95082, 12]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752]),
  ('regression: depletion cap', (2, 2.0, 0.05, 10, 20, 5), [10.0, 10]),
  ('control: unknown kind', (4, 0.1, 0.1, 10, 1, 1), None),
  ('control: no prey', (2, 0.5, 0.5, 0, 2, 1), [0.0, 0.0])],
 [('control: type 1 saturated filter feeder', (1, 0.5, 0.25, 20, 2, 1), [4.0, 8.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752]),
  ('regression: depletion cap', (2, 2.0, 0.05, 10, 20, 5), [10.0, 10]),
  ('control: unknown kind', (4, 0.1, 0.1, 10, 1, 1), None),
  ('control: no prey', (2, 0.5, 0.5, 0, 2, 1), [0.0, 0.0]),
  ('control: invalid negative handling', (2, 0.5, -0.1, 10, 1, 1), None)],
 [('control: type 1 saturated filter feeder', (1, 0.5, 0.25, 20, 2, 1), [4.0, 8.0]),
  ('control: type 1 unsaturated', (1, 0.1, 0.5, 10, 1, 2), [1.0, 2.0]),
  ('control: type 1 no handling', (1, 0.3, 0.0, 40, 1, 1), [12.0, 12.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: no prey', (2, 0.5, 0.5, 0, 2, 1), [0.0, 0.0]),
  ('control: invalid negative handling', (2, 0.5, -0.1, 10, 1, 1), None)],
 [('control: type 1 unsaturated', (1, 0.1, 0.5, 10, 1, 2), [1.0, 2.0]),
  ('control: type 1 no handling', (1, 0.3, 0.0, 40, 1, 1), [12.0, 12.0]),
  ('regression: type 2 wolves on moose', (2, 0.8, 0.5, 30, 3, 2), [1.846154, 11.0769]),
  ('regression: type 2 low density', (2, 0.2, 0.1, 3, 1, 1), [0.566038, 0.566]),
  ('control: type 3 prey switching', (3, 0.05, 0.2, 12, 2, 3), [2.95082, 12]),
  ('control: type 3 high density', (3, 0.1, 0.4, 50, 1, 1), [2.475248, 2.4752]),
  ('regression: depletion cap', (2, 2.0, 0.05, 10, 20, 5), [10.0, 10])]]
for label, args, expected in fixtures[N - 1]:
    check(label, solve(*args), expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
Boundary fixtureActualExpectedOutcome
control: type 1 saturated filter feeder[4.0, 8.0][4.0, 8.0]Passed
control: type 1 unsaturated[1.0, 2.0][1.0, 2.0]Passed
control: type 1 no handling[12.0, 12.0][12.0, 12.0]Passed
regression: type 2 wolves on moose[1.846154, 11.0769][1.846154, 11.0769]Passed
regression: type 2 low density[0.566038, 0.566][0.566038, 0.566]Passed
control: type 3 prey switching[2.95082, 12][2.95082, 12]Passed
control: type 3 high density[2.475248, 2.4752][2.475248, 2.4752]Passed

SHA-256 / 415bf152424710e37f474390078ab4def3a88bec34a6d1aafa87db4cd19804a9

Verification & scope

Deterministic bounded teaching model with a stipulated contract; not a validated scientific or public-health modelling library. This reproducer isolates one failure mechanism. Results cover the supplied fixtures. Variants within a family share a test contract and should remain grouped when constructing evaluation splits. Related mechanisms with a shared evaluation_group must also remain together; these controlled models are not independent production incidents.

Observations recorded using Python 3.12.14 at 2026-09-29T14:47:33.999060+00:00.

Case digest / 9b08b429af7d2a274602f6cd0aee6c633608eb83ca516c356066dd5b4033c22a