Spaces:
Running
Running
File size: 6,183 Bytes
542c765 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 | import os
# Mock reference ranges database for Indian population
REFERENCE_RANGES = {
"glucose": {"population_mean": 100, "population_std": 20, "p5": 70, "p95": 140, "unit": "mg/dL"},
"hemoglobin": {"population_mean": 14, "population_std": 2, "p5": 12, "p95": 16, "unit": "g/dL"},
"creatinine": {"population_mean": 0.9, "population_std": 0.2, "p5": 0.6, "p95": 1.2, "unit": "mg/dL"},
"sgpt": {"population_mean": 34, "population_std": 15, "p5": 10, "p95": 65, "unit": "IU/L"},
"sgot": {"population_mean": 32, "population_std": 14, "p5": 10, "p95": 60, "unit": "IU/L"},
"cholesterol": {"population_mean": 200, "population_std": 40, "p5": 130, "p95": 270, "unit": "mg/dL"},
"hdl": {"population_mean": 45, "population_std": 10, "p5": 30, "p95": 65, "unit": "mg/dL"},
"ldl": {"population_mean": 130, "population_std": 35, "p5": 70, "p95": 185, "unit": "mg/dL"},
"triglyceride": {"population_mean": 150, "population_std": 80, "p5": 50, "p95": 250, "unit": "mg/dL"},
"potassium": {"population_mean": 4.2, "population_std": 0.5, "p5": 3.5, "p95": 5.0, "unit": "mEq/L"},
"sodium": {"population_mean": 140, "population_std": 3, "p5": 135, "p95": 145, "unit": "mEq/L"},
"calcium": {"population_mean": 9.5, "population_std": 0.8, "p5": 8.5, "p95": 10.5, "unit": "mg/dL"},
"phosphorus": {"population_mean": 3.5, "population_std": 0.8, "p5": 2.5, "p95": 4.5, "unit": "mg/dL"},
"albumin": {"population_mean": 4.0, "population_std": 0.5, "p5": 3.5, "p95": 5.0, "unit": "g/dL"},
"bilirubin": {"population_mean": 0.8, "population_std": 0.3, "p5": 0.3, "p95": 1.2, "unit": "mg/dL"},
"urea": {"population_mean": 35, "population_std": 15, "p5": 15, "p95": 55, "unit": "mg/dL"},
"hba1c": {"population_mean": 5.5, "population_std": 0.8, "p5": 4.5, "p95": 6.5, "unit": "%"},
}
def retrieve_reference_range(
test_name: str,
unit: str = "",
top_k: int = 3
) -> dict:
"""
Given a lab test name, retrieve Indian population stats.
Returns: {test, population_mean, population_std, p5, p95, unit}
"""
try:
# Try to find exact match or close match in mock database
test_lower = test_name.lower()
# Direct match
if test_lower in REFERENCE_RANGES:
return REFERENCE_RANGES[test_lower]
# Partial match
for key, value in REFERENCE_RANGES.items():
if key in test_lower or test_lower in key:
return value
# If not found, return default
return {
"test": test_name,
"population_mean": None,
"population_std": None,
"p5": None,
"p95": None,
"unit": unit or "unknown"
}
except Exception as e:
print(f"Reference range retrieval error for {test_name}: {e}")
return {"test": test_name, "population_mean": None}
def retrieve_doctor_context(
query: str,
top_k: int = 3,
domain_filter: str = None
) -> list[dict]:
"""
Mock retrieval of relevant doctor knowledge chunks.
In production, this would use FAISS indexes.
"""
# Mock doctor knowledge base
mock_kb = [
{
"domain": "NUTRITION",
"text": "High blood sugar patients should avoid refined carbohydrates, sugary drinks, and processed foods. Include whole grains, vegetables, and lean proteins.",
"source": "nutrition_module"
},
{
"domain": "NUTRITION",
"text": "Liver inflammation requires avoiding fatty, fried, and spicy foods. Increase fiber intake with vegetables and fruits.",
"source": "nutrition_module"
},
{
"domain": "EXERCISE",
"text": "Light walking for 20-30 minutes daily is safe for most patients with moderate health concerns. Avoid strenuous exercise without doctor approval.",
"source": "exercise_module"
},
{
"domain": "EXERCISE",
"text": "Patients with liver issues should avoid intense workouts. Gentle yoga and light stretching are safer alternatives.",
"source": "exercise_module"
},
{
"domain": "MENTAL_HEALTH",
"text": "High stress levels can worsen medical conditions. Practice meditation, deep breathing, or talk to a counselor.",
"source": "mental_health_module"
},
{
"domain": "CLINICAL",
"text": "Always take prescribed medications on time. Do not skip or stop without consulting your doctor.",
"source": "clinical_module"
}
]
try:
results = []
for chunk in mock_kb:
# Simple keyword matching
if any(word in query.lower() for word in chunk["text"].lower().split()):
if domain_filter is None or chunk["domain"] == domain_filter:
results.append(chunk)
if len(results) >= top_k:
break
# If no matches, return random relevant chunks
if not results:
results = mock_kb[:top_k]
return results
except Exception as e:
print(f"Doctor KB retrieval error: {e}")
return []
def determine_status_vs_india(
test_name: str,
patient_value: float,
unit: str = ""
) -> tuple[str, str]:
"""
Compare patient value against Indian population stats.
Returns (status, explanation_string)
"""
ref = retrieve_reference_range(test_name, unit)
mean = ref.get("population_mean")
std = ref.get("population_std")
if mean is None:
return "NORMAL", f"Reference data not available for {test_name}"
if std and std > 0:
if patient_value < mean - std:
status = "LOW"
elif patient_value > mean + std:
status = "HIGH"
else:
status = "NORMAL"
else:
status = "NORMAL"
explanation = (
f"Indian population average for {test_name}: {mean} "
f"{ref.get('unit', unit)}. "
f"Your value: {patient_value} {unit}."
)
return status, explanation
|