/** * Calls Gaussian1D as a child algorithm to fit the offset peak in a spectrum * @param mosaic * @param rcrystallite * @param inname * @param corrOption * @param pointOption * @param tofParams * @return */ double OptimizeExtinctionParameters::fitMosaic( double mosaic, double rcrystallite, std::string inname, std::string corrOption, std::string pointOption, std::string tofParams) { PeaksWorkspace_sptr inputW = boost::dynamic_pointer_cast<PeaksWorkspace>( AnalysisDataService::Instance().retrieve(inname)); std::vector<double> tofParam = Kernel::VectorHelper::splitStringIntoVector<double>(tofParams); if (mosaic < 0.0 || rcrystallite < 0.0) return 1e300; API::IAlgorithm_sptr tofextinction = createChildAlgorithm("TOFExtinction", 0.0, 0.2); tofextinction->setProperty("InputWorkspace", inputW); tofextinction->setProperty("OutputWorkspace", "tmp"); tofextinction->setProperty("ExtinctionCorrectionType", corrOption); tofextinction->setProperty<double>("Mosaic", mosaic); tofextinction->setProperty<double>("Cell", tofParam[0]); tofextinction->setProperty<double>("RCrystallite", rcrystallite); tofextinction->executeAsChildAlg(); PeaksWorkspace_sptr peaksW = tofextinction->getProperty("OutputWorkspace"); API::IAlgorithm_sptr sorthkl = createChildAlgorithm("SortHKL", 0.0, 0.2); sorthkl->setProperty("InputWorkspace", peaksW); sorthkl->setProperty("OutputWorkspace", peaksW); sorthkl->setProperty("PointGroup", pointOption); sorthkl->executeAsChildAlg(); double Chisq = sorthkl->getProperty("OutputChi2"); std::cout << mosaic << " " << rcrystallite << " " << Chisq << "\n"; return Chisq; }
/** Call edit instrument geometry */ API::MatrixWorkspace_sptr AlignAndFocusPowder::editInstrument( API::MatrixWorkspace_sptr ws, std::vector<double> polars, std::vector<specnum_t> specids, std::vector<double> l2s, std::vector<double> phis) { g_log.information() << "running EditInstrumentGeometry started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr editAlg = createChildAlgorithm("EditInstrumentGeometry"); editAlg->setProperty("Workspace", ws); if (m_l1 > 0.) editAlg->setProperty("PrimaryFlightPath", m_l1); if (!polars.empty()) editAlg->setProperty("Polar", polars); if (!specids.empty()) editAlg->setProperty("SpectrumIDs", specids); if (!l2s.empty()) editAlg->setProperty("L2", l2s); if (!phis.empty()) editAlg->setProperty("Azimuthal", phis); editAlg->executeAsChildAlg(); ws = editAlg->getProperty("Workspace"); return ws; }
/** * Removes exponential decay from a workspace * @param wsInput :: [input] Workspace to work on * @return :: Workspace with decay removed */ API::MatrixWorkspace_sptr CalMuonDetectorPhases::removeExpDecay( const API::MatrixWorkspace_sptr &wsInput) { API::IAlgorithm_sptr remove = createChildAlgorithm("RemoveExpDecay"); remove->setProperty("InputWorkspace", wsInput); remove->executeAsChildAlg(); API::MatrixWorkspace_sptr wsRem = remove->getProperty("OutputWorkspace"); return wsRem; }
/** Extracts relevant data from a workspace * @param startTime :: [input] First X value to consider * @param endTime :: [input] Last X value to consider * @return :: Pre-processed workspace to fit */ API::MatrixWorkspace_sptr CalMuonDetectorPhases::extractDataFromWorkspace(double startTime, double endTime) { // Extract counts from startTime to endTime API::IAlgorithm_sptr crop = createChildAlgorithm("CropWorkspace"); crop->setProperty("InputWorkspace", m_inputWS); crop->setProperty("XMin", startTime); crop->setProperty("XMax", endTime); crop->executeAsChildAlg(); boost::shared_ptr<API::MatrixWorkspace> wsCrop = crop->getProperty("OutputWorkspace"); return wsCrop; }
/// Run ConvertUnits as a Child Algorithm to convert to dSpacing MatrixWorkspace_sptr DiffractionFocussing::convertUnitsToDSpacing( const API::MatrixWorkspace_sptr &workspace) { const std::string CONVERSION_UNIT = "dSpacing"; Unit_const_sptr xUnit = workspace->getAxis(0)->unit(); g_log.information() << "Converting units from " << xUnit->label().ascii() << " to " << CONVERSION_UNIT << ".\n"; API::IAlgorithm_sptr childAlg = createChildAlgorithm("ConvertUnits", 0.34, 0.66); childAlg->setProperty("InputWorkspace", workspace); childAlg->setPropertyValue("Target", CONVERSION_UNIT); childAlg->executeAsChildAlg(); return childAlg->getProperty("OutputWorkspace"); }
/// Run Rebin as a Child Algorithm to harmonise the bin boundaries void DiffractionFocussing::RebinWorkspace( API::MatrixWorkspace_sptr &workspace) { double min = 0; double max = 0; double step = 0; calculateRebinParams(workspace, min, max, step); std::vector<double> paramArray{min, -step, max}; g_log.information() << "Rebinning from " << min << " to " << max << " in " << step << " logaritmic steps.\n"; API::IAlgorithm_sptr childAlg = createChildAlgorithm("Rebin"); childAlg->setProperty<MatrixWorkspace_sptr>("InputWorkspace", workspace); childAlg->setProperty<std::vector<double>>("Params", paramArray); childAlg->executeAsChildAlg(); workspace = childAlg->getProperty("OutputWorkspace"); }
/** Call diffraction focus to a matrix workspace. */ API::MatrixWorkspace_sptr AlignAndFocusPowder::diffractionFocus(API::MatrixWorkspace_sptr ws) { if (!m_groupWS) { g_log.information() << "not focussing data\n"; return ws; } g_log.information() << "running DiffractionFocussing. \n"; API::IAlgorithm_sptr focusAlg = createChildAlgorithm("DiffractionFocussing"); focusAlg->setProperty("InputWorkspace", ws); focusAlg->setProperty("OutputWorkspace", ws); focusAlg->setProperty("GroupingWorkspace", m_groupWS); focusAlg->setProperty("PreserveEvents", m_preserveEvents); focusAlg->executeAsChildAlg(); ws = focusAlg->getProperty("OutputWorkspace"); return ws; }
/** Rebin */ API::MatrixWorkspace_sptr AlignAndFocusPowder::rebin(API::MatrixWorkspace_sptr matrixws) { if (m_resampleX != 0) { // ResampleX g_log.information() << "running ResampleX(NumberBins=" << abs(m_resampleX) << ", LogBinning=" << (m_resampleX < 0) << ", dMin(" << m_dmins.size() << "), dmax(" << m_dmaxs.size() << ")) started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr alg = createChildAlgorithm("ResampleX"); alg->setProperty("InputWorkspace", matrixws); alg->setProperty("OutputWorkspace", matrixws); if ((!m_dmins.empty()) && (!m_dmaxs.empty())) { size_t numHist = m_outputW->getNumberHistograms(); if ((numHist == m_dmins.size()) && (numHist == m_dmaxs.size())) { alg->setProperty("XMin", m_dmins); alg->setProperty("XMax", m_dmaxs); } else { g_log.information() << "Number of dmin and dmax values don't match the " << "number of workspace indices. Ignoring the parameters.\n"; } } alg->setProperty("NumberBins", abs(m_resampleX)); alg->setProperty("LogBinning", (m_resampleX < 0)); alg->executeAsChildAlg(); matrixws = alg->getProperty("OutputWorkspace"); return matrixws; } else { g_log.information() << "running Rebin( "; for (double param : m_params) g_log.information() << param << " "; g_log.information() << ") started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr rebin3Alg = createChildAlgorithm("Rebin"); rebin3Alg->setProperty("InputWorkspace", matrixws); rebin3Alg->setProperty("OutputWorkspace", matrixws); rebin3Alg->setProperty("Params", m_params); rebin3Alg->executeAsChildAlg(); matrixws = rebin3Alg->getProperty("OutputWorkspace"); return matrixws; } }
void LoadILLSANS::moveDetectorVertical(double shift, const std::string &componentName) { API::IAlgorithm_sptr mover = createChildAlgorithm("MoveInstrumentComponent"); V3D pos = getComponentPosition(componentName); try { mover->setProperty<MatrixWorkspace_sptr>("Workspace", m_localWorkspace); mover->setProperty("ComponentName", componentName); mover->setProperty("X", pos.X()); mover->setProperty("Y", shift); mover->setProperty("Z", pos.Z()); mover->setProperty("RelativePosition", false); mover->executeAsChildAlg(); g_log.debug() << "Moving component '" << componentName << "' to Y = " << shift << '\n'; } catch (std::exception &e) { g_log.error() << "Cannot move the component '" << componentName << "' to Y = " << shift << '\n'; g_log.error() << e.what() << '\n'; } }
/** Perform SortHKL on the output workspaces * * @param ws :: any PeaksWorkspace * @param runName :: string to put in statistics table */ void StatisticsOfPeaksWorkspace::doSortHKL(Mantid::API::Workspace_sptr ws, std::string runName) { std::string pointGroup = getPropertyValue("PointGroup"); std::string latticeCentering = getPropertyValue("LatticeCentering"); std::string wkspName = getPropertyValue("OutputWorkspace"); std::string tableName = getPropertyValue("StatisticsTable"); API::IAlgorithm_sptr statsAlg = createChildAlgorithm("SortHKL"); statsAlg->setProperty("InputWorkspace", ws); statsAlg->setPropertyValue("OutputWorkspace", wkspName); statsAlg->setPropertyValue("StatisticsTable", tableName); statsAlg->setProperty("PointGroup", pointGroup); statsAlg->setProperty("LatticeCentering", latticeCentering); statsAlg->setProperty("RowName", runName); if (runName.compare("Overall") != 0) statsAlg->setProperty("Append", true); statsAlg->executeAsChildAlg(); PeaksWorkspace_sptr statsWksp = statsAlg->getProperty("OutputWorkspace"); ITableWorkspace_sptr tablews = statsAlg->getProperty("StatisticsTable"); if (runName.compare("Overall") == 0) setProperty("OutputWorkspace", statsWksp); setProperty("StatisticsTable", tablews); }
/** Executes the algorithm * @throw Exception::FileError If the grouping file cannot be opened or read * successfully * @throw runtime_error If unable to run one of the Child Algorithms * successfully */ void AlignAndFocusPowder::exec() { // retrieve the properties m_inputW = getProperty("InputWorkspace"); m_inputEW = boost::dynamic_pointer_cast<EventWorkspace>(m_inputW); m_instName = m_inputW->getInstrument()->getName(); m_instName = Kernel::ConfigService::Instance().getInstrument(m_instName).shortName(); std::string calFilename = getPropertyValue("CalFileName"); std::string groupFilename = getPropertyValue("GroupFilename"); m_calibrationWS = getProperty("CalibrationWorkspace"); m_maskWS = getProperty("MaskWorkspace"); m_groupWS = getProperty("GroupingWorkspace"); DataObjects::TableWorkspace_sptr maskBinTableWS = getProperty("MaskBinTable"); m_l1 = getProperty("PrimaryFlightPath"); specids = getProperty("SpectrumIDs"); l2s = getProperty("L2"); tths = getProperty("Polar"); phis = getProperty("Azimuthal"); m_params = getProperty("Params"); dspace = getProperty("DSpacing"); auto dmin = getVecPropertyFromPmOrSelf("DMin", m_dmins); auto dmax = getVecPropertyFromPmOrSelf("DMax", m_dmaxs); LRef = getProperty("UnwrapRef"); DIFCref = getProperty("LowResRef"); minwl = getProperty("CropWavelengthMin"); maxwl = getProperty("CropWavelengthMax"); if (maxwl == 0.) maxwl = EMPTY_DBL(); // python can only specify 0 for unused tmin = getProperty("TMin"); tmax = getProperty("TMax"); m_preserveEvents = getProperty("PreserveEvents"); m_resampleX = getProperty("ResampleX"); // determine some bits about d-space and binning if (m_resampleX != 0) { m_params.clear(); // ignore the normal rebin parameters } else if (m_params.size() == 1) { if (dmax > 0.) dspace = true; else dspace = false; } if (dspace) { if (m_params.size() == 1 && dmax > 0) { double step = m_params[0]; m_params.clear(); if (step > 0 || dmin > 0) { m_params.push_back(dmin); m_params.push_back(step); m_params.push_back(dmax); g_log.information() << "d-Spacing Binning: " << m_params[0] << " " << m_params[1] << " " << m_params[2] << "\n"; } } } else { if (m_params.size() == 1 && tmax > 0) { double step = m_params[0]; if (step > 0 || tmin > 0) { m_params[0] = tmin; m_params.push_back(step); m_params.push_back(tmax); g_log.information() << "TOF Binning: " << m_params[0] << " " << m_params[1] << " " << m_params[2] << "\n"; } } } xmin = 0.; xmax = 0.; if (tmin > 0.) { xmin = tmin; } if (tmax > 0.) { xmax = tmax; } if (!dspace && m_params.size() == 3) { xmin = m_params[0]; xmax = m_params[2]; } // Low resolution int lowresoffset = getProperty("LowResSpectrumOffset"); if (lowresoffset < 0) { m_processLowResTOF = false; } else { m_processLowResTOF = true; m_lowResSpecOffset = static_cast<size_t>(lowresoffset); } loadCalFile(calFilename, groupFilename); // Now setup the output workspace m_outputW = getProperty("OutputWorkspace"); if (m_inputEW) { if (m_outputW != m_inputW) { m_outputEW = m_inputEW->clone(); } m_outputEW = boost::dynamic_pointer_cast<EventWorkspace>(m_outputW); } else { if (m_outputW != m_inputW) { m_outputW = WorkspaceFactory::Instance().create(m_inputW); } } if (m_processLowResTOF) { if (!m_inputEW) { throw std::runtime_error( "Input workspace is not EventWorkspace. It is not supported now."); } else { // Make a brand new EventWorkspace m_lowResEW = boost::dynamic_pointer_cast<EventWorkspace>( WorkspaceFactory::Instance().create( "EventWorkspace", m_inputEW->getNumberHistograms(), 2, 1)); // Cast to the matrixOutputWS and save it m_lowResW = boost::dynamic_pointer_cast<MatrixWorkspace>(m_lowResEW); // m_lowResW->setName(lowreswsname); } } // set up a progress bar with the "correct" number of steps m_progress = new Progress(this, 0., 1., 22); if (m_inputEW) { double tolerance = getProperty("CompressTolerance"); if (tolerance > 0.) { g_log.information() << "running CompressEvents(Tolerance=" << tolerance << ") started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr compressAlg = createChildAlgorithm("CompressEvents"); compressAlg->setProperty("InputWorkspace", m_outputEW); compressAlg->setProperty("OutputWorkspace", m_outputEW); compressAlg->setProperty("OutputWorkspace", m_outputEW); compressAlg->setProperty("Tolerance", tolerance); compressAlg->executeAsChildAlg(); m_outputEW = compressAlg->getProperty("OutputWorkspace"); m_outputW = boost::dynamic_pointer_cast<MatrixWorkspace>(m_outputEW); } else { g_log.information() << "Not compressing event list\n"; doSortEvents(m_outputW); // still sort to help some thing out } } m_progress->report(); if (xmin > 0. || xmax > 0.) { double tempmin; double tempmax; m_outputW->getXMinMax(tempmin, tempmax); g_log.information() << "running CropWorkspace(TOFmin=" << xmin << ", TOFmax=" << xmax << ") started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr cropAlg = createChildAlgorithm("CropWorkspace"); cropAlg->setProperty("InputWorkspace", m_outputW); cropAlg->setProperty("OutputWorkspace", m_outputW); if ((xmin > 0.) && (xmin > tempmin)) cropAlg->setProperty("Xmin", xmin); if ((xmax > 0.) && (xmax < tempmax)) cropAlg->setProperty("Xmax", xmax); cropAlg->executeAsChildAlg(); m_outputW = cropAlg->getProperty("OutputWorkspace"); m_outputEW = boost::dynamic_pointer_cast<EventWorkspace>(m_outputW); } m_progress->report(); // filter the input events if appropriate double removePromptPulseWidth = getProperty("RemovePromptPulseWidth"); if (removePromptPulseWidth > 0.) { m_outputEW = boost::dynamic_pointer_cast<EventWorkspace>(m_outputW); if (m_outputEW->getNumberEvents() > 0) { g_log.information() << "running RemovePromptPulse(Width=" << removePromptPulseWidth << ") started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr filterPAlg = createChildAlgorithm("RemovePromptPulse"); filterPAlg->setProperty("InputWorkspace", m_outputW); filterPAlg->setProperty("OutputWorkspace", m_outputW); filterPAlg->setProperty("Width", removePromptPulseWidth); filterPAlg->executeAsChildAlg(); m_outputW = filterPAlg->getProperty("OutputWorkspace"); m_outputEW = boost::dynamic_pointer_cast<EventWorkspace>(m_outputW); } else { g_log.information("skipping RemovePromptPulse on empty EventWorkspace"); } } m_progress->report(); if (maskBinTableWS) { g_log.information() << "running MaskBinsFromTable started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr alg = createChildAlgorithm("MaskBinsFromTable"); alg->setProperty("InputWorkspace", m_outputW); alg->setProperty("OutputWorkspace", m_outputW); alg->setProperty("MaskingInformation", maskBinTableWS); alg->executeAsChildAlg(); m_outputW = alg->getProperty("OutputWorkspace"); m_outputEW = boost::dynamic_pointer_cast<EventWorkspace>(m_outputW); } m_progress->report(); if (m_maskWS) { g_log.information() << "running MaskDetectors started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr maskAlg = createChildAlgorithm("MaskDetectors"); maskAlg->setProperty("Workspace", m_outputW); maskAlg->setProperty("MaskedWorkspace", m_maskWS); maskAlg->executeAsChildAlg(); Workspace_sptr tmpW = maskAlg->getProperty("Workspace"); m_outputW = boost::dynamic_pointer_cast<MatrixWorkspace>(tmpW); m_outputEW = boost::dynamic_pointer_cast<EventWorkspace>(m_outputW); } m_progress->report(); if (!dspace) m_outputW = rebin(m_outputW); m_progress->report(); if (m_calibrationWS) { g_log.information() << "running AlignDetectors started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr alignAlg = createChildAlgorithm("AlignDetectors"); alignAlg->setProperty("InputWorkspace", m_outputW); alignAlg->setProperty("OutputWorkspace", m_outputW); alignAlg->setProperty("CalibrationWorkspace", m_calibrationWS); alignAlg->executeAsChildAlg(); m_outputW = alignAlg->getProperty("OutputWorkspace"); } else { m_outputW = convertUnits(m_outputW, "dSpacing"); } m_progress->report(); if (LRef > 0. || minwl > 0. || DIFCref > 0. || (!isEmpty(maxwl))) { m_outputW = convertUnits(m_outputW, "TOF"); } m_progress->report(); // Beyond this point, low resolution TOF workspace is considered. if (LRef > 0.) { g_log.information() << "running UnwrapSNS(LRef=" << LRef << ",Tmin=" << tmin << ",Tmax=" << tmax << ") started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr removeAlg = createChildAlgorithm("UnwrapSNS"); removeAlg->setProperty("InputWorkspace", m_outputW); removeAlg->setProperty("OutputWorkspace", m_outputW); removeAlg->setProperty("LRef", LRef); if (tmin > 0.) removeAlg->setProperty("Tmin", tmin); if (tmax > tmin) removeAlg->setProperty("Tmax", tmax); removeAlg->executeAsChildAlg(); m_outputW = removeAlg->getProperty("OutputWorkspace"); } m_progress->report(); if (minwl > 0. || (!isEmpty(maxwl))) { // just crop the worksapce // turn off the low res stuff m_processLowResTOF = false; EventWorkspace_sptr ews = boost::dynamic_pointer_cast<EventWorkspace>(m_outputW); if (ews) g_log.information() << "Number of events = " << ews->getNumberEvents() << ". "; g_log.information("\n"); m_outputW = convertUnits(m_outputW, "Wavelength"); g_log.information() << "running CropWorkspace(WavelengthMin=" << minwl; if (!isEmpty(maxwl)) g_log.information() << ", WavelengthMax=" << maxwl; g_log.information() << ") started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr removeAlg = createChildAlgorithm("CropWorkspace"); removeAlg->setProperty("InputWorkspace", m_outputW); removeAlg->setProperty("OutputWorkspace", m_outputW); removeAlg->setProperty("XMin", minwl); removeAlg->setProperty("XMax", maxwl); removeAlg->executeAsChildAlg(); m_outputW = removeAlg->getProperty("OutputWorkspace"); if (ews) g_log.information() << "Number of events = " << ews->getNumberEvents() << ".\n"; } else if (DIFCref > 0.) { g_log.information() << "running RemoveLowResTof(RefDIFC=" << DIFCref << ",K=3.22) started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; EventWorkspace_sptr ews = boost::dynamic_pointer_cast<EventWorkspace>(m_outputW); if (ews) g_log.information() << "Number of events = " << ews->getNumberEvents() << ". "; g_log.information("\n"); API::IAlgorithm_sptr removeAlg = createChildAlgorithm("RemoveLowResTOF"); removeAlg->setProperty("InputWorkspace", m_outputW); removeAlg->setProperty("OutputWorkspace", m_outputW); removeAlg->setProperty("ReferenceDIFC", DIFCref); removeAlg->setProperty("K", 3.22); if (tmin > 0.) removeAlg->setProperty("Tmin", tmin); if (m_processLowResTOF) removeAlg->setProperty("LowResTOFWorkspace", m_lowResW); removeAlg->executeAsChildAlg(); m_outputW = removeAlg->getProperty("OutputWorkspace"); if (m_processLowResTOF) m_lowResW = removeAlg->getProperty("LowResTOFWorkspace"); } m_progress->report(); EventWorkspace_sptr ews = boost::dynamic_pointer_cast<EventWorkspace>(m_outputW); if (ews) { size_t numhighevents = ews->getNumberEvents(); if (m_processLowResTOF) { EventWorkspace_sptr lowes = boost::dynamic_pointer_cast<EventWorkspace>(m_lowResW); size_t numlowevents = lowes->getNumberEvents(); g_log.information() << "Number of high TOF events = " << numhighevents << "; " << "Number of low TOF events = " << numlowevents << ".\n"; } } m_progress->report(); // Convert units if (LRef > 0. || minwl > 0. || DIFCref > 0. || (!isEmpty(maxwl))) { m_outputW = convertUnits(m_outputW, "dSpacing"); if (m_processLowResTOF) m_lowResW = convertUnits(m_lowResW, "dSpacing"); } m_progress->report(); if (dspace) { m_outputW = rebin(m_outputW); if (m_processLowResTOF) m_lowResW = rebin(m_lowResW); } m_progress->report(); doSortEvents(m_outputW); if (m_processLowResTOF) doSortEvents(m_lowResW); m_progress->report(); // Diffraction focus m_outputW = diffractionFocus(m_outputW); if (m_processLowResTOF) m_lowResW = diffractionFocus(m_lowResW); m_progress->report(); doSortEvents(m_outputW); if (m_processLowResTOF) doSortEvents(m_lowResW); m_progress->report(); // this next call should probably be in for rebin as well // but it changes the system tests if (dspace && m_resampleX != 0) { m_outputW = rebin(m_outputW); if (m_processLowResTOF) m_lowResW = rebin(m_lowResW); } m_progress->report(); // edit the instrument geometry if (m_groupWS && (m_l1 > 0 || !tths.empty() || !l2s.empty() || !phis.empty())) { size_t numreg = m_outputW->getNumberHistograms(); try { // set up the vectors for doing everything auto specidsSplit = splitVectors(specids, numreg, "specids"); auto tthsSplit = splitVectors(tths, numreg, "two-theta"); auto l2sSplit = splitVectors(l2s, numreg, "L2"); auto phisSplit = splitVectors(phis, numreg, "phi"); // Edit instrument m_outputW = editInstrument(m_outputW, tthsSplit.reg, specidsSplit.reg, l2sSplit.reg, phisSplit.reg); if (m_processLowResTOF) { m_lowResW = editInstrument(m_lowResW, tthsSplit.low, specidsSplit.low, l2sSplit.low, phisSplit.low); } } catch (std::runtime_error &e) { g_log.warning("Not editing instrument geometry:"); g_log.warning(e.what()); } } m_progress->report(); // Conjoin 2 workspaces if there is low resolution if (m_processLowResTOF) { m_outputW = conjoinWorkspaces(m_outputW, m_lowResW, m_lowResSpecOffset); } m_progress->report(); // Convert units to TOF m_outputW = convertUnits(m_outputW, "TOF"); m_progress->report(); // compress again if appropriate double tolerance = getProperty("CompressTolerance"); m_outputEW = boost::dynamic_pointer_cast<EventWorkspace>(m_outputW); if ((m_outputEW) && (tolerance > 0.)) { g_log.information() << "running CompressEvents(Tolerance=" << tolerance << ") started at " << Kernel::DateAndTime::getCurrentTime() << "\n"; API::IAlgorithm_sptr compressAlg = createChildAlgorithm("CompressEvents"); compressAlg->setProperty("InputWorkspace", m_outputEW); compressAlg->setProperty("OutputWorkspace", m_outputEW); compressAlg->setProperty("OutputWorkspace", m_outputEW); compressAlg->setProperty("Tolerance", tolerance); compressAlg->executeAsChildAlg(); m_outputEW = compressAlg->getProperty("OutputWorkspace"); m_outputW = boost::dynamic_pointer_cast<MatrixWorkspace>(m_outputEW); } m_progress->report(); if ((!m_params.empty()) && (m_params.size() != 1)) { m_params.erase(m_params.begin()); m_params.pop_back(); } if (!m_dmins.empty()) m_dmins.clear(); if (!m_dmaxs.empty()) m_dmaxs.clear(); m_outputW = rebin(m_outputW); m_progress->report(); // return the output workspace setProperty("OutputWorkspace", m_outputW); }
/** * Execute the algorithm. */ void LoadBBY::exec() { // Delete the output workspace name if it existed std::string outName = getPropertyValue("OutputWorkspace"); if (API::AnalysisDataService::Instance().doesExist(outName)) API::AnalysisDataService::Instance().remove(outName); // Get the name of the data file. std::string filename = getPropertyValue(FilenameStr); ANSTO::Tar::File tarFile(filename); if (!tarFile.good()) throw std::invalid_argument("invalid BBY file"); // region of intreset std::vector<bool> roi = createRoiVector(getPropertyValue(MaskStr)); double tofMinBoundary = getProperty(FilterByTofMinStr); double tofMaxBoundary = getProperty(FilterByTofMaxStr); double timeMinBoundary = getProperty(FilterByTimeStartStr); double timeMaxBoundary = getProperty(FilterByTimeStopStr); if (isEmpty(tofMaxBoundary)) tofMaxBoundary = std::numeric_limits<double>::infinity(); if (isEmpty(timeMaxBoundary)) timeMaxBoundary = std::numeric_limits<double>::infinity(); API::Progress prog(this, 0.0, 1.0, Progress_Total); prog.doReport("creating instrument"); // create workspace DataObjects::EventWorkspace_sptr eventWS = boost::make_shared<DataObjects::EventWorkspace>(); eventWS->initialize(HISTO_BINS_Y * HISTO_BINS_X, 2, // number of TOF bin boundaries 1); // set the units eventWS->getAxis(0)->unit() = Kernel::UnitFactory::Instance().create("TOF"); eventWS->setYUnit("Counts"); // set title const std::vector<std::string> &subFiles = tarFile.files(); for (const auto &subFile : subFiles) if (subFile.compare(0, 3, "BBY") == 0) { std::string title = subFile; if (title.rfind(".hdf") == title.length() - 4) title.resize(title.length() - 4); if (title.rfind(".nx") == title.length() - 3) title.resize(title.length() - 3); eventWS->setTitle(title); break; } // create instrument InstrumentInfo instrumentInfo; // Geometry::Instrument_sptr instrument = createInstrument(tarFile, /* ref */ instrumentInfo); // eventWS->setInstrument(instrument); // load events size_t numberHistograms = eventWS->getNumberHistograms(); std::vector<EventVector_pt> eventVectors(numberHistograms, nullptr); std::vector<size_t> eventCounts(numberHistograms, 0); // phase correction Kernel::Property *periodMasterProperty = getPointerToProperty(PeriodMasterStr); Kernel::Property *periodSlaveProperty = getPointerToProperty(PeriodSlaveStr); Kernel::Property *phaseSlaveProperty = getPointerToProperty(PhaseSlaveStr); double periodMaster; double periodSlave; double phaseSlave; if (periodMasterProperty->isDefault() || periodSlaveProperty->isDefault() || phaseSlaveProperty->isDefault()) { if (!periodMasterProperty->isDefault() || !periodSlaveProperty->isDefault() || !phaseSlaveProperty->isDefault()) { throw std::invalid_argument("Please specify PeriodMaster, PeriodSlave " "and PhaseSlave or none of them."); } // if values have not been specified in loader then use values from hdf file periodMaster = instrumentInfo.period_master; periodSlave = instrumentInfo.period_slave; phaseSlave = instrumentInfo.phase_slave; } else { periodMaster = getProperty(PeriodMasterStr); periodSlave = getProperty(PeriodSlaveStr); phaseSlave = getProperty(PhaseSlaveStr); if ((periodMaster < 0.0) || (periodSlave < 0.0)) throw std::invalid_argument( "Please specify a positive value for PeriodMaster and PeriodSlave."); } double period = periodSlave; double shift = -1.0 / 6.0 * periodMaster - periodSlave * phaseSlave / 360.0; // count total events per pixel to reserve necessary memory ANSTO::EventCounter eventCounter( roi, HISTO_BINS_Y, period, shift, tofMinBoundary, tofMaxBoundary, timeMinBoundary, timeMaxBoundary, eventCounts); loadEvents(prog, "loading neutron counts", tarFile, eventCounter); // prepare event storage ANSTO::ProgressTracker progTracker(prog, "creating neutron event lists", numberHistograms, Progress_ReserveMemory); for (size_t i = 0; i != numberHistograms; ++i) { DataObjects::EventList &eventList = eventWS->getEventList(i); eventList.setSortOrder(DataObjects::PULSETIME_SORT); eventList.reserve(eventCounts[i]); eventList.setDetectorID(static_cast<detid_t>(i)); eventList.setSpectrumNo(static_cast<detid_t>(i)); DataObjects::getEventsFrom(eventList, eventVectors[i]); progTracker.update(i); } progTracker.complete(); ANSTO::EventAssigner eventAssigner( roi, HISTO_BINS_Y, period, shift, tofMinBoundary, tofMaxBoundary, timeMinBoundary, timeMaxBoundary, eventVectors); loadEvents(prog, "loading neutron events", tarFile, eventAssigner); Kernel::cow_ptr<MantidVec> axis; MantidVec &xRef = axis.access(); xRef.resize(2, 0.0); xRef[0] = std::max( 0.0, floor(eventCounter.tofMin())); // just to make sure the bins hold it all xRef[1] = eventCounter.tofMax() + 1; eventWS->setAllX(axis); // count total number of masked bins size_t maskedBins = 0; for (size_t i = 0; i != roi.size(); i++) if (!roi[i]) maskedBins++; if (maskedBins > 0) { // create list of masked bins std::vector<size_t> maskIndexList(maskedBins); size_t maskIndex = 0; for (size_t i = 0; i != roi.size(); i++) if (!roi[i]) maskIndexList[maskIndex++] = i; API::IAlgorithm_sptr maskingAlg = createChildAlgorithm("MaskDetectors"); maskingAlg->setProperty("Workspace", eventWS); maskingAlg->setProperty("WorkspaceIndexList", maskIndexList); maskingAlg->executeAsChildAlg(); } // set log values API::LogManager &logManager = eventWS->mutableRun(); logManager.addProperty("filename", filename); logManager.addProperty("att_pos", static_cast<int>(instrumentInfo.att_pos)); logManager.addProperty("frame_count", static_cast<int>(eventCounter.numFrames())); logManager.addProperty("period", period); // currently beam monitor counts are not available, instead number of frames // times period is used logManager.addProperty( "bm_counts", static_cast<double>(eventCounter.numFrames()) * period / 1.0e6); // static_cast<double>(instrumentInfo.bm_counts) // currently Kernel::time_duration duration = boost::posix_time::microseconds(static_cast<boost::int64_t>( static_cast<double>(eventCounter.numFrames()) * period)); Kernel::DateAndTime start_time("2000-01-01T00:00:00"); Kernel::DateAndTime end_time(start_time + duration); logManager.addProperty("start_time", start_time.toISO8601String()); logManager.addProperty("end_time", end_time.toISO8601String()); std::string time_str = start_time.toISO8601String(); AddSinglePointTimeSeriesProperty(logManager, time_str, "L1_chopper_value", instrumentInfo.L1_chopper_value); AddSinglePointTimeSeriesProperty(logManager, time_str, "L2_det_value", instrumentInfo.L2_det_value); AddSinglePointTimeSeriesProperty(logManager, time_str, "L2_curtainl_value", instrumentInfo.L2_curtainl_value); AddSinglePointTimeSeriesProperty(logManager, time_str, "L2_curtainr_value", instrumentInfo.L2_curtainr_value); AddSinglePointTimeSeriesProperty(logManager, time_str, "L2_curtainu_value", instrumentInfo.L2_curtainu_value); AddSinglePointTimeSeriesProperty(logManager, time_str, "L2_curtaind_value", instrumentInfo.L2_curtaind_value); AddSinglePointTimeSeriesProperty(logManager, time_str, "D_det_value", instrumentInfo.D_det_value); AddSinglePointTimeSeriesProperty(logManager, time_str, "D_curtainl_value", instrumentInfo.D_curtainl_value); AddSinglePointTimeSeriesProperty(logManager, time_str, "D_curtainr_value", instrumentInfo.D_curtainr_value); AddSinglePointTimeSeriesProperty(logManager, time_str, "D_curtainu_value", instrumentInfo.D_curtainu_value); AddSinglePointTimeSeriesProperty(logManager, time_str, "D_curtaind_value", instrumentInfo.D_curtaind_value); AddSinglePointTimeSeriesProperty(logManager, time_str, "curtain_rotation", 10.0); API::IAlgorithm_sptr loadInstrumentAlg = createChildAlgorithm("LoadInstrument"); loadInstrumentAlg->setProperty("Workspace", eventWS); loadInstrumentAlg->setPropertyValue("InstrumentName", "BILBY"); loadInstrumentAlg->setProperty("RewriteSpectraMap", Mantid::Kernel::OptionalBool(false)); loadInstrumentAlg->executeAsChildAlg(); setProperty("OutputWorkspace", eventWS); }
/** Calls Gaussian1D as a child algorithm to fit the offset peak in a spectrum * * @param wi :: The Workspace Index to fit. * @param inputW :: Input workspace. * @param peakPositions :: Peak positions. * @param fitWindows :: Fit windows. * @param nparams :: Number of parameters. * @param minD :: Min distance. * @param maxD :: Max distance. * @param peakPosToFit :: Actual peak positions to fit (output). * @param peakPosFitted :: Actual peak positions fitted (output). * @param chisq :: chisq. * @param peakHeights :: vector for fitted heights of peaks * @param i_highestpeak:: index of the highest peak among all peaks * @param resolution :: spectrum's resolution delta(d)/d * @param dev_resolution :: standard deviation resolution * @return The number of peaks in range */ int GetDetOffsetsMultiPeaks::fitSpectra( const int64_t wi, MatrixWorkspace_sptr inputW, const std::vector<double> &peakPositions, const std::vector<double> &fitWindows, size_t &nparams, double &minD, double &maxD, std::vector<double> &peakPosToFit, std::vector<double> &peakPosFitted, std::vector<double> &chisq, std::vector<double> &peakHeights, int &i_highestpeak, double &resolution, double &dev_resolution) { // Default overall fit range is the whole spectrum const MantidVec &X = inputW->readX(wi); minD = X.front(); maxD = X.back(); // Trim in the edges based on where the data turns off of zero const MantidVec &Y = inputW->readY(wi); size_t minDindex = 0; for (; minDindex < Y.size(); ++minDindex) { if (Y[minDindex] > 0.) { minD = X[minDindex]; break; } } if (minD >= maxD) { // throw if minD >= maxD std::stringstream ess; ess << "Stuff went wrong with wkspIndex=" << wi << " specIndex=" << inputW->getSpectrum(wi)->getSpectrumNo(); throw std::runtime_error(ess.str()); } size_t maxDindex = Y.size() - 1; for (; maxDindex > minDindex; --maxDindex) { if (Y[maxDindex] > 0.) { maxD = X[maxDindex]; break; } } std::stringstream dbss; dbss << "D-RANGE[" << inputW->getSpectrum(wi)->getSpectrumNo() << "]: " << minD << " -> " << maxD; g_log.debug(dbss.str()); // Setup the fit windows bool useFitWindows = (!fitWindows.empty()); std::vector<double> fitWindowsToUse; for (int i = 0; i < static_cast<int>(peakPositions.size()); ++i) { if ((peakPositions[i] > minD) && (peakPositions[i] < maxD)) { if (m_useFitWindowTable) { fitWindowsToUse.push_back(std::max(m_vecFitWindow[wi][2 * i], minD)); fitWindowsToUse.push_back( std::min(m_vecFitWindow[wi][2 * i + 1], maxD)); } else if (useFitWindows) { fitWindowsToUse.push_back(std::max(fitWindows[2 * i], minD)); fitWindowsToUse.push_back(std::min(fitWindows[2 * i + 1], maxD)); } peakPosToFit.push_back(peakPositions[i]); } } int numPeaksInRange = static_cast<int>(peakPosToFit.size()); if (numPeaksInRange == 0) { std::stringstream outss; outss << "Spectrum " << wi << " has no peak in range (" << minD << ", " << maxD << ")"; g_log.information(outss.str()); return 0; } // Fit peaks API::IAlgorithm_sptr findpeaks = createChildAlgorithm("FindPeaks", -1, -1, false); findpeaks->setProperty("InputWorkspace", inputW); findpeaks->setProperty<int>("FWHM", 7); findpeaks->setProperty<int>("Tolerance", 4); // FindPeaks will do the checking on the validity of WorkspaceIndex findpeaks->setProperty("WorkspaceIndex", static_cast<int>(wi)); // Get the specified peak positions, which is optional findpeaks->setProperty("PeakPositions", peakPosToFit); if (useFitWindows) findpeaks->setProperty("FitWindows", fitWindowsToUse); findpeaks->setProperty<std::string>("PeakFunction", m_peakType); findpeaks->setProperty<std::string>("BackgroundType", m_backType); findpeaks->setProperty<bool>("HighBackground", this->getProperty("HighBackground")); findpeaks->setProperty<int>("MinGuessedPeakWidth", 4); findpeaks->setProperty<int>("MaxGuessedPeakWidth", 4); findpeaks->setProperty<double>("MinimumPeakHeight", m_minPeakHeight); findpeaks->setProperty("StartFromObservedPeakCentre", true); findpeaks->executeAsChildAlg(); // Collect fitting resutl of all peaks ITableWorkspace_sptr peakslist = findpeaks->getProperty("PeaksList"); // use tmpPeakPosToFit to shuffle the vectors std::vector<double> tmpPeakPosToFit; generatePeaksList(peakslist, static_cast<int>(wi), peakPosToFit, tmpPeakPosToFit, peakPosFitted, peakHeights, chisq, (useFitWindows || m_useFitWindowTable), fitWindowsToUse, minD, maxD, resolution, dev_resolution); peakPosToFit = tmpPeakPosToFit; nparams = peakPosFitted.size(); // Find the highest peak i_highestpeak = -1; double maxheight = 0; for (int i = 0; i < static_cast<int>(peakPosFitted.size()); ++i) { double tmpheight = peakHeights[i]; if (tmpheight > maxheight) { maxheight = tmpheight; i_highestpeak = i; } } return numPeaksInRange; }
/// Execute the algorithm void SassenaFFT::exec() { const std::string gwsName = this->getPropertyValue("InputWorkspace"); API::WorkspaceGroup_sptr gws = this->getProperty("InputWorkspace"); const std::string ftqReName = gwsName + "_fqt.Re"; const std::string ftqImName = gwsName + "_fqt.Im"; // Make sure the intermediate structure factor is there if(!gws->contains(ftqReName) ) { const std::string errMessg = "workspace "+gwsName+" does not contain an intermediate structure factor"; this->g_log.error(errMessg); throw Kernel::Exception::NotFoundError("group workspace does not contain",ftqReName); } // Retrieve the real and imaginary parts of the intermediate scattering function DataObjects::Workspace2D_sptr fqtRe = boost::dynamic_pointer_cast<DataObjects::Workspace2D>( gws->getItem( ftqReName ) ); DataObjects::Workspace2D_sptr fqtIm = boost::dynamic_pointer_cast<DataObjects::Workspace2D>( gws->getItem( ftqImName ) ); // Calculate the FFT for all spectra, retaining only the real part since F(q,-t) = F*(q,t) int part=3; // extract the real part of the transform, assuming I(Q,t) is real const std::string sqwName = gwsName + "_sqw"; API::IAlgorithm_sptr fft = this->createChildAlgorithm("ExtractFFTSpectrum"); fft->setProperty<DataObjects::Workspace2D_sptr>("InputWorkspace", fqtRe); if( !this->getProperty("FFTonlyRealPart") ) { part=0; // extract the real part of the transform, assuming I(Q,t) is complex fft->setProperty<DataObjects::Workspace2D_sptr>("InputImagWorkspace", fqtIm); } fft->setPropertyValue("OutputWorkspace", sqwName ); fft->setProperty<int>("FFTPart",part); // extract the real part fft->executeAsChildAlg(); API::MatrixWorkspace_sptr sqw0 = fft->getProperty("OutputWorkspace"); DataObjects::Workspace2D_sptr sqw = boost::dynamic_pointer_cast<DataObjects::Workspace2D>( sqw0 ); API::AnalysisDataService::Instance().addOrReplace( sqwName, sqw ); // Transform the X-axis to appropriate dimensions // We assume the units of the intermediate scattering function are in picoseconds // The resulting frequency unit is in mili-eV, thus use m_ps2meV API::IAlgorithm_sptr scaleX = this->createChildAlgorithm("ScaleX"); scaleX->setProperty<DataObjects::Workspace2D_sptr>("InputWorkspace",sqw); scaleX->setProperty<double>("Factor", m_ps2meV); scaleX->setProperty<DataObjects::Workspace2D_sptr>("OutputWorkspace", sqw); scaleX->executeAsChildAlg(); //Do we apply the detailed balance condition exp(E/(2*kT)) ? if( this->getProperty("DetailedBalance") ) { double T = this->getProperty("Temp"); // The ExponentialCorrection algorithm assumes the form C0*exp(-C1*x). Note the explicit minus in the exponent API::IAlgorithm_sptr ec = this->createChildAlgorithm("ExponentialCorrection"); ec->setProperty<DataObjects::Workspace2D_sptr>("InputWorkspace", sqw); ec->setProperty<DataObjects::Workspace2D_sptr>("OutputWorkspace", sqw); ec->setProperty<double>("C0",1.0); ec->setProperty<double>("C1",-1.0/(2.0*T*m_T2ueV)); // Temperature in units of ueV ec->setPropertyValue("Operation","Multiply"); ec->executeAsChildAlg(); } // Set the Energy unit for the X-axis sqw->getAxis(0)->unit() = Kernel::UnitFactory::Instance().create("DeltaE"); // Add to group workspace, except if we are replacing the workspace. In this case, the group workspace // is already notified of the changes by the analysis data service. if(!gws->contains(sqwName)) { gws->add( sqwName ); } else { this->g_log.information("Workspace "+sqwName+" replaced with new contents"); } }
/** Select background automatically */ DataObjects::Workspace2D_sptr ProcessBackground::autoBackgroundSelection(Workspace2D_sptr bkgdWS) { // Get background type and create bakground function BackgroundFunction_sptr bkgdfunction = createBackgroundFunction(m_bkgdType); int bkgdorder = getProperty("BackgroundOrder"); if (bkgdorder == 0) g_log.warning("(Input) background function order is 0. It might not be " "able to give a good estimation."); bkgdfunction->setAttributeValue("n", bkgdorder); bkgdfunction->initialize(); g_log.information() << "Input background points has " << bkgdWS->readX(0).size() << " data points for fit " << bkgdorder << "-th order " << bkgdfunction->name() << " (background) function" << bkgdfunction->asString() << "\n"; // Fit input (a few) background pionts to get initial guess API::IAlgorithm_sptr fit; try { fit = this->createChildAlgorithm("Fit", 0.0, 0.2, true); } catch (Exception::NotFoundError &) { g_log.error() << "Requires CurveFitting library." << std::endl; throw; } double startx = m_lowerBound; double endx = m_upperBound; fit->setProperty("Function", boost::dynamic_pointer_cast<API::IFunction>(bkgdfunction)); fit->setProperty("InputWorkspace", bkgdWS); fit->setProperty("WorkspaceIndex", 0); fit->setProperty("MaxIterations", 500); fit->setProperty("StartX", startx); fit->setProperty("EndX", endx); fit->setProperty("Minimizer", "Levenberg-Marquardt"); fit->setProperty("CostFunction", "Least squares"); fit->executeAsChildAlg(); // Get fit result // a) Status std::string fitStatus = fit->getProperty("OutputStatus"); bool allowedfailure = (fitStatus.find("cannot") < fitStatus.size()) && (fitStatus.find("tolerance") < fitStatus.size()); if (fitStatus.compare("success") != 0 && !allowedfailure) { g_log.error() << "ProcessBackground: Fit Status = " << fitStatus << ". Not to update fit result" << std::endl; throw std::runtime_error("Bad Fit"); } // b) check that chi2 got better const double chi2 = fit->getProperty("OutputChi2overDoF"); g_log.information() << "Fit background: Fit Status = " << fitStatus << ", chi2 = " << chi2 << "\n"; // Filter and construct for the output workspace Workspace2D_sptr outws = filterForBackground(bkgdfunction); return outws; } // END OF FUNCTION
/** Select background automatically */ DataObjects::Workspace2D_sptr ProcessBackground::autoBackgroundSelection(Workspace2D_sptr bkgdWS) { // Get background type and create bakground function BackgroundFunction_sptr bkgdfunction = createBackgroundFunction(m_bkgdType); int bkgdorder = getProperty("BackgroundOrder"); bkgdfunction->setAttributeValue("n", bkgdorder); g_log.debug() << "DBx622 Background Workspace has " << bkgdWS->readX(0).size() << " data points." << std::endl; // Fit input (a few) background pionts to get initial guess API::IAlgorithm_sptr fit; try { fit = this->createChildAlgorithm("Fit", 0.0, 0.2, true); } catch (Exception::NotFoundError &) { g_log.error() << "Requires CurveFitting library." << std::endl; throw; } double startx = m_lowerBound; double endx = m_upperBound; fit->setProperty("Function", boost::dynamic_pointer_cast<API::IFunction>(bkgdfunction)); fit->setProperty("InputWorkspace", bkgdWS); fit->setProperty("WorkspaceIndex", 0); fit->setProperty("MaxIterations", 500); fit->setProperty("StartX", startx); fit->setProperty("EndX", endx); fit->setProperty("Minimizer", "Levenberg-Marquardt"); fit->setProperty("CostFunction", "Least squares"); fit->executeAsChildAlg(); // Get fit result // a) Status std::string fitStatus = fit->getProperty("OutputStatus"); bool allowedfailure = (fitStatus.find("cannot") < fitStatus.size()) && (fitStatus.find("tolerance") < fitStatus.size()); if (fitStatus.compare("success") != 0 && !allowedfailure) { g_log.error() << "ProcessBackground: Fit Status = " << fitStatus << ". Not to update fit result" << std::endl; throw std::runtime_error("Bad Fit"); } // b) check that chi2 got better const double chi2 = fit->getProperty("OutputChi2overDoF"); g_log.information() << "Fit background: Fit Status = " << fitStatus << ", chi2 = " << chi2 << "\n"; // c) get out the parameter names API::IFunction_sptr func = fit->getProperty("Function"); /* Comment out as not being used std::vector<std::string> parnames = func->getParameterNames(); std::map<std::string, double> parvalues; for (size_t iname = 0; iname < parnames.size(); ++iname) { double value = func->getParameter(parnames[iname]); parvalues.insert(std::make_pair(parnames[iname], value)); } DataObject::Workspace2D_const_sptr theorybackground = AnalysisDataService::Instance().retrieve(wsname); */ // Filter and construct for the output workspace Workspace2D_sptr outws = filterForBackground(bkgdfunction); return outws; } // END OF FUNCTION
void GoniometerAnglesFromPhiRotation::exec() { PeaksWorkspace_sptr PeaksRun1 = getProperty("PeaksWorkspace1"); PeaksWorkspace_sptr PeaksRun2 = getProperty("PeaksWorkspace2"); double Tolerance = getProperty("Tolerance"); Kernel::Matrix<double> Gon1(3, 3); Kernel::Matrix<double> Gon2(3, 3); if (!CheckForOneRun(PeaksRun1, Gon1) || !CheckForOneRun(PeaksRun2, Gon2)) { g_log.error("Each peaks workspace MUST have only one run"); throw std::invalid_argument("Each peaks workspace MUST have only one run"); } Kernel::Matrix<double> UB1; bool Run1HasOrientedLattice = true; if (!PeaksRun1->sample().hasOrientedLattice()) { Run1HasOrientedLattice = false; const std::string fft("FindUBUsingFFT"); API::IAlgorithm_sptr findUB = this->createChildAlgorithm(fft); findUB->initialize(); findUB->setProperty<PeaksWorkspace_sptr>("PeaksWorkspace", getProperty("PeaksWorkspace1")); findUB->setProperty("MIND", static_cast<double>(getProperty("MIND"))); findUB->setProperty("MAXD", static_cast<double>(getProperty("MAXD"))); findUB->setProperty("Tolerance", Tolerance); findUB->executeAsChildAlg(); if (!PeaksRun1->sample().hasOrientedLattice()) { g_log.notice(std::string("Could not find UB for ") + std::string(PeaksRun1->getName())); throw std::invalid_argument(std::string("Could not find UB for ") + std::string(PeaksRun1->getName())); } } //-------------get UB raw :No goniometer---------------- UB1 = PeaksRun1->sample().getOrientedLattice().getUB(); UB1 = getUBRaw(UB1, Gon1); int N1; double avErrIndx, avErrAll; IndexRaw(PeaksRun1, UB1, N1, avErrIndx, avErrAll, Tolerance); if (N1 < .6 * PeaksRun1->getNumberPeaks()) { g_log.notice(std::string("UB did not index well for ") + std::string(PeaksRun1->getName())); throw std::invalid_argument(std::string("UB did not index well for ") + std::string(PeaksRun1->getName())); } //---------------------------------------------- Geometry::OrientedLattice lat2 = PeaksRun1->sample().getOrientedLattice(); lat2.setUB(UB1); PeaksRun2->mutableSample().setOrientedLattice(&lat2); if (!Run1HasOrientedLattice) PeaksRun1->mutableSample().setOrientedLattice(nullptr); double dphi = static_cast<double>(getProperty("Phi2")) - static_cast<double>(getProperty("Run1Phi")); Kernel::Matrix<double> Gon22(3, 3, true); for (int i = 0; i < PeaksRun2->getNumberPeaks(); i++) { PeaksRun2->getPeak(i).setGoniometerMatrix(Gon22); } int RunNum = PeaksRun2->getPeak(0).getRunNumber(); std::string RunNumStr = std::to_string(RunNum); int Npeaks = PeaksRun2->getNumberPeaks(); // n indexed, av err, phi, chi,omega std::array<double, 5> MinData = {{0., 0., 0., 0., 0.}}; MinData[0] = 0.0; std::vector<V3D> directionList = IndexingUtils::MakeHemisphereDirections(50); API::FrameworkManager::Instance(); for (auto dir : directionList) for (int sgn = 1; sgn > -2; sgn -= 2) { dir.normalize(); Quat Q(sgn * dphi, dir); Q.normalize(); Kernel::Matrix<double> Rot(Q.getRotation()); int Nindexed; double dummyAvErrIndx, dummyAvErrAll; IndexRaw(PeaksRun2, Rot * UB1, Nindexed, dummyAvErrIndx, dummyAvErrAll, Tolerance); if (Nindexed > MinData[0]) { MinData[0] = Nindexed; MinData[1] = sgn; MinData[2] = dir[0]; MinData[3] = dir[1]; MinData[4] = dir[2]; } } g_log.debug() << "Best direction unOptimized is (" << (MinData[1] * MinData[2]) << "," << (MinData[1] * MinData[3]) << "," << (MinData[1] * MinData[4]) << ")\n"; //----------------------- Optimize around best---------------------------- auto ws = createWorkspace<Workspace2D>(1, 3 * Npeaks, 3 * Npeaks); MantidVec Xvals; for (int i = 0; i < Npeaks; ++i) { Xvals.push_back(i); Xvals.push_back(i); Xvals.push_back(i); } ws->setPoints(0, Xvals); //--------------------Set up other Fit function arguments------------------ V3D dir(MinData[2], MinData[3], MinData[4]); dir.normalize(); Quat Q(MinData[1] * dphi, dir); Q.normalize(); Kernel::Matrix<double> Rot(Q.getRotation()); Goniometer Gon(Rot); std::vector<double> omchiphi = Gon.getEulerAngles("yzy"); MinData[2] = omchiphi[2]; MinData[3] = omchiphi[1]; MinData[4] = omchiphi[0]; std::string FunctionArgs = "name=PeakHKLErrors, PeakWorkspaceName=" + PeaksRun2->getName() + ",OptRuns=" + RunNumStr + ",phi" + RunNumStr + "=" + boost::lexical_cast<std::string>(MinData[2]) + ",chi" + RunNumStr + "=" + boost::lexical_cast<std::string>(MinData[3]) + ",omega" + RunNumStr + "=" + boost::lexical_cast<std::string>(MinData[4]); std::string Constr = boost::lexical_cast<std::string>(MinData[2] - 5) + "<phi" + RunNumStr + "<" + boost::lexical_cast<std::string>(MinData[2] + 5); Constr += "," + boost::lexical_cast<std::string>(MinData[3] - 5) + "<chi" + RunNumStr + "<" + boost::lexical_cast<std::string>(MinData[3] + 5) + ","; Constr += boost::lexical_cast<std::string>(MinData[4] - 5) + "<omega" + RunNumStr + "<" + boost::lexical_cast<std::string>(MinData[4] + 5); std::string Ties = "SampleXOffset=0.0,SampleYOffset=0.0,SampleZOffset=0.0," "GonRotx=0.0,GonRoty=0.0,GonRotz=0.0"; boost::shared_ptr<Algorithm> Fit = createChildAlgorithm("Fit"); Fit->initialize(); Fit->setProperty("Function", FunctionArgs); Fit->setProperty("Ties", Ties); Fit->setProperty("Constraints", Constr); Fit->setProperty("InputWorkspace", ws); Fit->setProperty("CreateOutput", true); std::string outputName = "out"; Fit->setProperty("Output", outputName); Fit->executeAsChildAlg(); boost::shared_ptr<API::ITableWorkspace> results = Fit->getProperty("OutputParameters"); double chisq = Fit->getProperty("OutputChi2overDoF"); MinData[0] = chisq; MinData[2] = results->Double(6, 1); MinData[3] = results->Double(7, 1); MinData[4] = results->Double(8, 1); g_log.debug() << "Best direction Optimized is (" << (MinData[2]) << "," << (MinData[3]) << "," << (MinData[4]) << ")\n"; // ---------------------Find number indexed ----------------------- Quat Q1 = Quat(MinData[4], V3D(0, 1, 0)) * Quat(MinData[3], V3D(0, 0, 1)) * Quat(MinData[2], V3D(0, 1, 0)); int Nindexed; Kernel::Matrix<double> Mk(Q1.getRotation()); IndexRaw(PeaksRun2, Mk * UB1, Nindexed, avErrIndx, avErrAll, Tolerance); //------------------------------------ Convert/Save Results //----------------------------- double deg, ax1, ax2, ax3; Q1.getAngleAxis(deg, ax1, ax2, ax3); if (dphi * deg < 0) { deg = -deg; ax1 = -ax1; ax2 = -ax2; ax3 = -ax3; } double phi2 = static_cast<double>(getProperty("Run1Phi")) + dphi; double chi2 = acos(ax2) / M_PI * 180; double omega2 = atan2(ax3, -ax1) / M_PI * 180; g_log.notice() << "============================ Results ============================\n"; g_log.notice() << " phi,chi, and omega= (" << phi2 << "," << chi2 << "," << omega2 << ")\n"; g_log.notice() << " #indexed =" << Nindexed << '\n'; g_log.notice() << " ==============================================\n"; setProperty("Phi2", phi2); setProperty("Chi2", chi2); setProperty("Omega2", omega2); setProperty("NIndexed", Nindexed); setProperty("AvErrIndex", avErrIndx); setProperty("AvErrAll", avErrAll); Q1 = Quat(omega2, V3D(0, 1, 0)) * Quat(chi2, V3D(0, 0, 1)) * Quat(phi2, V3D(0, 1, 0)); Kernel::Matrix<double> Gon2a(Q1.getRotation()); for (int i = 0; i < PeaksRun2->getNumberPeaks(); i++) { PeaksRun2->getPeak(i).setGoniometerMatrix(Gon2a); } OrientedLattice latt2(PeaksRun2->mutableSample().getOrientedLattice()); // Kernel::Matrix<double> UB = latt2.getUB(); Rot.Invert(); Gon2a.Invert(); latt2.setUB(Gon2a * Mk * UB1); PeaksRun2->mutableSample().setOrientedLattice(&latt2); }
/** Fit background function */ void ProcessBackground::fitBackgroundFunction(std::string bkgdfunctiontype) { // Get background type and create bakground function BackgroundFunction_sptr bkgdfunction = createBackgroundFunction(bkgdfunctiontype); int bkgdorder = getProperty("OutputBackgroundOrder"); bkgdfunction->setAttributeValue("n", bkgdorder); if (bkgdfunctiontype == "Chebyshev") { double xmin = m_outputWS->readX(0).front(); double xmax = m_outputWS->readX(0).back(); g_log.information() << "Chebyshev Fit range: " << xmin << ", " << xmax << "\n"; bkgdfunction->setAttributeValue("StartX", xmin); bkgdfunction->setAttributeValue("EndX", xmax); } g_log.information() << "Fit selected background " << bkgdfunctiontype << " to data workspace with " << m_outputWS->getNumberHistograms() << " spectra." << "\n"; // Fit input (a few) background pionts to get initial guess API::IAlgorithm_sptr fit; try { fit = this->createChildAlgorithm("Fit", 0.9, 1.0, true); } catch (Exception::NotFoundError &) { g_log.error() << "Requires CurveFitting library." << std::endl; throw; } g_log.information() << "Fitting background function: " << bkgdfunction->asString() << "\n"; double startx = m_lowerBound; double endx = m_upperBound; fit->setProperty("Function", boost::dynamic_pointer_cast<API::IFunction>(bkgdfunction)); fit->setProperty("InputWorkspace", m_outputWS); fit->setProperty("WorkspaceIndex", 0); fit->setProperty("MaxIterations", 500); fit->setProperty("StartX", startx); fit->setProperty("EndX", endx); fit->setProperty("Minimizer", "Levenberg-MarquardtMD"); fit->setProperty("CostFunction", "Least squares"); fit->executeAsChildAlg(); // Get fit status and chi^2 std::string fitStatus = fit->getProperty("OutputStatus"); bool allowedfailure = (fitStatus.find("cannot") < fitStatus.size()) && (fitStatus.find("tolerance") < fitStatus.size()); if (fitStatus.compare("success") != 0 && !allowedfailure) { g_log.error() << "ProcessBackground: Fit Status = " << fitStatus << ". Not to update fit result" << std::endl; throw std::runtime_error("Bad Fit"); } const double chi2 = fit->getProperty("OutputChi2overDoF"); g_log.information() << "Fit background: Fit Status = " << fitStatus << ", chi2 = " << chi2 << "\n"; // Get out the parameter names API::IFunction_sptr funcout = fit->getProperty("Function"); TableWorkspace_sptr outbkgdparws = boost::make_shared<TableWorkspace>(); outbkgdparws->addColumn("str", "Name"); outbkgdparws->addColumn("double", "Value"); TableRow typerow = outbkgdparws->appendRow(); typerow << bkgdfunctiontype << 0.; vector<string> parnames = funcout->getParameterNames(); size_t nparam = funcout->nParams(); for (size_t i = 0; i < nparam; ++i) { TableRow newrow = outbkgdparws->appendRow(); newrow << parnames[i] << funcout->getParameter(i); } TableRow chi2row = outbkgdparws->appendRow(); chi2row << "Chi-square" << chi2; g_log.information() << "Set table workspace (#row = " << outbkgdparws->rowCount() << ") to OutputBackgroundParameterTable. " << "\n"; setProperty("OutputBackgroundParameterWorkspace", outbkgdparws); // Set output workspace const MantidVec &vecX = m_outputWS->readX(0); const MantidVec &vecY = m_outputWS->readY(0); FunctionDomain1DVector domain(vecX); FunctionValues values(domain); funcout->function(domain, values); MantidVec &dataModel = m_outputWS->dataY(1); MantidVec &dataDiff = m_outputWS->dataY(2); for (size_t i = 0; i < dataModel.size(); ++i) { dataModel[i] = values[i]; dataDiff[i] = vecY[i] - dataModel[i]; } return; }
void GetDetOffsetsMultiPeaks::fitSpectra(const int64_t s, MatrixWorkspace_sptr inputW, const std::vector<double> &peakPositions, const std::vector<double> &fitWindows, size_t &nparams, double &minD, double &maxD, std::vector<double>&peakPosToFit, std::vector<double>&peakPosFitted, std::vector<double> &chisq) { const MantidVec & X = inputW->readX(s); minD = X.front(); maxD = X.back(); bool useFitWindows = (!fitWindows.empty()); std::vector<double> fitWindowsToUse; for (int i = 0; i < static_cast<int>(peakPositions.size()); ++i) { if((peakPositions[i] > minD) && (peakPositions[i] < maxD)) { peakPosToFit.push_back(peakPositions[i]); if (useFitWindows) { fitWindowsToUse.push_back(std::max(fitWindows[2*i], minD)); fitWindowsToUse.push_back(std::min(fitWindows[2*i+1], maxD)); } } } API::IAlgorithm_sptr findpeaks = createChildAlgorithm("FindPeaks", -1, -1, false); findpeaks->setProperty("InputWorkspace", inputW); findpeaks->setProperty<int>("FWHM",7); findpeaks->setProperty<int>("Tolerance",4); // FindPeaks will do the checking on the validity of WorkspaceIndex findpeaks->setProperty("WorkspaceIndex",static_cast<int>(s)); //Get the specified peak positions, which is optional findpeaks->setProperty("PeakPositions", peakPosToFit); if (useFitWindows) findpeaks->setProperty("FitWindows", fitWindowsToUse); findpeaks->setProperty<std::string>("PeakFunction", m_peakType); findpeaks->setProperty<std::string>("BackgroundType", m_backType); findpeaks->setProperty<bool>("HighBackground", this->getProperty("HighBackground")); findpeaks->setProperty<int>("MinGuessedPeakWidth",4); findpeaks->setProperty<int>("MaxGuessedPeakWidth",4); findpeaks->executeAsChildAlg(); ITableWorkspace_sptr peakslist = findpeaks->getProperty("PeaksList"); std::vector<size_t> banned; std::vector<double> peakWidFitted; std::vector<double> peakHighFitted; std::vector<double> peakBackground; for (size_t i = 0; i < peakslist->rowCount(); ++i) { // peak value double centre = peakslist->getRef<double>("centre",i); double width = peakslist->getRef<double>("width",i); double height = peakslist->getRef<double>("height", i); // background value double back_intercept = peakslist->getRef<double>("backgroundintercept", i); double back_slope = peakslist->getRef<double>("backgroundslope", i); double back_quad = peakslist->getRef<double>("A2", i); double background = back_intercept + back_slope * centre + back_quad * centre * centre; // goodness of fit double chi2 = peakslist->getRef<double>("chi2",i); // Get references to the data peakPosFitted.push_back(centre); peakWidFitted.push_back(width); peakHighFitted.push_back(height); peakBackground.push_back(background); chisq.push_back(chi2); } // first remove things that just didn't fit (center outside of window, bad chisq, ...) for (size_t i = 0; i < peakslist->rowCount(); ++i) { if (peakPosFitted[i] <= minD || peakPosFitted[i] >= maxD) { banned.push_back(i); continue; } else if (useFitWindows) // be more restrictive if fit windows were specified { if (peakPosFitted[i] <= fitWindowsToUse[2*i] || peakPosFitted[i] >= fitWindowsToUse[2*i+1]) { banned.push_back(i); continue; } } if (chisq[i] > m_maxChiSq) { banned.push_back(i); continue; } } // delete banned peaks g_log.debug() << "Deleting " << banned.size() << " of " << peakPosFitted.size() << " peaks in wkspindex = " << s << "\n"; deletePeaks(banned, peakPosToFit, peakPosFitted, peakWidFitted, peakHighFitted, peakBackground, chisq); // ban peaks that are low intensity compared to their widths for (size_t i = 0; i < peakWidFitted.size(); ++i) { if (peakHighFitted[i] * FWHM_TO_SIGMA / peakWidFitted[i] < 5.) { g_log.debug() << "Banning peak at " << peakPosFitted[i] << " in wkspindex = " << s << " I/sigma = " << (peakHighFitted[i] * FWHM_TO_SIGMA / peakWidFitted[i]) << "\n"; banned.push_back(i); continue; } } // delete banned peaks g_log.debug() << "Deleting " << banned.size() << " of " << peakPosFitted.size() << " peaks in wkspindex = " << s << "\n"; deletePeaks(banned, peakPosToFit, peakPosFitted, peakWidFitted, peakHighFitted, peakBackground, chisq); // determine the (z-value) for constant "width" - (delta d)/d std::vector<double> widthDivPos(peakWidFitted.size(), 0.); // DELETEME for (size_t i = 0; i < peakWidFitted.size(); ++i) { widthDivPos[i] = peakWidFitted[i] / peakPosFitted[i]; // DELETEME } std::vector<double> Zscore = getZscore(widthDivPos); for (size_t i = 0; i < peakWidFitted.size(); ++i) { if (Zscore[i] > 2.0) { g_log.debug() << "Banning peak at " << peakPosFitted[i] << " in wkspindex = " << s << " sigma/d = " << widthDivPos[i] << "\n"; banned.push_back(i); continue; } } // delete banned peaks g_log.debug() << "Deleting " << banned.size() << " of " << peakPosFitted.size() << " peaks in wkspindex = " << s << "\n"; deletePeaks(banned, peakPosToFit, peakPosFitted, peakWidFitted, peakHighFitted, peakBackground, chisq); // ban peaks that are not outside of error bars for the background for (size_t i = 0; i < peakWidFitted.size(); ++i) { if (peakHighFitted[i] < 0.5 * std::sqrt(peakHighFitted[i] + peakBackground[i])) { g_log.debug() << "Banning peak at " << peakPosFitted[i] << " in wkspindex = " << s << " " << peakHighFitted[i] << " < " << 0.5 * std::sqrt(peakHighFitted[i] + peakBackground[i]) << "\n"; banned.push_back(i); continue; } } // delete banned peaks g_log.debug() << "Deleting " << banned.size() << " of " << peakPosFitted.size() << " peaks in wkspindex = " << s << "\n"; deletePeaks(banned, peakPosToFit, peakPosFitted, peakWidFitted, peakHighFitted, peakBackground, chisq); nparams = peakPosFitted.size(); return; }