##// END OF EJS Templates
Parser refactoring (4)...
Alexandre Leroux -
r988:6f8d3c2b5ba3
parent child
Show More
@@ -56,7 +56,12 public:
56 56 void readResultLine(const QString &line) override;
57 57
58 58 private:
59 /// @return the reading order of the "value" columns for a result line of the AMDA file
60 std::vector<int> valuesIndexes() const;
61
59 62 Properties m_Properties{};
63 std::vector<double> m_XAxisData{};
64 std::vector<double> m_ValuesData{};
60 65 };
61 66
62 67 /**
@@ -70,7 +75,12 public:
70 75 void readResultLine(const QString &line) override;
71 76
72 77 private:
78 /// @return the reading order of the "value" columns for a result line of the AMDA file
79 std::vector<int> valuesIndexes() const;
80
73 81 Properties m_Properties{};
82 std::vector<double> m_XAxisData{};
83 std::vector<double> m_ValuesData{};
74 84 };
75 85
76 86 #endif // SCIQLOP_AMDARESULTPARSERHELPER_H
@@ -1,11 +1,28
1 1 #include "AmdaResultParserHelper.h"
2 2
3 #include <Common/DateUtils.h>
4
5 #include <Data/ScalarSeries.h>
3 6 #include <Data/Unit.h>
7 #include <Data/VectorSeries.h>
8
9 #include <QtCore/QDateTime>
10 #include <QtCore/QRegularExpression>
4 11
5 12 Q_LOGGING_CATEGORY(LOG_AmdaResultParserHelper, "AmdaResultParserHelper")
6 13
7 14 namespace {
8 15
16 // ///////// //
17 // Constants //
18 // ///////// //
19
20 /// Separator between values in a result line
21 const auto RESULT_LINE_SEPARATOR = QRegularExpression{QStringLiteral("\\s+")};
22
23 /// Format for dates in result files
24 const auto DATE_FORMAT = QStringLiteral("yyyy-MM-ddThh:mm:ss.zzz");
25
9 26 // /////// //
10 27 // Methods //
11 28 // /////// //
@@ -28,6 +45,87 bool checkUnit(const Properties &properties, const QString &key, const QString &
28 45 return true;
29 46 }
30 47
48 QDateTime dateTimeFromString(const QString &stringDate) noexcept
49 {
50 #if QT_VERSION >= QT_VERSION_CHECK(5, 8, 0)
51 return QDateTime::fromString(stringDate, Qt::ISODateWithMs);
52 #else
53 return QDateTime::fromString(stringDate, DATE_FORMAT);
54 #endif
55 }
56
57 /// Converts a string date to a double date
58 /// @return a double that represents the date in seconds, NaN if the string date can't be converted
59 double doubleDate(const QString &stringDate) noexcept
60 {
61 // Format: yyyy-MM-ddThh:mm:ss.zzz
62 auto dateTime = dateTimeFromString(stringDate);
63 dateTime.setTimeSpec(Qt::UTC);
64 return dateTime.isValid() ? DateUtils::secondsSinceEpoch(dateTime)
65 : std::numeric_limits<double>::quiet_NaN();
66 }
67
68 /**
69 * Reads a line from the AMDA file and tries to extract a x-axis data and value data from it
70 * @param xAxisData the vector in which to store the x-axis data extracted
71 * @param valuesData the vector in which to store the value extracted
72 * @param line the line to read to extract the property
73 * @param valuesIndexes indexes of insertion of read values. For example, if the line contains three
74 * columns of values, and valuesIndexes are {2, 0, 1}, the value of the third column will be read
75 * and inserted first, then the value of the first column, and finally the value of the second
76 * column.
77 * @param fillValue value that tags an invalid data. For example, if fillValue is -1 and a read
78 * value is -1, then this value is considered as invalid and converted to NaN
79 */
80 void tryReadResult(std::vector<double> &xAxisData, std::vector<double> &valuesData,
81 const QString &line, const std::vector<int> &valuesIndexes,
82 double fillValue = std::numeric_limits<double>::quiet_NaN())
83 {
84 auto lineData = line.split(RESULT_LINE_SEPARATOR, QString::SkipEmptyParts);
85
86 // Checks that the line contains expected number of values + x-axis value
87 if (lineData.size() == valuesIndexes.size() + 1) {
88 // X : the data is converted from date to double (in secs)
89 auto x = doubleDate(lineData.at(0));
90
91 // Adds result only if x is valid. Then, if value is invalid, it is set to NaN
92 if (!std::isnan(x)) {
93 xAxisData.push_back(x);
94
95 // Values
96 for (auto valueIndex : valuesIndexes) {
97 bool valueOk;
98 // we use valueIndex + 1 to skip column 0 (x-axis value)
99 auto value = lineData.at(valueIndex + 1).toDouble(&valueOk);
100
101 if (!valueOk) {
102 qCWarning(LOG_AmdaResultParserHelper())
103 << QObject::tr(
104 "Value from (line %1, column %2) is invalid and will be "
105 "converted to NaN")
106 .arg(line, valueIndex);
107 value = std::numeric_limits<double>::quiet_NaN();
108 }
109
110 // Handles fill value
111 if (!std::isnan(fillValue) && !std::isnan(value) && fillValue == value) {
112 value = std::numeric_limits<double>::quiet_NaN();
113 }
114
115 valuesData.push_back(value);
116 }
117 }
118 else {
119 qCWarning(LOG_AmdaResultParserHelper())
120 << QObject::tr("Can't retrieve results from line %1: x is invalid").arg(line);
121 }
122 }
123 else {
124 qCWarning(LOG_AmdaResultParserHelper())
125 << QObject::tr("Can't retrieve results from line %1: invalid line").arg(line);
126 }
127 }
128
31 129 /**
32 130 * Reads a line from the AMDA file and tries to extract a property from it
33 131 * @param properties the properties map in which to put the property extracted from the line
@@ -81,7 +179,9 bool ScalarParserHelper::checkProperties()
81 179
82 180 std::shared_ptr<IDataSeries> ScalarParserHelper::createSeries()
83 181 {
84 /// @todo ALX
182 return std::make_shared<ScalarSeries>(std::move(m_XAxisData), std::move(m_ValuesData),
183 m_Properties.value(X_AXIS_UNIT_PROPERTY).value<Unit>(),
184 m_Properties.value(VALUES_UNIT_PROPERTY).value<Unit>());
85 185 }
86 186
87 187 void ScalarParserHelper::readPropertyLine(const QString &line)
@@ -91,7 +191,14 void ScalarParserHelper::readPropertyLine(const QString &line)
91 191
92 192 void ScalarParserHelper::readResultLine(const QString &line)
93 193 {
94 /// @todo ALX
194 tryReadResult(m_XAxisData, m_ValuesData, line, valuesIndexes());
195 }
196
197 std::vector<int> ScalarParserHelper::valuesIndexes() const
198 {
199 // Only one value to read
200 static auto result = std::vector<int>{0};
201 return result;
95 202 }
96 203
97 204 // ////////////////// //
@@ -106,7 +213,9 bool VectorParserHelper::checkProperties()
106 213
107 214 std::shared_ptr<IDataSeries> VectorParserHelper::createSeries()
108 215 {
109 /// @todo ALX
216 return std::make_shared<VectorSeries>(std::move(m_XAxisData), std::move(m_ValuesData),
217 m_Properties.value(X_AXIS_UNIT_PROPERTY).value<Unit>(),
218 m_Properties.value(VALUES_UNIT_PROPERTY).value<Unit>());
110 219 }
111 220
112 221 void VectorParserHelper::readPropertyLine(const QString &line)
@@ -116,5 +225,12 void VectorParserHelper::readPropertyLine(const QString &line)
116 225
117 226 void VectorParserHelper::readResultLine(const QString &line)
118 227 {
119 /// @todo ALX
228 tryReadResult(m_XAxisData, m_ValuesData, line, valuesIndexes());
229 }
230
231 std::vector<int> VectorParserHelper::valuesIndexes() const
232 {
233 // 3 values to read, in order in the file (x, y, z)
234 static auto result = std::vector<int>{0, 1, 2};
235 return result;
120 236 }
General Comments 0
You need to be logged in to leave comments. Login now