Kidney-IS-Predictor / kappa_lambda_meta.py
MarkBarsoum's picture
Replace with Universal Kidney Pattern Recognition Model (Gradio, image-only)
8ef0a28 verified
Raw
History Blame Contribute Delete
2.6 kB
#!/usr/bin/env python3
"""
kappa_lambda_meta.py (v3 - rule-based)
========================================
Derives kappa/lambda clonality via deterministic clinical rules.
No classifier needed: the logic is unambiguous.
Rules:
Kappa+ and Lambda- -> kappa_dominant
Lambda+ and Kappa- -> lambda_dominant
Both positive -> polyclonal
Both negative -> polyclonal (non-specific, no light chain restriction)
Clinical note: kappa/lambda ratio indicates CLONALITY, not IS need directly.
Monoclonal patterns narrow the differential toward plasma cell dyscrasias
(LCDD, amyloid, myeloma cast nephropathy) which are mostly IS=No or
require disease-specific regimens. The ratio feeds into the IS classifier
as one feature among many, not as a standalone IS decision.
Used by: infer_case_v2.py (inline rule, no pkl needed)
train_is_classifier.py (encodes ratio as ordinal feature)
"""
# Threshold: grade > 0 = positive (i.e. 1+, 2+, 3+, 4+)
# grade = 0 means negative or trace
def derive_kappa_lambda_ratio(kappa_grade, lambda_grade):
"""
Args:
kappa_grade: float, predicted or true ordinal grade (0-4)
lambda_grade: float, predicted or true ordinal grade (0-4)
Returns:
(label, confidence)
label: 'kappa_dominant' | 'lambda_dominant' | 'polyclonal'
confidence: float (1.0 for pure rule, lower if grades are borderline)
"""
k_pos = kappa_grade > 0
l_pos = lambda_grade > 0
if k_pos and not l_pos:
label = "kappa_dominant"
elif l_pos and not k_pos:
label = "lambda_dominant"
else:
label = "polyclonal"
# Confidence reflects how clear-cut the contrast is
# Strong contrast (e.g. k=3, l=0) -> high confidence
# Borderline (e.g. k=1, l=1) -> lower
contrast = abs(kappa_grade - lambda_grade)
if contrast >= 2:
conf = 0.90
elif contrast == 1:
conf = 0.70
else:
conf = 0.55 # both 0 or both equal positive -> ambiguous
return label, conf
if __name__ == "__main__":
# Sanity check
tests = [
(3, 0, "kappa_dominant"),
(0, 2, "lambda_dominant"),
(2, 2, "polyclonal"),
(0, 0, "polyclonal"),
(1, 0, "kappa_dominant"),
]
print("Rule check:")
all_pass = True
for k, l, expected in tests:
label, conf = derive_kappa_lambda_ratio(k, l)
status = "OK" if label == expected else "FAIL"
if status == "FAIL": all_pass = False
print(f" k={k} l={l} -> {label} (conf={conf:.2f}) [{status}]")
print(f"\nAll tests passed: {all_pass}")