Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 11 additions & 1 deletion pwiz_tools/Skyline/Test/AdductTest.cs
Original file line number Diff line number Diff line change
Expand Up @@ -347,12 +347,22 @@ private static void CheckLabel(string label)
private void TestMassOnly(IEnumerable<string>[] adductLists)
{
var formula = @"[456.78]"; // Mass-only molecule description
var molecule = ParsedMolecule.Create(formula);
var massMolecule = molecule.MonoMassOffset;
AssertEx.AreEqual(456.78,massMolecule);
foreach (var adductList in adductLists)
{
foreach (var adductStr in adductList)
{
var adduct = Adduct.FromString(adductStr, Adduct.ADDUCT_TYPE.proteomic, null);
IonInfo.ApplyAdductToFormula(formula, adduct);
var ion = IonInfo.ApplyAdductToFormula(formula, adduct);
var massAdduct = adduct.MonoMassAdduct + adduct.IsotopesIncrementalMonoMass + massMolecule * (adduct.GetMassMultiplier()-1);
var massIon = BioMassCalc.MONOISOTOPIC.CalculateMass(ion);
if (!adduct.IsChargeOnly)
{
AssertEx.AreNotEqual(massIon, massMolecule, "adduct has no effect?");
}
AssertEx.AreEqual(massIon, massMolecule + massAdduct, .0001, $"ion {ion} mass {massIon} vs mol {molecule} mass + adduct {adduct} mass ({massMolecule}+{massAdduct}");
}
}
}
Expand Down
62 changes: 30 additions & 32 deletions pwiz_tools/Skyline/Util/Adduct.cs
Original file line number Diff line number Diff line change
Expand Up @@ -70,11 +70,11 @@ public class Adduct : Immutable, IComparable, IEquatable<Adduct>, IAuditLogObjec
{
private Molecule Composition { get; set; } // The chemical makeup of the adduct - the "2H" part in 4M3Cl37+2H
private string Description { get; set; } // The text description (will be empty for protonation, we just use charge)
private TypedMass AverageMassAdduct { get; set; } // Average mass of the adduct itself - the "2H" in 4M3Cl37+2H
private TypedMass MonoMassAdduct { get; set; } // Monoisotopic mass of the adduct itself - the "2H" in 4M3Cl37+2H
public TypedMass AverageMassAdduct { get; private set; } // Average mass of the adduct itself - the "2H" in 4M3Cl37+2H
public TypedMass MonoMassAdduct { get; private set; } // Monoisotopic mass of the adduct itself - the "2H" in 4M3Cl37+2H
private int MassMultiplier { get; set; } // Returns, for example, the 2 in "[2M+Na]", which means the ion is two molecules + the adduct mass.
private TypedMass IsotopesIncrementalAverageMass { get; set; } // The incremental average mass due to (4*3) (Cl37 - Cl) in 4M3Cl37+2H
private TypedMass IsotopesIncrementalMonoMass { get; set; } // The incremental mono mass due to (4*3) (Cl37 - Cl) in 4M3Cl37+2H
public TypedMass IsotopesIncrementalAverageMass { get; private set; } // The incremental average mass due to (4*3) (Cl37 - Cl) in 4M3Cl37+2H
public TypedMass IsotopesIncrementalMonoMass { get; private set; } // The incremental mono mass due to (4*3) (Cl37 - Cl) in 4M3Cl37+2H

private int _hashCode; // We want comparisons to be on the same order as comparing ints, as when we used to just use integer charge instead of proper adducts

Expand Down Expand Up @@ -1368,44 +1368,42 @@ public ParsedMolecule ApplyToMolecule(ParsedMolecule molecule)

var resultDict = new Dictionary<string, int>(molecule.Molecule);

if (!molecule.IsMassOnly)
// Deal with any mass multiplier (the 2 in "[2M+Na]")
if (MassMultiplier != 1)
{
// Deal with any mass multiplier (the 2 in "[2M+Na]")
if (MassMultiplier != 1)
foreach (var element in resultDict.Keys.ToArray())
{
foreach (var element in resultDict.Keys.ToArray())
{
resultDict[element] *= MassMultiplier;
}
resultDict[element] *= MassMultiplier;
}
}

// Add in the "Na" of [M+Na] (or remove the 4H in [M-4H])
foreach (var pair in Composition)
// Add in the "Na" of [M+Na] (or remove the 4H in [M-4H])
foreach (var pair in Composition)
{
if (resultDict.TryGetValue(pair.Key, out var count))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If you wanted, you could replace these 17 lines with:

                resultDict.TryGetValue(pair.Key, out var count);
                count += pair.Value;
                if (count == 0)
                {
                    resultDict.Remove(pair.Key);
                }
                else
                {
                    resultDict[pair.Key] = count;
                }

{
if (resultDict.TryGetValue(pair.Key, out var count))
{
count += pair.Value;
if (count == 0)
{
resultDict.Remove(pair.Key);
}
else
{
resultDict[pair.Key] = count;
}
}
else if (pair.Value != 0)
count += pair.Value;
if (count == 0)
{
resultDict.Add(pair.Key, pair.Value);
count = pair.Value;
resultDict.Remove(pair.Key);
}
if (count < 0 && !Equals(pair.Key, BioMassCalc.H)) // Treat H loss as a general proton loss
else
{
throw new InvalidDataException(
string.Format(Resources.Adduct_ApplyToMolecule_Adduct___0___calls_for_removing_more__1__atoms_than_are_found_in_the_molecule__2_,
this, pair.Key, molecule.ToString()));
resultDict[pair.Key] = count;
}
}
else if (pair.Value != 0)
{
resultDict.Add(pair.Key, pair.Value);
count = pair.Value;
}
if (!molecule.IsMassOnly &&
count < 0 && !Equals(pair.Key, BioMassCalc.H)) // Treat H loss as a general proton loss
{
throw new InvalidDataException(
string.Format(Resources.Adduct_ApplyToMolecule_Adduct___0___calls_for_removing_more__1__atoms_than_are_found_in_the_molecule__2_,
this, pair.Key, molecule.ToString()));
}
}

return ApplyIsotopeValues(molecule, MassMultiplier, resultDict);
Expand Down