Mantid
Loading...
Searching...
No Matches
CloneMatrixWorkspace.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 +
7//-----------------------------------------------------------------------------
8// Includes
9//-----------------------------------------------------------------------------
13
14#include <boost/python/extract.hpp>
15
16// See
17// http://docs.scipy.org/doc/numpy/reference/c-api.array.html#PY_ARRAY_UNIQUE_SYMBOL
18#define PY_ARRAY_UNIQUE_SYMBOL API_ARRAY_API
19#define NO_IMPORT_ARRAY
20#include <numpy/arrayobject.h>
21
25
26// ----------------------------------------------------------------------------------------------------------
27namespace {
29enum DataField { XValues = 0, YValues = 1, EValues = 2, DxValues = 3 };
30
40PyArrayObject *cloneArray(const MatrixWorkspace &workspace, DataField field, const size_t start, const size_t endp1) {
41 const npy_intp numHist(endp1 - start);
42 npy_intp stride{0};
43
44 // Find out which function we need to call to access the data
45 using ArrayAccessFn = const MantidVec &(MatrixWorkspace::*)(const size_t) const;
46 ArrayAccessFn dataAccesor;
51 if (field == XValues) {
52 stride = workspace.readX(0).size();
53 dataAccesor = &MatrixWorkspace::readX;
54 } else if (field == DxValues) {
55 stride = workspace.readDx(0).size();
56 dataAccesor = &MatrixWorkspace::readDx;
57 } else {
58 stride = workspace.blocksize();
59 if (field == YValues)
60 dataAccesor = &MatrixWorkspace::readY;
61 else
62 dataAccesor = &MatrixWorkspace::readE;
63 }
64 npy_intp arrayDims[2] = {numHist, stride};
65 auto *nparray =
66 reinterpret_cast<PyArrayObject *>(PyArray_NewFromDescr(&PyArray_Type, PyArray_DescrFromType(NPY_DOUBLE),
67 2, // rank 2
68 arrayDims, // Length in each dimension
69 nullptr, nullptr, 0, nullptr));
70 auto *dest = reinterpret_cast<double *>(PyArray_DATA(nparray)); // HEAD of the contiguous numpy data array
71
73 for (npy_intp i = 0; i < numHist; ++i) {
74 const MantidVec &src = (workspace.*(dataAccesor))(start + i);
75 std::copy(src.begin(), src.end(), std::next(dest, i * stride));
76 }
77 return nparray;
78}
79} // namespace
80
81// -------------------------------------- Cloned
82// arrays---------------------------------------------------
83/* Create a numpy array from the X values of the given workspace reference
84 * This acts like a python method on a Matrixworkspace object
85 * @param self :: A pointer to a PyObject representing the calling object
86 * @return A 2D numpy array created from the X values
87 */
88PyObject *cloneX(const MatrixWorkspace &self) {
89 return reinterpret_cast<PyObject *>(cloneArray(self, XValues, 0, self.getNumberHistograms()));
90}
91/* Create a numpy array from the Y values of the given workspace reference
92 * This acts like a python method on a Matrixworkspace object
93 * @param self :: A pointer to a PyObject representing the calling object
94 * @return A 2D numpy array created from the Y values
95 */
96PyObject *cloneY(const MatrixWorkspace &self) {
97 return reinterpret_cast<PyObject *>(cloneArray(self, YValues, 0, self.getNumberHistograms()));
98}
99
100/* Create a numpy array from the E values of the given workspace reference
101 * This acts like a python method on a Matrixworkspace object
102 * @param self :: A pointer to a PyObject representing the calling object
103 * @return A 2D numpy array created from the E values
104 */
105PyObject *cloneE(const MatrixWorkspace &self) {
106 return reinterpret_cast<PyObject *>(cloneArray(self, EValues, 0, self.getNumberHistograms()));
107}
108
109/* Create a numpy array from the E values of the given workspace reference
110 * This acts like a python method on a Matrixworkspace object
111 * @param self :: A pointer to a PyObject representing the calling object
112 * @return A 2D numpy array created from the E values
113 */
114PyObject *cloneDx(const MatrixWorkspace &self) {
115 return reinterpret_cast<PyObject *>(cloneArray(self, DxValues, 0, self.getNumberHistograms()));
116}
117} // namespace Mantid::PythonInterface
IPeaksWorkspace_sptr workspace
Definition: IndexPeaks.cpp:114
#define PARALLEL_FOR_IF(condition)
Empty definitions - to enable set your complier to enable openMP.
tagPyArrayObject PyArrayObject
Base MatrixWorkspace Abstract Class.
const MantidVec & readE(std::size_t const index) const
Deprecated, use e() instead.
const MantidVec & readDx(size_t const index) const
Deprecated, use dx() instead.
virtual std::size_t getNumberHistograms() const =0
Returns the number of histograms in the workspace.
const MantidVec & readY(std::size_t const index) const
Deprecated, use y() instead.
const MantidVec & readX(std::size_t const index) const
Deprecated, use x() instead.
std::shared_ptr< MatrixWorkspace > MatrixWorkspace_sptr
shared pointer to the matrix workspace base class
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.
Definition: MultiThreaded.h:22
PyObject * cloneE(const API::MatrixWorkspace &self)
Create a numpy array from the E values of the given workspace reference.
PyObject * cloneY(const API::MatrixWorkspace &self)
Create a numpy array from the Y values of the given workspace reference.
PyObject * cloneDx(const API::MatrixWorkspace &self)
Create a numpy array from the E values of the given workspace reference.
PyObject * cloneX(const API::MatrixWorkspace &self)
{ Create a numpy array from the X values of the given workspace reference
std::vector< double > MantidVec
typedef for the data storage used in Mantid matrix workspaces
Definition: cow_ptr.h:172