Mantid
Loading...
Searching...
No Matches
ResetNegatives.cpp
Go to the documentation of this file.
1// Mantid Repository : https://github.com/mantidproject/mantid
2//
3// Copyright © 2018 ISIS Rutherford Appleton Laboratory UKRI,
4// NScD Oak Ridge National Laboratory, European Spallation Source,
5// Institut Laue - Langevin & CSNS, Institute of High Energy Physics, CAS
6// SPDX - License - Identifier: GPL - 3.0 +
11
12using namespace Mantid::Kernel;
13using namespace Mantid::API;
14using std::size_t;
15
16namespace Mantid::Algorithms {
17
18// Register the algorithm into the AlgorithmFactory
19DECLARE_ALGORITHM(ResetNegatives)
20
21//----------------------------------------------------------------------------------------------
23const std::string ResetNegatives::name() const { return "ResetNegatives"; }
24
26int ResetNegatives::version() const { return 1; }
27
29const std::string ResetNegatives::category() const { return "CorrectionFunctions\\SpecialCorrections"; }
30
31//----------------------------------------------------------------------------------------------
34 declareProperty(std::make_unique<WorkspaceProperty<>>("InputWorkspace", "", Direction::Input), "An input workspace.");
35 declareProperty(std::make_unique<WorkspaceProperty<>>("OutputWorkspace", "", Direction::Output),
36 "An output workspace.");
37 declareProperty("AddMinimum", true, "Add the minimum value of the spectrum to bring it up to zero.");
38 declareProperty("ResetValue", 0., "Reset negative values to this number (default=0)");
39 setPropertySettings("ResetValue", std::make_unique<EnabledWhenProperty>("AddMinimum", IS_NOT_DEFAULT));
40}
41
42//----------------------------------------------------------------------------------------------
45 MatrixWorkspace_sptr inputWS = this->getProperty("InputWorkspace");
46 MatrixWorkspace_sptr outputWS = this->getProperty("OutputWorkspace");
47
48 // get the minimum for each spectrum
49 auto alg = createChildAlgorithm("Min", 0., .1);
50 alg->setProperty<MatrixWorkspace_sptr>("InputWorkspace", inputWS);
51 alg->executeAsChildAlg();
52 MatrixWorkspace_const_sptr minWS = alg->getProperty("OutputWorkspace");
53
54 // determine if there is anything to do
55 auto nHist = static_cast<int64_t>(minWS->getNumberHistograms());
56 bool hasNegative = false;
57 for (int64_t i = 0; i < nHist; i++) {
58 if (minWS->y(i)[0] < 0.0) {
59 hasNegative = true;
60 break;
61 }
62 }
63
64 // get out early if there is nothing to do
65 if (!hasNegative) {
66 g_log.information() << "No values are negative. Copying InputWorkspace to "
67 "OutputWorkspace\n";
68 if (inputWS != outputWS) {
69 auto clone = createChildAlgorithm("CloneWorkspace", .1, 1.);
70 clone->setProperty<Workspace_sptr>("InputWorkspace", inputWS);
71 clone->executeAsChildAlg();
72
73 Workspace_sptr temp = clone->getProperty("OutputWorkspace");
74 setProperty("OutputWorkspace", std::dynamic_pointer_cast<MatrixWorkspace>(temp));
75 }
76 return;
77 }
78
79 // sort the event list to make it fast and thread safe
81 std::dynamic_pointer_cast<const DataObjects::EventWorkspace>(inputWS);
82 if (eventWS)
83 eventWS->sortAll(DataObjects::TOF_SORT, nullptr);
84
85 Progress prog(this, 0.1, 1.0, 2 * nHist);
86
87 // generate output workspace - copy X and dY
88 outputWS = API::WorkspaceFactory::Instance().create(inputWS);
89 PARALLEL_FOR_IF(Kernel::threadSafe(*inputWS, *outputWS))
90 for (int64_t i = 0; i < nHist; i++) {
92 const auto index = static_cast<size_t>(i);
93 outputWS->setHistogram(index, inputWS->histogram(index));
94 prog.report();
96 }
98
99 // do the actual work
100 if (this->getProperty("AddMinimum")) {
101 this->pushMinimum(minWS, outputWS, prog);
102 } else {
103 this->changeNegatives(minWS, this->getProperty("ResetValue"), outputWS, prog);
104 }
105
106 setProperty("OutputWorkspace", outputWS);
107}
108
109namespace { // anonymous namespace
113inline double fixZero(const double value) { return value != -0. ? value : 0.; }
114} // namespace
115
126 Progress &prog) {
127 int64_t nHist = minWS->getNumberHistograms();
128 PARALLEL_FOR_IF(Kernel::threadSafe(*wksp, *minWS))
129 for (int64_t i = 0; i < nHist; i++) {
131 double minValue = minWS->y(i)[0];
132 if (minValue <= 0) {
133 minValue *= -1.;
134 auto &y = wksp->mutableY(i);
135 std::transform(y.begin(), y.end(), y.begin(), [minValue](double value) { return fixZero(value + minValue); });
136 }
137 prog.report();
139 }
141}
142
153void ResetNegatives::changeNegatives(const MatrixWorkspace_const_sptr &minWS, const double spectrumNegativeValues,
154 const MatrixWorkspace_sptr &wksp, Progress &prog) {
155 int64_t nHist = wksp->getNumberHistograms();
156 PARALLEL_FOR_IF(Kernel::threadSafe(*minWS, *wksp))
157 for (int64_t i = 0; i < nHist; i++) {
159 if (minWS->y(i)[0] <= 0.) // quick check to see if there is a reason to bother
160 {
161 auto &y = wksp->mutableY(i);
162 for (double &value : y) {
163 if (value < 0.) {
164 value = spectrumNegativeValues;
165 } else
166 value = fixZero(value);
167 }
168 }
169 prog.report();
171 }
173}
174
175} // namespace Mantid::Algorithms
std::string name
Definition Run.cpp:60
#define DECLARE_ALGORITHM(classname)
Definition Algorithm.h:538
double value
The value of the point.
Definition FitMW.cpp:51
std::map< DeltaEMode::Type, std::string > index
#define PARALLEL_START_INTERRUPT_REGION
Begins a block to skip processing is the algorithm has been interupted Note the end of the block if n...
#define PARALLEL_END_INTERRUPT_REGION
Ends a block to skip processing is the algorithm has been interupted Note the start of the block if n...
#define PARALLEL_FOR_IF(condition)
Empty definitions - to enable set your complier to enable openMP.
#define PARALLEL_CHECK_INTERRUPT_REGION
Adds a check after a Parallel region to see if it was interupted.
void declareProperty(std::unique_ptr< Kernel::Property > p, const std::string &doc="") override
Add a property to the list of managed properties.
TypedValue getProperty(const std::string &name) const override
Get the value of a property.
virtual std::shared_ptr< Algorithm > createChildAlgorithm(const std::string &name, const double startProgress=-1., const double endProgress=-1., const bool enableLogging=true, const int &version=-1)
Create a Child Algorithm.
Kernel::Logger & g_log
Definition Algorithm.h:422
Helper class for reporting progress from algorithms.
Definition Progress.h:25
A property class for workspaces.
ResetNegatives : Reset negative values to something else.
void changeNegatives(const API::MatrixWorkspace_const_sptr &minWS, const double spectrumNegativeValues, const API::MatrixWorkspace_sptr &wksp, API::Progress &prog)
Search each spectrum for y-values that are less than zero and reset them to the supplied value.
int version() const override
function to return a version of the algorithm, must be overridden in all algorithms
void pushMinimum(const API::MatrixWorkspace_const_sptr &minWS, const API::MatrixWorkspace_sptr &wksp, API::Progress &prog)
Add -1.
void init() override
Virtual method - must be overridden by concrete algorithm.
const std::string category() const override
function to return a category of the algorithm.
void exec() override
Virtual method - must be overridden by concrete algorithm.
IPropertyManager * setProperty(const std::string &name, const T &value)
Templated method to set the value of a PropertyWithValue.
void setPropertySettings(const std::string &name, std::unique_ptr< IPropertySettings > settings)
void information(const std::string &msg)
Logs at information level.
Definition Logger.cpp:136
void report()
Increments the loop counter by 1, then sends the progress notification on behalf of its algorithm.
static T & Instance()
Return a reference to the Singleton instance, creating it if it does not already exist Creation is do...
std::shared_ptr< Workspace > Workspace_sptr
shared pointer to Mantid::API::Workspace
std::shared_ptr< const MatrixWorkspace > MatrixWorkspace_const_sptr
shared pointer to the matrix workspace base class (const version)
std::shared_ptr< MatrixWorkspace > MatrixWorkspace_sptr
shared pointer to the matrix workspace base class
std::shared_ptr< const EventWorkspace > EventWorkspace_const_sptr
shared pointer to a const Workspace2D
std::enable_if< std::is_pointer< Arg >::value, bool >::type threadSafe(Arg workspace)
Thread-safety check Checks the workspace to ensure it is suitable for multithreaded access.
STL namespace.
@ Input
An input workspace.
Definition Property.h:53
@ Output
An output workspace.
Definition Property.h:54