Mantid
Loading...
Searching...
No Matches
CombineDiffCal.cpp
Go to the documentation of this file.
1// Mantid Repository : https://github.com/mantidproject/mantid
2//
3// Copyright © 2021 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 +
7
10#include "MantidAPI/TableRow.h"
14
15namespace Mantid::Algorithms {
18
19// Register the algorithm into the AlgorithmFactory
20DECLARE_ALGORITHM(CombineDiffCal)
21
22//----------------------------------------------------------------------------------------------
23
24
25const std::string CombineDiffCal::name() const { return "CombineDiffCal"; }
26
28int CombineDiffCal::version() const { return 1; }
29
31const std::string CombineDiffCal::category() const { return "Diffraction\\Utility"; }
32
34const std::string CombineDiffCal::summary() const {
35 return "Combine a per-pixel calibration with a grouped spectrum calibration";
36}
37
38//----------------------------------------------------------------------------------------------
43 std::make_unique<WorkspaceProperty<DataObjects::TableWorkspace>>("PixelCalibration", "", Direction::Input),
44 "OffsetsWorkspace generated from cross-correlation. This is the source of DIFCpixel.");
46 std::make_unique<WorkspaceProperty<DataObjects::TableWorkspace>>("GroupedCalibration", "", Direction::Input),
47 "DiffCal table generated from calibrating grouped spectra. This is the source of DIFCgroup.");
49 std::make_unique<WorkspaceProperty<API::MatrixWorkspace>>("CalibrationWorkspace", "", Direction::Input),
50 "Workspace where conversion from d-spacing to time-of-flight for each spectrum is determined from. This is the "
51 "source of DIFCarb.");
53 std::make_unique<WorkspaceProperty<DataObjects::TableWorkspace>>("OutputWorkspace", "", Direction::Output),
54 "DiffCal table generated from calibrating grouped spectra");
57 "MaskedWorkspace for PixelCalibration");
58}
59
62 auto alg = createChildAlgorithm("SortTableWorkspace");
63 alg->setLoggingOffset(1);
64 alg->setProperty("InputWorkspace", table);
65 alg->setProperty("OutputWorkspace", table);
66 alg->setProperty("Columns", "detid");
67 alg->executeAsChildAlg();
68
69 return alg->getProperty("OutputWorkspace");
70}
71
72bool findColumn(const std::vector<std::string> &columnNames, const std::string &name) {
73 return std::find(columnNames.begin(), columnNames.end(), name) != columnNames.end();
74}
75
77 const std::vector<std::string> columnNames = ws->getColumnNames();
78
79 std::stringstream error;
80 if (!findColumn(columnNames, "detid"))
81 error << "detid ";
82 if (!findColumn(columnNames, "difc"))
83 error << "difc ";
84 if (!findColumn(columnNames, "difa"))
85 error << "difa ";
86 if (!findColumn(columnNames, "tzero"))
87 error << "tzero ";
88
89 return error.str();
90}
91
92std::map<std::string, std::string> CombineDiffCal::validateInputs() {
93 std::map<std::string, std::string> results;
94
95 const DataObjects::TableWorkspace_sptr groupedCalibrationWS = getProperty("GroupedCalibration");
96 const DataObjects::TableWorkspace_sptr pixelCalibrationWS = getProperty("PixelCalibration");
97
98 const auto groupedResult = generateErrorString(groupedCalibrationWS);
99 if (!groupedResult.empty())
100 results["GroupedCalibration"] = "The GroupedCalibration Workspace is missing [ " + groupedResult + "]";
101
102 const auto pixelResult = generateErrorString(pixelCalibrationWS);
103 if (!pixelResult.empty())
104 results["PixelCalibration"] = "The PixelCalibration Workspace is missing [ " + pixelResult + "]";
105
106 return results;
107}
108
109std::shared_ptr<Mantid::API::TableRow> binarySearchForRow(const API::ITableWorkspace_sptr &ws, int detid) {
110 size_t start = 0;
111 size_t end = ws->rowCount() - 1;
112 while (end >= start) {
113 size_t currentPosition = start + ((end - start) / 2);
114
115 Mantid::API::TableRow currentRow = ws->getRow(currentPosition);
116 if (currentRow.Int(0) > detid) {
117 end = currentPosition - 1;
118 } else if (currentRow.Int(0) < detid) {
119 start = currentPosition + 1;
120 } else {
121 return std::make_shared<Mantid::API::TableRow>(currentRow);
122 }
123 }
124 return nullptr;
125}
126
128 Mantid::API::TableRow newRow = ws->appendRow();
129 newRow << row.Int(0) << row.Double(1) << row.Double(2) << row.Double(3);
130}
131
132// Per Pixel:
133//
134// DIFC{eff} = (DIFC{pd}/DIFC{arb}) * DIFC{prev}
135//
136// DIFC{eff} = Output of this Alg, the combined DIFC
137// DIFC{pd} = The DIFC produced by PDCalibration, found in the "GroupedCalibration"
138// DIFC{arb} = found in the "CalibrationWorkspace" param
139// DIFC{prev} = The previous DIFCs, found in "PixelCalibration", as per description this was the set generated by CC
140
141//----------------------------------------------------------------------------------------------
145 const API::MatrixWorkspace_sptr calibrationWS = getProperty("CalibrationWorkspace");
146
147 DataObjects::TableWorkspace_sptr presortedGroupedCalibrationWS = getProperty("GroupedCalibration");
148 const API::ITableWorkspace_sptr groupedCalibrationWS = sortTableWorkspace(presortedGroupedCalibrationWS);
149
150 DataObjects::TableWorkspace_sptr presortedPixelCalibrationWS = getProperty("PixelCalibration");
151 const API::ITableWorkspace_sptr pixelCalibrationWS = sortTableWorkspace(presortedPixelCalibrationWS);
152
153 const DataObjects::MaskWorkspace_sptr maskWorkspace = getProperty("MaskWorkspace");
154
155 DataObjects::TableWorkspace_sptr outputWorkspace = std::make_shared<DataObjects::TableWorkspace>();
156 outputWorkspace->addColumn("int", "detid");
157 outputWorkspace->addColumn("double", "difc");
158 outputWorkspace->addColumn("double", "difa");
159 outputWorkspace->addColumn("double", "tzero");
160
161 Mantid::API::TableRow groupedCalibrationRow = groupedCalibrationWS->getFirstRow();
162 do {
163 int detid = groupedCalibrationRow.Int(0);
164 bool prevDifValsExist = false;
165
166 if (!(maskWorkspace && maskWorkspace->isMasked(detid))) {
167 std::shared_ptr<Mantid::API::TableRow> pixelCalibrationRow = binarySearchForRow(pixelCalibrationWS, detid);
168 if (pixelCalibrationRow) {
169 double difcPD = groupedCalibrationRow.Double(1);
170 double difcArb = calibrationWS->spectrumInfo().diffractometerConstants(
171 calibrationWS->getIndicesFromDetectorIDs({detid})[0])[Kernel::UnitParams::difc];
172 double difcPrev = pixelCalibrationRow->Double(1);
173 double difaPrev = pixelCalibrationRow->Double(2);
174
175 double difcNew = (difcPD / difcArb) * difcPrev;
176 double difaNew = ((difcPD / difcArb) * (difcPD / difcArb)) * difaPrev;
177
178 double tzeroNew = pixelCalibrationRow->Double(3);
179
180 Mantid::API::TableRow newRow = outputWorkspace->appendRow();
181 newRow << detid << difcNew << difaNew << tzeroNew;
182 prevDifValsExist = true;
183 }
184 }
185
186 if (!prevDifValsExist) {
187 // copy from group
188 addRowFromGroupedCalibration(outputWorkspace, groupedCalibrationRow);
189 }
190 } while (groupedCalibrationRow.next());
191
192 setProperty("OutputWorkspace", outputWorkspace);
193}
194
195} // namespace Mantid::Algorithms
#define DECLARE_ALGORITHM(classname)
Definition: Algorithm.h:576
double error
Definition: IndexPeaks.cpp:133
void declareProperty(std::unique_ptr< Kernel::Property > p, const std::string &doc="") override
Add a property to the list of managed properties.
Definition: Algorithm.cpp:1913
TypedValue getProperty(const std::string &name) const override
Get the value of a property.
Definition: Algorithm.cpp:2076
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.
Definition: Algorithm.cpp:842
TableRow represents a row in a TableWorkspace.
Definition: TableRow.h:39
bool next()
Steps to the next row in the TableWorkspace if there is one.
Definition: TableRow.cpp:40
double & Double(size_t col)
Returns a reference to the element in position col if its type is double.
Definition: TableRow.h:137
int & Int(size_t col)
Returns a reference to the element in position col if its type is int.
Definition: TableRow.h:131
A property class for workspaces.
CombineDiffCal : Calibrate groups of pixels after cross correlation so that diffraction peaks can be ...
API::ITableWorkspace_sptr sortTableWorkspace(DataObjects::TableWorkspace_sptr &table)
sort the calibration table according increasing values in column "detid"
void exec() override
Execute the algorithm.
const std::string category() const override
Algorithm's category for identification.
int version() const override
Algorithm's version for identification.
std::map< std::string, std::string > validateInputs() override
Method checking errors on ALL the inputs, before execution.
const std::string summary() const override
Algorithm's summary for use in the GUI and help.
void init() override
Initialize the algorithm's properties.
IPropertyManager * setProperty(const std::string &name, const T &value)
Templated method to set the value of a PropertyWithValue.
std::shared_ptr< ITableWorkspace > ITableWorkspace_sptr
shared pointer to Mantid::API::ITableWorkspace
std::shared_ptr< MatrixWorkspace > MatrixWorkspace_sptr
shared pointer to the matrix workspace base class
bool findColumn(const std::vector< std::string > &columnNames, const std::string &name)
std::string generateErrorString(const DataObjects::TableWorkspace_sptr &ws)
void addRowFromGroupedCalibration(const DataObjects::TableWorkspace_sptr &ws, Mantid::API::TableRow row)
std::shared_ptr< Mantid::API::TableRow > binarySearchForRow(const API::ITableWorkspace_sptr &ws, int detid)
std::shared_ptr< TableWorkspace > TableWorkspace_sptr
shared pointer to Mantid::DataObjects::TableWorkspace
std::shared_ptr< MaskWorkspace > MaskWorkspace_sptr
shared pointer to the MaskWorkspace class
Definition: MaskWorkspace.h:64
STL namespace.
Describes the direction (within an algorithm) of a Property.
Definition: Property.h:50
@ Input
An input workspace.
Definition: Property.h:53
@ Output
An output workspace.
Definition: Property.h:54