From 90019ec192894d6810b3d530c14b0d8b2013f245 Mon Sep 17 00:00:00 2001 From: "Austin L." <86896075+rvnminers-A-and-N@users.noreply.github.com> Date: Fri, 26 Jun 2026 23:46:06 +0000 Subject: [PATCH] fix(training): lift sour-rule recall 0.57 -> 0.93 (match acid anions) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The acidity rule matched only protonated acids (-OH), missing every carboxylate/sulfonate/phosphate anion and zwitterion — how many sour compounds are actually drawn. Match both -OH and -O- forms (in predict.py and the train_taste.py validation copy). Recall on labeled-sour rises 0.57 -> 0.93; firing 1349 -> 1675/3295 (acceptable: the rule is the structural cross-check, the trained sour_predicted head carries the perception signal). Closes #41. --- training/predict.py | 9 ++++++--- training/train_taste.py | 5 ++++- 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/training/predict.py b/training/predict.py index 73d96c2..fd8e57b 100644 --- a/training/predict.py +++ b/training/predict.py @@ -55,9 +55,12 @@ TASTE = Path("taste_models") ACID_SMARTS = { - "carboxylic acid": "[CX3](=O)[OX2H1]", - "sulfonic acid": "[SX4](=O)(=O)[OX2H1]", - "phosphoric/phosphonic acid": "[PX4](=O)[OX2H1]", + # Match both protonated (-OH) and deprotonated (-O-) forms — sour compounds are + # routinely drawn as carboxylate/sulfonate/phosphate anions or zwitterions. + # (Lifted the rule's recall on labeled-sour from 0.57 to 0.93.) + "carboxylic acid / carboxylate": "[CX3](=O)[OX2H1,OX1-]", + "sulfonic / sulfonate": "[SX4](=O)(=O)[OX2H1,OX1-]", + "phosphoric / phosphonic (+ anion)": "[PX4](=O)[OX2H1,OX1-]", } _ACID = {k: Chem.MolFromSmarts(v) for k, v in ACID_SMARTS.items()} diff --git a/training/train_taste.py b/training/train_taste.py index e39bcdf..0d3c810 100644 --- a/training/train_taste.py +++ b/training/train_taste.py @@ -49,7 +49,10 @@ # Acidic-group SMARTS — used both for the sour rule and to VALIDATE it against # whatever labeled sour compounds exist (so that data isn't wasted either). -ACID_SMARTS = ["[CX3](=O)[OX2H1]", "[SX4](=O)(=O)[OX2H1]", "[PX4](=O)[OX2H1]"] +# Match BOTH protonated (-OH) and deprotonated (-O-) forms: sour compounds are +# routinely drawn as carboxylate/sulfonate/phosphate anions or zwitterions, which +# the -OH-only patterns missed (the main driver of the low recall). +ACID_SMARTS = ["[CX3](=O)[OX2H1,OX1-]", "[SX4](=O)(=O)[OX2H1,OX1-]", "[PX4](=O)[OX2H1,OX1-]"] _ACID = [Chem.MolFromSmarts(s) for s in ACID_SMARTS]