Mantid
Loading...
Searching...
No Matches
AttenuationProfile.cpp
Go to the documentation of this file.
1// Mantid Repository : https://github.com/mantidproject/mantid
2//
3// Copyright © 2020 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#include <Poco/File.h>
12#include <Poco/Path.h>
13#include <fstream>
14
15namespace Mantid::Kernel {
16
27AttenuationProfile::AttenuationProfile(const std::string &inputFileName, const std::string &searchPath,
28 Material *extrapolationMaterial, double extrapolationMaxX) {
29 Poco::Path suppliedFileName(inputFileName);
30 Poco::Path inputFilePath;
31 std::string fileExt = suppliedFileName.getExtension();
32 std::transform(fileExt.begin(), fileExt.end(), fileExt.begin(), toupper);
33
34 if (fileExt == "DAT") {
35 if (suppliedFileName.isRelative()) {
36 bool useSearchDirectories = true;
37
38 if (!searchPath.empty()) {
39 inputFilePath = Poco::Path(Poco::Path(searchPath).parent(), inputFileName);
40 if (Poco::File(inputFilePath).exists()) {
41 useSearchDirectories = false;
42 }
43 }
44 if (useSearchDirectories) {
45 // ... and if that doesn't work look in the search directories
46 std::string foundFile = Mantid::Kernel::ConfigService::Instance().getFullPath(inputFileName, false, 0);
47 if (!foundFile.empty()) {
48 inputFilePath = Poco::Path(foundFile);
49 } else {
50 inputFilePath = suppliedFileName;
51 }
52 }
53 } else {
54 inputFilePath = suppliedFileName;
55 }
56 std::ifstream input(inputFilePath.toString(), std::ios_base::in);
57 if (input) {
58 std::string line;
59 double minX = std::numeric_limits<double>::max();
60 double maxX = std::numeric_limits<double>::lowest();
61 while (std::getline(input, line)) {
62 double x, alpha, error;
63 if (std::stringstream(line) >> x >> alpha >> error) {
64 minX = std::min(x, minX);
65 maxX = std::max(x, maxX);
66 m_Interpolator.addPoint(x, 1000 * alpha);
67 }
68 }
69 input.close();
70 // Assist the extrapolation outside the supplied x range to better
71 // handle noisy data. Add two surrounding points using the attenuation
72 // calculated from tabulated absorption\scattering cross sections
73 if (m_Interpolator.containData() && extrapolationMaterial) {
74 if ((minX > 0) && (minX < std::numeric_limits<double>::max())) {
75 m_Interpolator.addPoint(0, extrapolationMaterial->attenuationCoefficient(0));
76 }
77 if ((maxX < extrapolationMaxX) && (maxX > std::numeric_limits<double>::lowest())) {
78 m_Interpolator.addPoint(extrapolationMaxX, extrapolationMaterial->attenuationCoefficient(extrapolationMaxX));
79 }
80 }
81 } else {
82 throw Exception::FileError("Error reading attenuation profile file", inputFileName);
83 }
84 } else {
85 throw Exception::FileError("Attenuation profile file must be a .DAT file", inputFileName);
86 }
87}
88
102void AttenuationProfile::setAttenuationCoefficient(const double x, const double atten) {
103 m_Interpolator.addPoint(x, atten);
104}
105} // namespace Mantid::Kernel
double error
Definition: IndexPeaks.cpp:133
double getAttenuationCoefficient(const double x) const
Returns the attenuation coefficient for the supplied x value.
void setAttenuationCoefficient(const double x, const double atten)
Set the attenuation coefficient at x value.
Records the filename and the description of failure.
Definition: Exception.h:98
bool containData() const
return false if no data has been added
Definition: Interpolation.h:78
double value(const double &at) const
get interpolated value at location at
void addPoint(const double &xx, const double &yy)
add data point
A material is defined as being composed of a given element, defined as a PhysicalConstants::NeutronAt...
Definition: Material.h:50
double attenuationCoefficient(const double lambda) const
Definition: Material.cpp:267
static T & Instance()
Return a reference to the Singleton instance, creating it if it does not already exist Creation is do...
bool exists(::NeXus::File &file, const std::string &name)
Based on the current group in the file, does the named sub-entry exist?