147{
148 std::ifstream in(path);
149 if (!in) {
150 std::stringstream ss;
151 ss << "Cannot open LEM table input file: " << path;
152 G4Exception("RBE::LoadData", "WrongTable", FatalException, ss.str().c_str());
153 }
154
155
157 if (!getline(in, line)) {
158 std::stringstream ss;
159 ss << "Cannot read header from the LEM table file: " << path;
160 G4Exception("RBE::LoadLEMTable", "CannotReadHeader", FatalException, ss.str().c_str());
161 }
162 std::vector<G4String> header =
split(line,
",");
163
164
165 std::vector<G4String> columns = {"alpha_x", "beta_x", "D_t", "specific_energy",
166 "alpha", "beta", "cell", "particle"};
167 std::map<G4String, int> columnIndices;
168 for (auto columnName : columns) {
169 auto pos = find(header.begin(), header.end(), columnName);
170 if (pos == header.end()) {
171 std::stringstream ss;
172 ss << "Column " << columnName << " not present in the LEM table file.";
173 G4Exception("RBE::LoadLEMTable", "ColumnNotPresent", FatalException, ss.str().c_str());
174 }
175 else {
176 columnIndices[columnName] = distance(header.begin(), pos);
177 }
178 }
179
180
181 while (getline(in, line)) {
182 std::vector<G4String> lineParts =
split(line,
",");
183 G4String cellLine = lineParts[columnIndices[
"cell"]];
184
186 G4int element = man->FindOrBuildElement(lineParts[columnIndices["particle"]])->GetZasInt();
187
189 std::stod(lineParts[columnIndices["specific_energy"]]) * MeV);
190 fTablesAlpha[cellLine][element].push_back(stod(lineParts[columnIndices[
"alpha"]]));
191
192
193
194 fTablesBeta[cellLine][element].push_back(stod(lineParts[columnIndices[
"beta"]]));
195
196 fTablesAlphaX[cellLine] = stod(lineParts[columnIndices[
"alpha_x"]]) / gray;
197 fTablesBetaX[cellLine] = stod(lineParts[columnIndices[
"beta_x"]]) / (gray * gray);
198 fTablesDoseCut[cellLine] = stod(lineParts[columnIndices[
"D_t"]]) * gray;
199 }
200
201
202
204 for (auto ePair : aPair.second) {
205 std::vector<G4double>& tableEnergy =
fTablesEnergy[aPair.first][ePair.first];
206 std::vector<G4double>& tableAlpha =
fTablesAlpha[aPair.first][ePair.first];
207 std::vector<G4double>& tableBeta =
fTablesBeta[aPair.first][ePair.first];
208
209 std::vector<size_t> idx(tableEnergy.size());
210 iota(idx.begin(), idx.end(), 0);
211 std::sort(idx.begin(), idx.end(),
212 [&tableEnergy](size_t i1, size_t i2) { return tableEnergy[i1] < tableEnergy[i2]; });
213
214 std::vector<std::vector<G4double>*> tables = {&tableEnergy, &tableAlpha, &tableBeta};
215 for (std::vector<G4double>* table : tables) {
216 std::vector<G4double> copy = *table;
217 for (size_t i = 0; i < copy.size(); ++i) {
218 (*table)[i] = copy[idx[i]];
219 }
220
221
222
223 }
224 }
225 }
226
228 G4cout << "RBE: read LEM data for the following cell lines and elements [number of points]:"
229 << G4endl;
231 G4cout << "- " << aPair.first << ": ";
232 for (auto ePair : aPair.second) {
233 G4cout << ePair.first << "[" << ePair.second.size() << "] ";
234 }
235 G4cout << G4endl;
236 }
237 }
238}
std::map< G4String, vector_type > fTablesEnergy
std::map< G4String, G4double > fTablesAlphaX
std::map< G4String, G4double > fTablesDoseCut
std::map< G4String, vector_type > fTablesAlpha
std::map< G4String, vector_type > fTablesBeta
std::map< G4String, G4double > fTablesBetaX
std::vector< G4String > split(const G4String &line, const G4String &delimiter)
Split string into parts using a delimiter.