ATLAS Offline Software
Loading...
Searching...
No Matches
TextFileDBReader.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
3*/
4
5#include "TextFileDBReader.h"
6#include <fstream>
7#include <sstream>
8#include <iostream>
9#include <vector>
10#include <iomanip>
11
16
17TextFileDBReader::TextFileDBReader(const std::string & filename)
18 : m_numSections(0),
20{
21 readFile(filename);
22}
23
24
25bool
27{
28 std::ifstream ifile;
29 ifile.open(readFile.c_str());
30 if (!ifile) {
31 //std::cout << "Error opening file: " << readFile << std::endl;
32 return false;
33 }
34
35 bool tableMode = false;
36 std::string currentTable;
37 int currentIndex = -1;
38 std::vector<std::string> currentFields;
40
41 while (ifile) {
42 std::string line;
43 std::getline(ifile,line);
44 if (!ifile) break;
45 // Skip blank or comment lines
46 if (line.empty() || line[0] == '#' || line.substr(0,2) == "//" ) continue;
47 std::istringstream istr(line);
48
49 std::string key;
50
51 istr >> key;
52
53 if (key.empty()) continue;
54
55 if (key == "Table") {
56 istr >> currentTable;
57 tableMode = true;
58 currentIndex = -1;
59 currentFields.clear();
60 } else if (key == "TableEnd") {
61 std::ostringstream ostr;
62 ostr << "TableSize:" << currentTable;
63 add(ostr.str(), currentIndex);
64 tableMode = false;
65 currentTable = "";
66 currentIndex = -1;
67 currentFields.clear();
68 } else if (key == "Section") {
69 std::string value;
70 istr >> value;
71 if (!value.empty()) {
72 int & section = m_sections[value];
73 // First section will number 1. Section 0 refers to unnamed section
76 }
77 } else if (key == "EndSection") {
79 } else {
80 if (!tableMode) {
81 std::string value;
82 istr >> value;
83 // Make sure its in correct format
84 key = formatKey(key);
85 add(key,value);
86 } else { // table mode
87 // reset stream.
88 std::istringstream istr2(line);
89
90 if (currentIndex < 0) {
91 // Get the fields
92 while (!istr2.eof()) {
93 std::string value;
94 istr2 >> value;
95 if (!value.empty()) currentFields.push_back(std::move(value));
96 }
97 } else {
98 // Get row of values
99 for (unsigned int i=0; i < currentFields.size(); i++) {
100 std::string value;
101 istr2 >> value;
102 if (istr2) {
103 std::ostringstream ostr;
104 ostr << currentTable << "#" << currentIndex << ":" << currentFields[i];
105 add(ostr.str(), value);
106 }
107 }
108 }
109 currentIndex++;
110 }
111 }
112 }
113 ifile.close();
114 //printParameters();
115 return true;
116}
117
118std::string
119TextFileDBReader::formatKey(const std::string & key) const
120{
121 //std::cout << "Key in: " << key << std::endl;
122 // Split into tableName, fieldName and rowNumber
123 // and recreate
124 std::string tableName;
125 std::string fieldName;
126 std::string rowNumber;
127 bool foundRowNumber = false;
128 std::string::size_type pos = key.find(':');
129 if (pos != std::string::npos) {
130 tableName = key.substr(0,pos);
131 foundRowNumber = getRowNumber(tableName,rowNumber);
132 fieldName = key.substr(++pos);
133 } else {
134 fieldName = key;
135 }
136 std::string tmpRowNumber;
137 if (getRowNumber(fieldName,tmpRowNumber)) {
138 if (foundRowNumber) {
139 // Already have rowNumber from before
140 std::cout << "ERROR in format:" << key << std::endl;
141 } else {
142 rowNumber = std::move(tmpRowNumber);
143 }
144 }
145
146 std::string newKey = key;
147 if ((tableName.empty() && !rowNumber.empty()) || fieldName.empty()) {
148 std::cout << "ERROR in format: " << key << std::endl;
149 } else {
150 if (rowNumber.empty()) rowNumber = "0";
151 if (tableName.empty()) {
152 newKey = std::move(fieldName);
153 }else if (tableName == "TableSize") {
154 newKey = "TableSize:"+fieldName;
155 } else {
156 newKey = tableName+"#"+rowNumber+":"+fieldName;
157 }
158 }
159 //std::cout << "Key out: " << newKey << std::endl;
160 return newKey;
161}
162
163bool
164TextFileDBReader::getRowNumber(std::string & key, std::string & rowNumber) const
165{
166 std::string::size_type pos = key.find('#');
167 if (pos != std::string::npos) {
168 rowNumber = key.substr(pos+1);
169 key.resize(pos);
170 return true;
171 }
172 return false;
173}
174
175
176
177void
178TextFileDBReader::add(const std::string & key, int value) {
179 std::ostringstream ostr;
180 ostr << value;
181 add(key,ostr.str());
182}
183
184
185void
186TextFileDBReader::add(const std::string & key, const std::string & value)
187{
188 if (m_table.find(key) != m_table.end()) {
189 std::cout << "WARNING! Overwriting exist entry with key: " << key << std::endl;
190 }
191 m_table.try_emplace (key, value, m_currentSection);
192}
193
194bool
195TextFileDBReader::find(const std::string & key, std::string & result) const
196{
197 std::unordered_map<std::string,Data>::const_iterator iter = m_table.find(key);
198 if (iter != m_table.end()) {
199 result = iter->second.value;
200 (iter->second).flag=true;
201 return true;
202 } else {
203 result = "";
204 return false;
205 }
206}
207
208void
210{
211 std::ios::fmtflags iosflags = std::cout.flags();
212 std::cout << std::left;
213 int sectionNum = 0;
214 if (!section.empty()) {
215 std::unordered_map<std::string,int>::const_iterator iterSect = m_sections.find(section);
216 if (iterSect != m_sections.end()) sectionNum = iterSect->second;
217 // If not found then prints those in unnamed section.(ie sectionNum = 0)
218 }
219 for (std::unordered_map<std::string,Data>::const_iterator iter = m_table.begin();
220 iter != m_table.end();
221 ++iter) {
222 if (section.empty() || iter->second.section == sectionNum) {
223 std::cout << std::setw(35) << iter->first << " " << iter->second.value << std::endl;
224 }
225 }
226 // reset flags to original state
227 std::cout.flags(iosflags);
228}
229
230// Print those variables that are not accessed
231void
232TextFileDBReader::printNotUsed(const std::string & section) const
233{
234 std::ios::fmtflags iosflags = std::cout.flags();
235 std::cout << std::left;
236 bool allused = true;
237 int sectionNum = 0;
238 if (!section.empty()) {
239 std::unordered_map<std::string,int>::const_iterator iterSect = m_sections.find(section);
240 if (iterSect != m_sections.end()) sectionNum = iterSect->second;
241 // If not found then considers those in unnamed section (ie sectionNum = 0)
242 }
243 for (std::unordered_map<std::string,Data>::const_iterator iter = m_table.begin();
244 iter != m_table.end();
245 ++iter) {
246 if ((section.empty() || iter->second.section == sectionNum) && (!(iter->second.flag))) {
247 std::cout << std::setw(35) << iter->first << " " << iter->second.value << std::endl;
248 allused = false;
249 }
250 }
251 if (allused) {
252 std::cout << "All parameters used" << std::endl;
253 }
254 // reset flags to original state
255 std::cout.flags(iosflags);
256}
257
258
259bool
261{
262 return (m_sections.find(section) != m_sections.end());
263}
void section(const std::string &sec)
void printNotUsed(const std::string &section="") const
void add(const std::string &key, const std::string &value)
std::string formatKey(const std::string &key) const
bool getRowNumber(std::string &key, std::string &rowNumber) const
void printParameters(const std::string &section="") const
bool find(const std::string &key, std::string &result) const
std::unordered_map< std::string, int > m_sections
bool readFile(const std::string &filename)
bool sectionPresent(const std::string &section) const
std::unordered_map< std::string, Data > m_table