Mantid
Loading...
Searching...
No Matches
LoadNXcanSAS.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 +
8
11#include "MantidAPI/Axis.h"
16#include "MantidAPI/Run.h"
17#include "MantidAPI/Workspace.h"
21#include "MantidKernel/Logger.h"
22#include "MantidNexus/H5Util.h"
23#include "MantidNexus/NexusFile.h"
24#include <H5Cpp.h>
25#include <cstring>
26
27using namespace Mantid::Kernel;
28using namespace Mantid::API;
29using namespace Mantid::DataHandling::NXcanSAS;
30using namespace Mantid::Nexus;
31
32namespace {
33Mantid::Kernel::Logger g_log("LoadNXcanSAS");
34const std::string NX_SPIN_LOG = "spin_state_NXcanSAS";
35const std::map<std::string, int> SAMPLE_GEOMETRIES = {
36 {"cylinder", 1}, {"flat plate", 2}, {"flatplate", 2}, {"disc", 3}};
37
38std::string getNameOfEntry(const H5::H5File &root) {
39 auto numberOfObjects = root.getNumObjs();
40 if (numberOfObjects != 1) {
41 throw std::invalid_argument("LoadNXcanSAS: Trying to load multiperiod "
42 "data. This is currently not supported.");
43 }
44 auto objectType = root.getObjTypeByIdx(0);
45 if (objectType != H5G_GROUP) {
46 throw std::invalid_argument("LoadNXcanSAS: The object below the root is not a H5::Group.");
47 }
48
49 return root.getObjnameByIdx(0);
50}
51
52Mantid::API::MatrixWorkspace_sptr createWorkspace(const DataSpaceInformation &dimInfo, const bool asHistogram = false) {
53 const auto &[dimSpectrumAxis, dimBin, _] = dimInfo;
54 // Create a workspace based on the dataSpace information
56 "Workspace2D", dimSpectrumAxis /*NHisto*/, asHistogram ? dimBin + 1 : dimBin /*xdata*/, dimBin /*ydata*/);
57}
58
59std::vector<double> getNumDataSetIfExists(const H5::Group &group, const std::string &datasetName) {
60 if (group.nameExists(datasetName)) {
61 return H5Util::readArray1DCoerce<double>(group, datasetName);
62 }
63 return {};
64}
65
66std::string getStrDataSetIfExists(const H5::Group &group, const std::string &datasetName) {
67 if (group.nameExists(datasetName)) {
68 return H5Util::readString(group, datasetName);
69 }
70 return {};
71}
72
73//----- Logs ----- //
74
75template <typename T>
76void addLogToWs(const MatrixWorkspace_sptr &workspace, const std::string &logName, const T &logValue,
77 const std::string &logUnits = "") {
78 auto &run = workspace->mutableRun();
79 auto property = std::make_unique<PropertyWithValue<T>>(logName, logValue);
80 if (!logUnits.empty()) {
81 property->setUnits(logUnits);
82 }
83 run.addProperty(std::move(property));
84}
85
86void loadLogs(const H5::Group &entry, const MatrixWorkspace_sptr &workspace) {
87 const auto addLogFromGroup = [workspace](const H5::Group &group, const std::string &sasTerm,
88 const std::string &propertyName) {
89 const auto propValue = getStrDataSetIfExists(group, sasTerm);
90 if (!propValue.empty()) {
91 addLogToWs(workspace, propertyName, propValue);
92 }
93 };
94 // Load UserFile, BatchFile and Run if present on file
95 const auto process = entry.openGroup(sasProcessGroupName);
96 addLogFromGroup(process, sasProcessTermUserFile, sasProcessUserFileInLogs);
97 addLogFromGroup(process, sasProcessTermBatchFile, sasProcessBatchFileInLogs);
98 addLogFromGroup(entry, sasEntryRun, sasEntryRunInLogs);
99}
100
101void loadTitle(const H5::Group &entry, const Workspace_sptr &workspace) {
102 if (entry.nameExists(sasEntryTitle)) {
103 workspace->setTitle(H5Util::readString(entry, sasEntryTitle));
104 }
105}
106
107//----- Polarization ----- //
108
113bool checkPolarization(const H5::Group &group) {
114 const auto pIn = group.nameExists(sasDataPin);
115 const auto pOut = group.nameExists(sasDataPout);
116 if (pIn != pOut) {
117 throw std::invalid_argument("Polarized data requires to have Pin and Pout axes");
118 }
119 return pIn;
120}
121
127std::pair<std::vector<int>, std::vector<int>> loadSpinVectors(const H5::Group &group) {
128 // Check for polarization first
129 std::vector<int> pIn;
130 std::vector<int> pOut;
131 if (checkPolarization(group)) {
132 pIn = H5Util::readArray1DCoerce<int>(group, sasDataPin);
133 pOut = H5Util::readArray1DCoerce<int>(group, sasDataPout);
134 }
135 return std::make_pair(pIn, pOut);
136}
137
148std::vector<SpinState> prepareSpinIndexes(const std::vector<int> &pIn, const std::vector<int> &pOut) {
149 // Holds spin pair with vector indexes to iterate hyperslab
150 auto spinToString = [](const int spinIndex) {
151 return spinIndex == 1 ? '+' + std::to_string(spinIndex) : std::to_string(spinIndex);
152 };
153
154 std::vector<SpinState> spinIndexes;
155 for (size_t i = 0; i < pIn.size(); i++) {
156 for (size_t j = 0; j < pOut.size(); j++) {
157 SpinState state;
158 state.strSpinState = spinToString(pIn.at(i)) + spinToString(pOut.at(j));
159 state.spinIndexPair = std::make_pair(i, j);
160 spinIndexes.push_back(std::move(state));
161 }
162 }
163 return spinIndexes;
164}
165
171void loadPolarizedLogs(const H5::Group &group, const MatrixWorkspace_sptr &workspace) {
172 const auto logNames = std::vector({sasSampleEMFieldDirectionAzimuthal, sasSampleEMFieldDirectionPolar,
174 for (const auto &log : logNames) {
175 auto logValue = getNumDataSetIfExists(group, log);
176 if (!logValue.empty()) {
177 std::string logUnits;
178 H5Util::readStringAttribute(group.openDataSet(log), sasUnitAttr, logUnits);
179 addLogToWs(workspace, log, logValue.front(), logUnits);
180 }
181 }
182}
183
184//----- Sample ----- //
185std::optional<H5::Group> getGroupIfExists(const H5::Group &group, const std::string &groupName) {
186 if (group.nameExists(groupName)) {
187 return group.openGroup(groupName);
188 }
189 return std::nullopt;
190}
191
197std::optional<Sample> loadSample(const H5::Group &group) {
198 // Load Height, Width, and Geometry from the aperture group and save to Sample object.
199 const auto &instrumentGroup = getGroupIfExists(group, sasInstrumentGroupName);
200 auto apertureGroup = std::optional<H5::Group>();
201 if (instrumentGroup.has_value()) {
202 apertureGroup = getGroupIfExists(instrumentGroup.value(), sasInstrumentApertureGroupName);
203 }
204 const auto &sampleGroup = getGroupIfExists(group, sasInstrumentSampleGroupAttr);
205
206 if (!apertureGroup.has_value() && !sampleGroup.has_value()) {
207 return std::nullopt;
208 }
209 auto sample = Sample();
210 if (apertureGroup.has_value()) {
211 const auto &height = getNumDataSetIfExists(apertureGroup.value(), sasInstrumentApertureGapHeight);
212 if (!height.empty()) {
213 sample.setHeight(height.front());
214 }
215 const auto &width = getNumDataSetIfExists(apertureGroup.value(), sasInstrumentApertureGapWidth);
216 if (!width.empty()) {
217 sample.setWidth(width.front());
218 }
219 auto geometry = getStrDataSetIfExists(apertureGroup.value(), sasInstrumentApertureShape);
220 boost::to_lower(geometry);
221 if (!geometry.empty()) {
222 SAMPLE_GEOMETRIES.contains(geometry) ? sample.setGeometryFlag(SAMPLE_GEOMETRIES.at(geometry))
223 : sample.setGeometryFlag(0);
224 }
225 }
226
227 // Load thickness from the sample group and save to the Sample object.
228 if (sampleGroup.has_value()) {
229 const auto &thickness = getNumDataSetIfExists(sampleGroup.value(), sasInstrumentSampleThickness);
230 if (!thickness.empty()) {
231 sample.setThickness(thickness.front());
232 }
233 }
234 return sample;
235}
236
242void loadInstrument(const Mantid::API::MatrixWorkspace_sptr &workspace, const InstrumentNameInfo &instrumentInfo) {
243 // Try to load the instrument. If it fails we will continue nevertheless.
244 try {
245 const auto instAlg = Mantid::API::AlgorithmManager::Instance().createUnmanaged("LoadInstrument");
246 instAlg->initialize();
247 instAlg->setChild(true);
248 instAlg->setProperty("Workspace", workspace);
249 instAlg->setProperty("InstrumentName", instrumentInfo.instrumentName);
250 if (!instrumentInfo.idf.empty()) {
251 instAlg->setProperty("Filename", instrumentInfo.idf);
252 }
253 instAlg->setProperty("RewriteSpectraMap", "False");
254 instAlg->execute();
255 } catch (std::invalid_argument &) {
256 g_log.information("Invalid argument to LoadInstrument Child Algorithm.");
257 } catch (std::runtime_error &) {
258 g_log.information("Unable to successfully run LoadInstrument Child Algorithm.");
259 }
260}
261
262//----- Data ----- //
263
283std::vector<hsize_t> updateOffset(const int axesIndex, const std::pair<size_t, size_t> &spinIndexPair,
284 std::vector<hsize_t> &slabShape) {
285 const bool isXAxis = axesIndex == WorkspaceDataAxes::X || axesIndex == WorkspaceDataAxes::XErr;
286 const auto &[indexPin, indexPout] = spinIndexPair;
287 auto position = std::vector<hsize_t>(slabShape.size(), 0);
288 if (slabShape.size() > 2) {
289 if (isXAxis) {
290 // cut slabShape for Q data
291 slabShape = std::vector<hsize_t>(slabShape.cbegin() + 2, slabShape.cend());
292 position = std::vector<hsize_t>(position.cbegin() + 2, position.cend());
293 } else {
294 position.at(0) = indexPin;
295 position.at(1) = indexPout;
296 }
297 }
298 return position;
299}
300
301std::string getStrAttribute(const H5::DataSet &dataSet, const std::string &attrName) {
302 std::string attrValue;
303 H5Util::readStringAttribute(dataSet, attrName, attrValue);
304 return attrValue;
305}
306
311struct WorkspaceDataInserter {
312 explicit WorkspaceDataInserter(MatrixWorkspace_sptr workspace) : workspace(std::move(workspace)), axisType(0) {}
313
314 void insertData(const size_t index, const std::vector<double> &data) const {
315 switch (axisType) {
316 case Y:
317 workspace->mutableY(index) = data;
318 break;
319 case YErr:
320 workspace->mutableE(index) = data;
321 break;
322 case X:
323 workspace->mutableX(index) = data;
324 break;
325 case XErr:
326 workspace->setPointStandardDeviations(index, data);
327 break;
328 default:
329 throw std::runtime_error("Provided axis is not compatible with workspace.");
330 }
331 }
332
333 void setUnits(const H5::DataSet &dataSet) const {
334 if (axisType == Y) {
335 workspace->setYUnit(getStrAttribute(dataSet, sasUnitAttr));
336 } else if (axisType == X) {
337 workspace->getAxis(0)->setUnit("MomentumTransfer");
338 }
339 }
340
341 void setAxisType(const int type) { axisType = type; }
343 int axisType;
344};
345
355void readDataIntoWorkspace(const H5::DataSet &dataSet, const WorkspaceDataInserter &inserter,
356 const std::vector<hsize_t> &slabShape, const hsize_t nPoints, const hsize_t nHistograms,
357 std::vector<hsize_t> &offset) {
358
359 // Memory Data Space
360 const std::array<hsize_t, 1> memSpaceDimension = {nPoints};
361 const H5::DataSpace memSpace(1, memSpaceDimension.data());
362 const bool isPolarizedDataSet = slabShape.size() > 2;
363 const auto histogramIndex = isPolarizedDataSet ? slabShape.size() - 2 : 0;
364
365 const auto fileSpace = dataSet.getSpace();
366 auto data = std::vector<double>(nPoints, 0);
367 for (size_t index = 0; index < nHistograms; ++index) {
368 // Set the dataSpace to a 1D HyperSlab
369 fileSpace.selectHyperslab(H5S_SELECT_SET, slabShape.data(), offset.data());
370 dataSet.read(data.data(), H5Util::getType<double>(), memSpace, fileSpace);
371 inserter.insertData(index, data);
372 offset.at(histogramIndex)++;
373 }
374}
375
383void readQyInto2DWorkspace(const H5::DataSet &dataSet, const Mantid::API::MatrixWorkspace_sptr &workspace,
384 const hsize_t nHistograms) {
385 // Size of single slab
386 const std::array<hsize_t, 2> slabShape = {nHistograms, 1};
387 const std::array<hsize_t, 2> position = {0, 0};
388
389 // Memory Data Space
390 const std::array<hsize_t, 1> memSpaceDimensions = {nHistograms};
391 const H5::DataSpace memSpace(1, memSpaceDimensions.data());
392
393 // Select the HyperSlab
394 const auto fileSpace = dataSet.getSpace();
395 fileSpace.selectHyperslab(H5S_SELECT_SET, slabShape.data(), position.data());
396
397 // Read the data
398 auto data = std::vector<double>(nHistograms);
399 dataSet.read(data.data(), H5Util::getType<double>(), memSpace, fileSpace);
400
401 auto newAxis = std::make_unique<Mantid::API::NumericAxis>(data);
402 workspace->replaceAxis(1, std::move(newAxis));
403
404 // Set the axis units
405 workspace->getAxis(1)->setUnit("MomentumTransfer");
406}
407
408//----- Transmission ----- //
409bool fileHasTransmissionEntry(const H5::Group &entry, const std::string &name) {
410 const bool hasTransmission = entry.nameExists(sasTransmissionSpectrumGroupName + "_" + name);
411 if (!hasTransmission) {
412 g_log.information("NXcanSAS file does not contain transmission for " + name);
413 }
414 return hasTransmission;
415}
416
422void loadTransmissionData(const H5::Group &transmission, const Mantid::API::MatrixWorkspace_sptr &workspace) {
423 //-----------------------------------------
424 // Load T
425 workspace->mutableY(0) = H5Util::readArray1DCoerce<double>(transmission, sasTransmissionSpectrumT);
426 //-----------------------------------------
427 // Load Tdev
428 workspace->mutableE(0) = H5Util::readArray1DCoerce<double>(transmission, sasTransmissionSpectrumTdev);
429 //-----------------------------------------
430 // Load Lambda. A bug in older versions (fixed in 6.0) allowed the
431 // transmission lambda points to be saved as bin edges rather than points as
432 // required by the NXcanSAS standard. We allow loading those files and convert
433 // to points on the fly
434 std::vector<double> lambda;
436 if (lambda.size() == workspace->blocksize())
437 workspace->setPoints(0, std::move(lambda));
438 else if (lambda.size() == workspace->blocksize() + 1)
439 workspace->setBinEdges(0, std::move(lambda));
440 else {
441 const std::string objectName{transmission.getObjName()};
442 throw std::runtime_error("Unexpected array size for lambda in transmission group '" + objectName +
443 "'. Expected length=" + std::to_string(workspace->blocksize()) +
444 ", found length=" + std::to_string(lambda.size()));
445 }
446 workspace->getAxis(0)->setUnit("Wavelength");
447 workspace->setYUnitLabel("Transmission");
448 // Set to distribution
449 workspace->setDistribution(true);
450}
451
452} // namespace
453
455// Register the algorithm into the AlgorithmFactory
457
458
460
462 const std::string &extn = descriptor.extension();
463 if (extn != ".nxs" && extn != ".h5") {
464 return 0;
465 }
466 int confidence = 0;
467 auto const &entries = descriptor.getAllEntries();
468 for (auto const &[sasEntry, nxClass] : entries) {
469 if (nxClass == sasEntryClassAttr || nxClass == nxEntryClassAttr) {
470 std::string const dataAddress = sasEntry + "/" + sasEntryDefinition;
471 std::string const definitionFromFile = descriptor.getStrData(dataAddress);
472 // NOTE: for reasons I don't care to investigate, even if this has the correct definition,
473 // comparing as strings can still lead to mismatch unless compared as C-strings
474 if (std::strcmp(definitionFromFile.c_str(), sasEntryDefinitionFormat.c_str()) == 0) {
475 confidence = 95;
476 break;
477 }
478 }
479 }
480 return confidence;
481}
482
484 // Declare required input parameters for algorithm
485 const std::vector<std::string> exts{".nxs", ".h5"};
486 declareProperty(std::make_unique<Mantid::API::FileProperty>("Filename", "", FileProperty::Load, exts),
487 "The name of the NXcanSAS file to read, as a full or relative path.");
488 declareProperty(std::make_unique<Mantid::API::WorkspaceProperty<Mantid::API::Workspace>>("OutputWorkspace", "",
490 "The name of the workspace to be created as the output of "
491 "the algorithm. A workspace of this name will be created "
492 "and stored in the Analysis Data Service. For multiperiod "
493 "files, one workspace may be generated for each period. "
494 "Currently only one workspace can be saved at a time so "
495 "multiperiod Mantid files are not generated.");
496
497 declareProperty(std::make_unique<PropertyWithValue<bool>>("LoadTransmission", false, Direction::Input),
498 "Load the transmission related data from the file if it is present "
499 "(optional, default False).");
500}
501
503 const std::string fileName = getPropertyValue("Filename");
504 const bool isLoadTransmissionChecked = getProperty("LoadTransmission");
505 H5::H5File file(fileName, H5F_ACC_RDONLY, Nexus::H5Util::defaultFileAcc());
506
507 const auto entry = file.openGroup(getNameOfEntry(file));
508 const auto dataGroup = entry.openGroup(sasDataGroupName);
509 const auto dataInfo = getDataSpaceInfo(dataGroup.openDataSet(sasDataI));
510
511 // Setup progress bar
512 const size_t stepsPerSpinState = dataInfo.spinStates * 5;
513 const auto numberOfSteps = isLoadTransmissionChecked ? stepsPerSpinState + 1 : stepsPerSpinState;
514 m_progress = std::make_unique<API::Progress>(this, 0.1, 1.0, numberOfSteps);
515
516 // Load metadata and data into output workspace
517 const InstrumentNameInfo instrumentInfo(entry);
518 const auto wsGroup = transferFileDataIntoWorkspace(entry, dataInfo, instrumentInfo);
519
520 // Load Transmissions
521 if (isLoadTransmissionChecked) {
522 m_progress->report("Loading transmissions.");
523 // Load sample transmission
525 // Load can transmission
527 }
528
529 const auto wsOut = dataInfo.spinStates == 1 ? wsGroup->getItem(0) : std::dynamic_pointer_cast<Workspace>(wsGroup);
530 file.close();
531 setProperty("OutputWorkspace", wsOut);
532}
533
543 const InstrumentNameInfo &instrumentInfo, const std::optional<Sample> &sample,
544 const bool hasPolarizedData) const {
545 // Load logs
546 m_progress->report("Loading logs.");
547 loadLogs(group, workspace);
548 if (hasPolarizedData && group.nameExists(sasInstrumentSampleGroupAttr)) {
549 loadPolarizedLogs(group.openGroup(sasInstrumentSampleGroupAttr), workspace);
550 }
551
552 // Load title
553 m_progress->report("Loading title");
554 loadTitle(group, workspace);
555
556 // Load sample info
557 m_progress->report("Loading sample.");
558 if (sample.has_value()) {
559 workspace->mutableSample() = sample.value();
560 }
561 // Load instrument
562 m_progress->report("Loading instrument.");
563 loadInstrument(workspace, instrumentInfo);
564}
565
573 const std::pair<size_t, size_t> &spinIndexPair) const {
574 m_progress->report("Loading data.");
575 workspace->setDistribution(true);
576 WorkspaceDataInserter dataInserter(workspace);
577 auto dataSets = std::map<std::string, int>{
578 {sasDataI, 0}, {sasDataIdev, 1}, {m_dataDims->getNumberOfHistograms() > 1 ? sasDataQx : sasDataQ, 2}};
579
580 if (dataGroup.nameExists(sasDataQdev)) {
581 dataSets.insert({sasDataQdev, 3});
582 }
583 auto slabShape = m_dataDims->getSlabShape();
584 const auto nPoints = m_dataDims->getNumberOfPoints();
585 const auto nHisto = m_dataDims->getNumberOfHistograms();
586
587 for (const auto &[setName, axesIndex] : dataSets) {
588 auto dataSet = dataGroup.openDataSet(setName);
589 auto offset = updateOffset(axesIndex, spinIndexPair, slabShape);
590 dataInserter.setAxisType(axesIndex);
591 readDataIntoWorkspace(dataSet, dataInserter, slabShape, nPoints, nHisto, offset);
592 dataInserter.setUnits(dataSet);
593 }
594
595 // Qy is inserted a bit differently
596 if (dataGroup.nameExists(sasDataQy)) {
597 readQyInto2DWorkspace(dataGroup.openDataSet(sasDataQy), workspace, m_dataDims->getNumberOfHistograms());
598 }
599}
600
607std::vector<SpinState> LoadNXcanSAS::prepareDataDimensions(const H5::Group &group,
608 const DataSpaceInformation &dataInfo) {
609 const auto &[pIn, pOut] = loadSpinVectors(group);
610 const auto spinPairs =
611 !pIn.empty() && !pOut.empty() ? std::optional(std::make_pair(pIn.size(), pOut.size())) : std::nullopt;
612
613 const auto spinStates = spinPairs.has_value() ? prepareSpinIndexes(pIn, pOut) :
614 /* default unpolarized: 1 state */ std::vector({SpinState()});
615 // prepare data dimensions and offset
616 m_dataDims = std::make_unique<DataDimensions>(dataInfo.dimBin, dataInfo.dimSpectrumAxis, spinPairs);
617 return spinStates;
618}
619
628 const DataSpaceInformation &dataInfo,
629 const InstrumentNameInfo &instrumentInfo) {
630 const auto dataGroup = group.openGroup(sasDataGroupName);
631 const auto states = prepareDataDimensions(dataGroup, dataInfo);
632 const auto wsName = getPropertyValue("OutputWorkspace");
633
634 auto dataOut = std::make_shared<WorkspaceGroup>();
635 const auto sample = loadSample(group); // Sample should be similar in all workspaces
636 // spinStr will be empty if data is not polarized -> Only one output workspace
637 for (const auto &[spinStr, spinIndexPair] : states) {
638 auto ws = createWorkspace(dataInfo);
639
640 loadMetadata(group, ws, instrumentInfo, sample, !spinStr.empty());
641 loadData(dataGroup, ws, spinIndexPair);
642
643 if (!spinStr.empty()) {
644 addLogToWs(ws, NX_SPIN_LOG, spinStr);
645 ws->setTitle(wsName + "_" + spinStr);
646 }
647 dataOut->addWorkspace(ws);
648 }
649 return dataOut;
650}
651
652void LoadNXcanSAS::loadTransmission(const H5::Group &entry, const std::string &name,
653 const InstrumentNameInfo &instrumentInfo) {
654 if (!fileHasTransmissionEntry(entry, name)) {
655 return;
656 }
657 const auto transmission = entry.openGroup(sasTransmissionSpectrumGroupName + "_" + name);
658 const auto tDataSet = transmission.openDataSet(sasTransmissionSpectrumT);
659 // Create a 1D workspace
660 const auto workspace = createWorkspace(getDataSpaceInfo(tDataSet), true);
661 // Load logs
662 loadLogs(entry, workspace);
663 loadTitle(entry, workspace);
664 workspace->setTitle(workspace->getTitle() + "_trans_" + name);
665 // Load Instrument
666 loadInstrument(workspace, instrumentInfo);
667 // Load transmission data
668 loadTransmissionData(transmission, workspace);
669 // Set the workspace on the output
670 const std::string propertyName = (name == "sample") ? "TransmissionWorkspace" : "TransmissionCanWorkspace";
671 declareProperty(std::make_unique<WorkspaceProperty<>>(propertyName, workspace->getTitle(), Direction::Output),
672 "The transmission workspace");
673 setProperty(propertyName, workspace);
674}
675
676} // namespace Mantid::DataHandling::NXcanSAS
std::string name
Definition Run.cpp:60
const std::vector< double > * lambda
double height
Definition GetAllEi.cpp:155
double position
Definition GetAllEi.cpp:154
IPeaksWorkspace_sptr workspace
std::map< DeltaEMode::Type, std::string > index
uint64_t hsize_t
#define DECLARE_NEXUS_LAZY_FILELOADER_ALGORITHM(classname)
DECLARE_NEXUS_LAZY_FILELOADER_ALGORITHM should be used in place of the standard DECLARE_ALGORITHM mac...
void declareProperty(std::unique_ptr< Kernel::Property > p, const std::string &doc="") override
Add a property to the list of managed properties.
std::string getPropertyValue(const std::string &name) const override
Get the value of a property as a string.
TypedValue getProperty(const std::string &name) const override
Get the value of a property.
@ Load
allowed here which will be passed to the algorithm
This class stores information about the sample used in particular run.
Definition Sample.h:33
A property class for workspaces.
LoadNXcanSAS : Tries to load an NXcanSAS file type into a Workspace2D.
void loadMetadata(const H5::Group &group, const Mantid::API::MatrixWorkspace_sptr &workspace, const InstrumentNameInfo &instrumentInfo, const std::optional< API::Sample > &sample, bool hasPolarizedData=false) const
Loads metadata from H5 File into a Workspace: sample logs, instrument and sample information.
void loadData(const H5::Group &dataGroup, const Mantid::API::MatrixWorkspace_sptr &workspace, const std::pair< size_t, size_t > &spinIndexPair) const
General data loader, uses m_dataDims.
std::unique_ptr< NXcanSAS::DataDimensions > m_dataDims
void init() override
Initialisation code.
const std::string name() const override
function to return a name of the algorithm, must be overridden in all algorithms
void loadTransmission(const H5::Group &entry, const std::string &name, const InstrumentNameInfo &instrumentInfo)
Loads the transmission runs.
Mantid::API::WorkspaceGroup_sptr transferFileDataIntoWorkspace(const H5::Group &group, const DataSpaceInformation &dataInfo, const InstrumentNameInfo &instrumentInfo)
Prepares data to be loaded based on type and dimensionality.
std::unique_ptr< API::Progress > m_progress
std::vector< SpinState > prepareDataDimensions(const H5::Group &group, const DataSpaceInformation &dataInfo)
Prepares the DataDimensions struct that contains the shapes of the dataset objects,...
int confidence(Nexus::NexusDescriptorLazy &descriptor) const override
Returns a confidence value that this algorithm can load a file.
IPropertyManager * setProperty(const std::string &name, const T &value)
Templated method to set the value of a PropertyWithValue.
The Logger class is in charge of the publishing messages from the framework through various channels.
Definition Logger.h:51
void information(const std::string &msg)
Logs at information level.
Definition Logger.cpp:136
The concrete, templated class for properties.
static T & Instance()
Return a reference to the Singleton instance, creating it if it does not already exist Creation is do...
std::string getStrData(std::string const &address)
Get string data from a dataset at address.
std::string const & extension() const noexcept
Access the file extension.
std::map< std::string, std::string > const & getAllEntries() const noexcept
Returns a const reference of the internal map holding all entries in the Nexus HDF5 file.
std::shared_ptr< WorkspaceGroup > WorkspaceGroup_sptr
shared pointer to Mantid::API::WorkspaceGroup
std::shared_ptr< Workspace > Workspace_sptr
shared pointer to Mantid::API::Workspace
std::shared_ptr< T > createWorkspace(InitArgs... args)
Kernel::Logger g_log("ExperimentInfo")
static logger object
std::shared_ptr< MatrixWorkspace > MatrixWorkspace_sptr
shared pointer to the matrix workspace base class
const std::string sasInstrumentApertureGapWidth
const std::string sasTransmissionSpectrumNameCanAttrValue
const std::string sasInstrumentApertureGapHeight
const std::string sasTransmissionSpectrumTdev
DataSpaceInformation getDataSpaceInfo(const H5::DataSet &dataSet)
const std::string sasSampleEMFieldDirectionAzimuthal
const std::string sasTransmissionSpectrumLambda
const std::string sasInstrumentSampleThickness
const std::string sasTransmissionSpectrumNameSampleAttrValue
const std::string sasInstrumentApertureGroupName
const std::string sasSampleEMFieldDirectionRotation
const std::string sasTransmissionSpectrumGroupName
const std::string sasInstrumentSampleGroupAttr
const std::string sasSampleEMFieldDirectionPolar
MANTID_NEXUS_DLL void readStringAttribute(const H5::H5Object &object, const std::string &attributeName, std::string &output)
Definition H5Util.cpp:342
MANTID_NEXUS_DLL std::string readString(H5::H5File &file, const std::string &address)
Definition H5Util.cpp:266
MANTID_NEXUS_DLL H5::FileAccPropList defaultFileAcc()
Default file access is H5F_CLOSE_STRONG.
Definition H5Util.cpp:119
void readArray1DCoerce(const H5::Group &group, const std::string &name, std::vector< NumT > &output)
MANTID_NEXUS_DLL DataType getType< double >()
Definition H5Util.cpp:40
Header for a base Nexus::Exception.
STL namespace.
std::string to_string(const wide_integer< Bits, Signed > &n)
std::pair< size_t, size_t > spinIndexPair
@ Input
An input workspace.
Definition Property.h:53
@ Output
An output workspace.
Definition Property.h:54