/// <summary> /// Compile a 2D list of files organized by sample group for rMFE filtering /// This list has input and output file paths (.rmc) /// </summary> /// <returns></returns> private ICollection <ICollection <CompoundFilterByBucket.DataPathInfo> > GetFilePaths() { // outer list is by sample group var rv = new List <ICollection <CompoundFilterByBucket.DataPathInfo> >(); foreach (var group in m_sampleGroupDict.Values.Distinct()) { // inner list is by .rmc file var grpList = new List <CompoundFilterByBucket.DataPathInfo>(); foreach (var file in m_sampleGroupDict.Where(sg => sg.Value == group).Select(sg => sg.Key)) { // there can be multiple .unfiltered.rmc files depending on frag voltage, polarity, etc. var rmcPath = FindCpdsMassHunter.GetPersistenceFilePath(file, null); foreach (var rmcFile in Directory.GetFiles(rmcPath, "*" + RMC_UNFILTERED_EXTENSION)) { var dpi = new CompoundFilterByBucket.DataPathInfo(); dpi.CustomerScalingFactor = 1.0f; dpi.InputCompoundFilePath = rmcFile; dpi.OutputCompoundFilePah = Regex.Replace(rmcFile, RMC_UNFILTERED_EXTENSION, RMC_EXTENSION); grpList.Add(dpi); } } rv.Add(grpList); } return(rv); }
/// <summary> /// Override to do the actual work of the command /// </summary> protected override void DoSpecialized() { //BatchExtractor.CommonUtility.LogMessage("Recursive MFE", this); var userParameters = GetAlignmentParameters(); clcfileList.Clear(); if (IsGCData() == true) // To do recursive MFE for GC data { return; } //var progressTracker = new PFEProgressTracker(m_AppManager, ProgressCategory.Task); try { //progressTracker.ReportProgress(ProgressStage.Starting, 0, new QualUserMessage(QualMessage.ExecutingFindCompounds)); for (int i = 0; i < m_analyses.Count; i++) { var m_analysis = m_analyses[i]; IFindCompoundsParameters findParams = GetFindCompoundsParams(); GetAnalysisSpecificParams(ref findParams, new object[] { m_analysis }); List <IonPolarity> polarityList = GetScanIonPolarities(findParams.DataAccess); // for Allion data, not to use fragVoltage. List <double> energyVoltages = null; double lowE = double.NaN; double[] highEs = null; bool bMultipleCEs = false; bool AllIonsData = FindCpdsUtilities.IsThisAllIonsData(findParams.DataAccess, out lowE, out highEs, out bMultipleCEs); if (AllIonsData) { energyVoltages = new List <double>(1); energyVoltages.Add(lowE); } else { energyVoltages = GetFragmentorVoltages(findParams.DataAccess); if (energyVoltages.Count == 1) { energyVoltages[0] = 0.0; } } // multiple time segemnt support. One segment per clc file. // No MFE data segment with no clc file generated. IBDADataAccess m_BdaDa = new BDADataAccess(); m_BdaDa.OpenDataFile(findParams.DataAccess.DataFileName, true); IRange[] tempRange = m_BdaDa.GetTimeSegmentRanges(); int m_totalTimeSegment = tempRange.Length; m_BdaDa.CloseDataFile(); // double fragVoltage = 0.0; // From B08, MFE data reader API has changed. It doesn't use the passed in multiple voltages. The reader handle it itself. if (energyVoltages.Count > 1) // for multiple frag voltageas, we take the smallest one { // fragVoltage = energyVoltages.Min(); // match the changes in MassHunterAlgorithm.cs and in MFE (MFE agreed to do so) } DesiredMSStorageType storeType = DesiredMSStorageType.PeakElseProfile; for (int idxPolarity = 0; idxPolarity < polarityList.Count; idxPolarity++) { IonPolarity ionPolarity = polarityList[idxPolarity]; foreach (var framVoltage in energyVoltages) // get one valid store type. { try { storeType = GetStorageType(findParams.DataAccess, ionPolarity, framVoltage); break; } catch // small framVoltage different could get there, we use a valid one (TT 268031) { } } for (int segnum = 1; segnum <= m_totalTimeSegment; segnum++) { var sPath = FindCpdsMassHunter.GetPersistenceFilePath( m_analysis.FilePath, null); var sName = FindCpdsMassHunter.GetPersistenceFileName( m_analysis.FilePath, ionPolarity, storeType, fragVoltage, segnum); clcFileItem clcItem; clcItem.rmcPath = Path.Combine(sPath, (sName + RMC_UNFILTERED_EXTENSION)); clcItem.clcPath = Path.Combine(sPath, (sName + CLC_EXTENSION)); clcItem.clcName = Regex.Replace(sName, @"^.+\.", String.Empty); clcItem.scalingfactor = 1.0f; clcfileList.Add(clcItem); } } } if (clcfileList.Count > 0) { var itemQuery = clcfileList.GroupBy(p => p.clcName); string errMsg = string.Empty; List <string> processedFilesList = new List <string>(); foreach (IGrouping <string, clcFileItem> queryItem in itemQuery) { List <string> clcFilePaths = new List <string> { }; List <string> rmcFilePaths = new List <string> { }; List <float> scalfactor = new List <float> { }; foreach (var clcItem in queryItem) { if (File.Exists(clcItem.clcPath)) { clcFilePaths.Add(clcItem.clcPath); rmcFilePaths.Add(clcItem.rmcPath); scalfactor.Add(clcItem.scalingfactor); processedFilesList.Add(clcItem.clcPath); } } if (clcFilePaths.Count > 0) // Do Recursive MFE only there is .clc file. { // Do RecursEngine RecursiveMfeEngine recursMfeEng = new RecursiveMfeEngine(clcFilePaths, rmcFilePaths, scalfactor, userParameters); for (int i = 0; i < recursMfeEng.StepCount; i++) // must start with 0. { //progressTracker.PercentComplete = (int)((double)(i+1) / recursMfeEng.StepCount * 100); //progressTracker.ReportProgress(ProgressStage.Progressing, (int)((double)(i + 1) / recursMfeEng.StepCount * 100), "Refinding isotope cluster assignments..."); try { recursMfeEng.StepIt(i); } catch (Exception ex) { errMsg = ex.Message; } if (this.CancelCommandIndicator.Cancel == true) { throw new Exception("This operation was canceled."); } } } } if (!string.IsNullOrEmpty(errMsg)) { bool bOK = false; foreach (string sF in processedFilesList) { string rmcFile = sF.Replace(".clc", ".rmc"); // if has rmc file be generated, at lease one of the time segment has data. if (File.Exists(rmcFile)) { bOK = true; break; } } if (!bOK) { throw new Exception(errMsg); } } } } catch (Exception ex) { // IUserMessage msg = new UserMessage(0, string.Empty, // ProgramModule.CoreDbSearch, // ProgramModule.MfeEngine); // throw new MSDAApplicationException(msg); //throw new Exception("CmdPFRecursiveMFECpd : " + ex.Message); var umsg = new QualUserMessage(QualMessage.MultipleAnalysisErrors_0, ex.Message); throw new MSDAApplicationException(umsg); } finally { //progressTracker.ReportProgress(ProgressStage.Finished, 100, new QualUserMessage(QualMessage.OperationComplete)); Trace.WriteLineIf(Ts.TraceInfo, Tm.Finish); } }