ARTS  2.4.0(git:4fb77825)
make_auto_md_cc.cc
Go to the documentation of this file.
1 /* Copyright (C) 2000-2012 Stefan Buehler <sbuehler@ltu.se>
2 
3  This program is free software; you can redistribute it and/or modify it
4  under the terms of the GNU General Public License as published by the
5  Free Software Foundation; either version 2, or (at your option) any
6  later version.
7 
8  This program is distributed in the hope that it will be useful,
9  but WITHOUT ANY WARRANTY; without even the implied warranty of
10  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11  GNU General Public License for more details.
12 
13  You should have received a copy of the GNU General Public License
14  along with this program; if not, write to the Free Software
15  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
16  USA. */
17 
18 #include "agenda_record.h"
19 #include "array.h"
20 #include "arts.h"
21 #include "file.h"
22 #include "global_data.h"
23 #include "methods.h"
24 #include "workspace_ng.h"
25 
26 /* Adds commas and indentation to parameter lists. */
27 void align(ofstream& ofs, bool& is_first_parameter, const String& indent) {
28  // Add comma and line break, if not first element:
29  if (is_first_parameter)
30  is_first_parameter = false;
31  else {
32  ofs << ",\n";
33  // Make proper indentation:
34  ofs << indent;
35  }
36 }
37 
38 int main() {
39  try {
40  // Make the global data visible:
43  const Array<WsvRecord>& wsv_data = Workspace::wsv_data;
44 
45  // Initialize the wsv group name array:
47 
48  // Initialize wsv data.
50 
51  // Initialize WsvMap.
53 
54  // Initialize method data.
56 
57  // Expand supergeneric methods:
59 
60  const Index n_md = md_data.nelem();
61 
62  // Write auto_md.cc:
63  // -----------
64  ofstream ofs;
65  open_output_file(ofs, "auto_md.cc");
66 
67  ofs << "// This file was generated automatically by make_auto_md_cc.cc.\n";
68  ofs << "// DO NOT EDIT !\n";
69  ofs << "// Generated: " << __DATE__ << ", " << __TIME__ << "\n\n";
70 
71  ofs << "#include \"arts.h\"\n"
72  << "#include \"auto_md.h\"\n"
73  << "#include \"wsv_aux.h\"\n"
74  << "#include \"mc_interp.h\"\n"
75  << "#include \"m_append.h\"\n"
76  << "#include \"m_delete.h\"\n"
77  << "#include \"m_copy.h\"\n"
78  << "#include \"m_conversion.h\"\n"
79  << "#include \"m_extract.h\"\n"
80  << "#include \"m_general.h\"\n"
81  << "#include \"m_gridded_fields.h\"\n"
82  << "#include \"m_ignore.h\"\n"
83  << "#include \"m_nc.h\"\n"
84  << "#include \"m_reduce.h\"\n"
85  << "#include \"m_select.h\"\n"
86  << "#include \"m_xml.h\"\n"
87  << "#include \"m_basic_types.h\"\n"
88  << "#include \"propagationmatrix.h\"\n"
89  << "#include \"transmissionmatrix.h\"\n"
90  << "#include \"agenda_record.h\"\n"
91  << "#include \"workspace_ng.h\"\n"
92  << "#include \"global_data.h\"\n"
93  << "#include \"absorptionlines.h\"\n"
94  << "\n";
95 
96  //ofs << "static Index agendacallcount = 0;\n";
97 
98  // Write all get-away functions:
99  // -----------------------------
100  for (Index i = 0; i < n_md; ++i) {
101  const MdRecord& mdd = md_data[i];
102 
103  // This is needed to flag the first function parameter, which
104  // needs no line break before being written:
105  bool is_first_parameter = true;
106  // The String indent is needed to achieve the correct
107  // indentation of the functin parameters:
108  String indent = String(mdd.Name().nelem() + 3, ' ');
109  ;
110  // Flag to pass the workspace to the WSM. Only true if the WSM has
111  // an Agenda as input.
112  bool pass_workspace = false;
113 
114  // There are four lists of parameters that we have to
115  // write.
116  ArrayOfIndex vo = mdd.Out(); // Output
117  const ArrayOfIndex& vi = mdd.InOnly(); // Input
118  ArrayOfIndex vgo = mdd.GOutType(); // Generic Output
119  ArrayOfIndex vgi = mdd.GInType(); // Generic Input
120  // vo and vi contain handles of workspace variables,
121  // vgo and vgi handles of workspace variable groups.
122 
123  // There used to be a similar block here for the generic
124  // input/output variables. However, this was a mistake. For
125  // example, if a method has a vector as generic input and a
126  // vector as generic output, this does not mean that it is
127  // the same vector!
128 
129  {
130  String ws, mr;
131 
132  // Use parameter name only if it is used inside the function
133  // to avoid warnings
134  ws = " ws";
135  // if (!mdd.AgendaMethod() && !mdd.PassWorkspace() && !vo.nelem () && !vi.nelem () && !vgo.nelem () && !vgi.nelem ())
136  // {
137  // ws = "";
138  // }
139 
140  // Find out if the WSM gets an agenda as input. If so, pass
141  // the current workspace to this method
142  for (Index j = 0; !pass_workspace && j < mdd.In().nelem(); j++) {
143  if (is_agenda_group_id(wsv_data[mdd.In()[j]].Group())) {
144  pass_workspace = true;
145  }
146  }
147 
148  // Find out if the WSM gets an agenda as input. If so, pass
149  // the current workspace to this method
150  for (Index j = 0; !pass_workspace && j < mdd.GInType().nelem(); j++) {
151  if (is_agenda_group_id(mdd.GInType()[j])) {
152  pass_workspace = true;
153  }
154  }
155 
156  // Use parameter name only if it is used inside the function
157  // to avoid warnings
158  if (vo.nelem() || vi.nelem() || vgo.nelem() || vgi.nelem() ||
159  mdd.AgendaMethod()) {
160  mr = " mr";
161  }
162 
163  if (mdd.Supergeneric()) {
164  ofs << "void " << mdd.Name() << "_sg_" << mdd.ActualGroups()
165  << "_g(Workspace&" << ws << ", const MRecord&" << mr << ")\n"
166  << "{\n";
167  } else {
168  ofs << "void " << mdd.Name() << "_g(Workspace&" << ws
169  << ", const MRecord&" << mr << ")\n"
170  << "{\n";
171  }
172  }
173 
174  // Erase all Output only variables to uncover if they are
175  // misused as Input variables
176 #ifndef NDEBUG
177  // Determine indexes of variables in vo that are only use as output
178  ArrayOfIndex voutonly; // Output only
179  for (Index k = 0; k < vo.nelem(); ++k) {
180  bool output_only = true;
181  for (ArrayOfIndex::const_iterator j = mdd.In().begin();
182  j != mdd.In().end();
183  ++j)
184  if (vo[k] == *j) {
185  output_only = false;
186  break;
187  }
188 
189  if (output_only) voutonly.push_back(k);
190  }
191 
192  // Set builtin-type variables to a certain value,
193  // initialize objects with their default constructor
194  for (Index j = 0; j < voutonly.nelem(); j++) {
195  ostringstream docstr;
196  docstr << " // " << wsv_data[vo[voutonly[j]]].Name() << "\n";
197 
198  String gname = wsv_group_names[wsv_data[vo[voutonly[j]]].Group()];
199  ostringstream initstr;
200  if (gname == "Numeric")
201  initstr << " = NAN;";
202  else if (gname == "Index")
203  initstr << " = -1;";
204  else
205  initstr << " = " << gname << "();";
206 
207  // Only zero-out the variable if it is not passed as an input
208  // variable for any other parameter
209  ofs << " if (mr.In().end() == find(mr.In().begin(), mr.In().end(),"
210  << " mr.Out()[" << voutonly[j] << "]))\n";
211  ofs << " (*((" << wsv_group_names[wsv_data[vo[voutonly[j]]].Group()]
212  << " *)ws[mr.Out()[" << voutonly[j] << "]]))" << initstr.str();
213  ofs << docstr.str();
214  }
215 #endif /* NDEBUG */
216 
217  ofs << " " << mdd.Name() << "(";
218 
219  if (pass_workspace || mdd.PassWorkspace() || mdd.AgendaMethod()) {
220  ofs << "ws";
221  is_first_parameter = false;
222  }
223 
224  // Write the Output workspace variables:
225  for (Index j = 0; j < vo.nelem(); ++j) {
226  // Check by assert whether the group identifier is too
227  // large to correspond to a group. This can easily
228  // happen if somebody puts a variable identifier instead
229  // of a group identifier in the argument of GOUTPUT:
230  assert(wsv_data[vo[j]].Group() < wsv_group_names.nelem());
231 
232  // Add comma and line break, if not first element:
233  align(ofs, is_first_parameter, indent);
234 
235  ofs << "*((" << wsv_group_names[wsv_data[vo[j]].Group()]
236  << " *)ws[mr.Out()[" << j << "]])";
237  }
238 
239  // Write the Generic output workspace variables:
240  for (Index j = 0; j < vgo.nelem(); ++j) {
241  // Check by assert whether the group identifier is too
242  // large to correspond to a group. This can easily
243  // happen if somebody puts a variable identifier instead
244  // of a group identifier in the argument of GOUTPUT:
245  assert(vgo[j] < wsv_group_names.nelem());
246 
247  // Add comma and line break, if not first element:
248  align(ofs, is_first_parameter, indent);
249 
250  ofs << "*((" << wsv_group_names[vgo[j]] << " *)ws[mr.Out()["
251  << j + vo.nelem() << "]])";
252  }
253 
254  // Write the Generic output workspace variable names:
255  if (mdd.PassWsvNames()) {
256  for (Index j = 0; j < vgo.nelem(); ++j) {
257  // Add comma and line break, if not first element:
258  align(ofs, is_first_parameter, indent);
259 
260  ofs << "Workspace::wsv_data[mr.Out()[" << j + vo.nelem()
261  << "]].Name()";
262  }
263  }
264 
265  // Write the Input workspace variables:
266  for (Index j = 0; j < vi.nelem(); ++j) {
267  // Add comma and line break, if not first element:
268  align(ofs, is_first_parameter, indent);
269 
270  if (is_agenda_group_id(wsv_data[vi[j]].Group())) {
271  ofs << "*((" << wsv_group_names[wsv_data[vi[j]].Group()]
272  << " *)ws[mr.In()[" << j << "]])";
273  } else {
274  ofs << "*((" << wsv_group_names[wsv_data[vi[j]].Group()]
275  << " *)ws[mr.In()[" << j << "]])";
276  }
277  }
278 
279  // Write the control parameters:
280  {
281  if (mdd.SetMethod()) {
282  // Add comma and line break, if not first element:
283  align(ofs, is_first_parameter, indent);
284 
285  ofs << "mr.SetValue()";
286  } else {
287  // Write the Generic input workspace variables:
288  for (Index j = 0; j < vgi.nelem(); ++j) {
289  // Check by assert whether the group identifier is too
290  // large to correspond to a group. This can easily
291  // happen if somebody puts a variable identifier instead
292  // of a group identifier in the argument of GINPUT:
293  assert(vgi[j] < wsv_group_names.nelem());
294 
295  // Add comma and line break, if not first element:
296  align(ofs, is_first_parameter, indent);
297 
298  ofs << "*((" << wsv_group_names[vgi[j]] << " *)ws[mr.In()["
299  << j + vi.nelem() << "]])";
300  }
301 
302  // Write the Generic input workspace variable names:
303  if (mdd.PassWsvNames()) {
304  for (Index j = 0; j < vgi.nelem(); ++j) {
305  // Add comma and line break, if not first element:
306  align(ofs, is_first_parameter, indent);
307 
308  ofs << "Workspace::wsv_data[mr.In()[" << j + vi.nelem()
309  << "]].Name()";
310  }
311  }
312  }
313  }
314 
315  // Write the agenda, if there is one.
316  if (mdd.AgendaMethod()) {
317  align(ofs, is_first_parameter, indent);
318  ofs << "mr.Tasks()";
319  }
320 
321  // Flag that is set to false if the WSM has verbosity as an input or
322  // output already. Otherwise it's passed as the last parameter.
323  bool pass_verbosity = true;
324 
325  // Find out if the WSM has the verbosity as input.
326  for (Index j = 0; pass_verbosity && j < mdd.In().nelem(); j++) {
327  if (wsv_data[mdd.In()[j]].Name() == "verbosity") {
328  pass_verbosity = false;
329  }
330  }
331 
332  // Find out if the WSM has the verbosity as output.
333  for (Index j = 0; pass_verbosity && j < mdd.Out().nelem(); j++) {
334  if (wsv_data[mdd.Out()[j]].Name() == "verbosity") {
335  pass_verbosity = false;
336  }
337  }
338 
339  if (pass_verbosity) {
340  static Index verbosity_wsv_id = get_wsv_id("verbosity");
341  static Index verbosity_group_id = get_wsv_group_id("Verbosity");
342  align(ofs, is_first_parameter, indent);
343  ofs << "*((" << wsv_group_names[verbosity_group_id] << " *)ws["
344  << verbosity_wsv_id << "])";
345  }
346 
347  ofs << ");\n";
348  ofs << "}\n\n";
349  }
350 
351  // Add getaways, the array that hold pointers to the getaway functions:
352  {
353  String indent = " ";
354  bool is_first_parameter = true;
355 
356  ofs << "// The array holding the pointers to the getaway functions.\n"
357  << "void (*getaways[])(Workspace&, const MRecord&)\n"
358  << " = {";
359  for (Index i = 0; i < n_md; ++i) {
360  const MdRecord& mdd = md_data[i];
361 
362  // Add comma and line break, if not first element:
363  align(ofs, is_first_parameter, indent);
364 
365  if (mdd.Supergeneric()) {
366  ofs << mdd.Name() << "_sg_" << mdd.ActualGroups() << "_g";
367  } else {
368  ofs << mdd.Name() << "_g";
369  }
370  }
371  // Add empty slot which can be used by the API for external callbacks.
372  ofs << ", nullptr};\n\n";
373  }
374 
375  // Agenda execute helper function
376 
377  ofs << "void auto_md_agenda_execute_helper(bool& agenda_failed, String& agenda_error_msg, Workspace& ws, const Agenda& input_agenda)\n";
378  ofs << "{\n";
379  ofs << " const ArrayOfIndex& outputs_to_push = input_agenda.get_output2push();\n";
380  ofs << " const ArrayOfIndex& outputs_to_dup = input_agenda.get_output2dup();\n";
381  ofs << "\n";
382  ofs << " for (auto&& i : outputs_to_push)\n";
383  ofs << " {\n";
384  ofs << " // Even if a variable is only used as WSM output inside this agenda,\n";
385  ofs << " // It is possible that it is used as input further down by another agenda,\n";
386  ofs << " // which we can't see here. Therefore initialized variables have to be\n";
387  ofs << " // duplicated.\n";
388  ofs << " if (ws.is_initialized(i))\n";
389  ofs << " ws.duplicate(i);\n";
390  ofs << " else\n";
391  ofs << " ws.push_uninitialized(i, NULL);\n";
392  ofs << " }\n";
393  ofs << "\n";
394  ofs << " for (auto&& i : outputs_to_dup)\n";
395  ofs << " ws.duplicate(i);\n";
396  ofs << "\n";
397  ofs << " agenda_failed = false;\n";
398  ofs << " try\n";
399  ofs << " {\n";
400  ofs << " input_agenda.execute(ws);\n";
401  ofs << " }\n";
402  ofs << " catch (const std::exception &e)\n";
403  ofs << " {\n";
404  ofs << " ostringstream os;\n";
405  ofs << " os << \"Run-time error in agenda: \"\n";
406  ofs << " << input_agenda.name() << \'\\n\' << e.what();\n";
407  ofs << " agenda_failed = true;\n";
408  ofs << " agenda_error_msg = os.str();\n";
409  ofs << " }\n";
410  ofs << "\n";
411  ofs << " for (auto&& i : outputs_to_push)\n";
412  ofs << " ws.pop_free(i);\n";
413  ofs << "\n";
414  ofs << " for (auto&& i : outputs_to_dup)\n";
415  ofs << " ws.pop_free(i);\n";
416  ofs << "}\n\n";
417 
418  // Create implementation of the agenda wrappers
419 
420  // Initialize agenda data.
423 
425  for (Index i = 0; i < agenda_data.nelem(); i++) {
426  const AgRecord& agr = agenda_data[i];
427  const ArrayOfIndex& ago = agr.Out();
428  const ArrayOfIndex& agi = agr.In();
429  ostringstream ain_push_os, ain_pop_os;
430  ostringstream aout_push_os, aout_pop_os;
431 
432  bool is_agenda_array = wsv_data[get_wsv_id(agr.Name())].Group() ==
433  get_wsv_group_id("ArrayOfAgenda");
434  write_agenda_wrapper_header(ofs, agr, is_agenda_array);
435 
436  ofs << "\n";
437  ofs << "{\n";
438 
439  if (ago.nelem() || agi.nelem()) {
440  if (is_agenda_array) {
441  ofs << " if (agenda_array_index < 0 || agenda_array_index >= input_agenda_array.nelem())\n"
442  << " {\n"
443  << " std::ostringstream os;\n"
444  << " os << \"Agenda index \" << agenda_array_index\n"
445  << " << \" out of bounds. 0 <= index < \" << input_agenda_array.nelem();\n"
446  << " throw std::runtime_error(os.str());\n"
447  << " }\n\n"
448  << " const Agenda& input_agenda = input_agenda_array[agenda_array_index];\n\n";
449  }
450  ofs << " using global_data::AgendaMap;\n"
451  << " using global_data::agenda_data;\n"
452  << "\n"
453  << " if (!input_agenda.checked())\n"
454  << " throw std::runtime_error(\"" << agr.Name()
455  << " is uninitialized. Use *AgendaSet* to add methods to it.\\n"
456  << "Agenda variables defined in the controlfile cannot be executed.\\nThe agenda must "
457  << "be copied to a workspace variable for execution.\");\n"
458  << "\n"
459  << " const AgRecord& agr =\n"
460  << " agenda_data[AgendaMap.find (input_agenda.name ())->second];\n"
461  << "\n";
462  }
463  if (ago.nelem()) {
464  for (Index j = 0; j < ago.nelem(); j++) {
465  // Mark agenda output-only variables as uninitialized
466  ArrayOfIndex::const_iterator it = agi.begin();
467  while (it != agi.end() && *it != ago[j]) it++;
468  if (it == agi.end()) {
469  aout_push_os << " ws.push_uninitialized (aout[" << j << "], "
470  << "(void *)&" << wsv_data[ago[j]].Name() << ");\n";
471  } else {
472  aout_push_os << " ws.push (aout[" << j << "], "
473  << "(void *)&" << wsv_data[ago[j]].Name() << ");\n";
474  }
475  aout_pop_os << " ws.pop (aout[" << j << "]);\n";
476  }
477  }
478  if (agi.nelem()) {
479  for (Index j = 0; j < agi.nelem(); j++) {
480  // Ignore Input parameters that are also output
481  ArrayOfIndex::const_iterator it = ago.begin();
482  while (it != ago.end() && *it != agi[j]) it++;
483  if (it == ago.end()) {
484  ain_push_os << " ws.push (ain[" << j << "], "
485  << "(void *)&" << wsv_data[agi[j]].Name() << ");\n";
486  ain_pop_os << " ws.pop (ain[" << j << "]);\n";
487  }
488  }
489  }
490 
491  if (aout_push_os.str().length()) {
492  ofs << " const ArrayOfIndex& aout = agr.Out();\n";
493  ofs << aout_push_os.str() << "\n";
494  }
495  if (ain_push_os.str().length()) {
496  ofs << " const ArrayOfIndex& ain = agr.In();\n";
497  ofs << ain_push_os.str() << "\n";
498  }
499 
500  ofs << " bool agenda_failed;\n";
501  ofs << " String agenda_error_msg;\n";
502  ofs << " auto_md_agenda_execute_helper(agenda_failed, agenda_error_msg, ws, input_agenda);\n\n";
503 
504  if (aout_pop_os.str().length()) {
505  ofs << aout_pop_os.str() << "\n";
506  }
507  if (ain_pop_os.str().length()) {
508  ofs << ain_pop_os.str() << "\n";
509  }
510 
511  ofs << " if (agenda_failed) throw runtime_error (agenda_error_msg);\n";
512  ofs << "}\n\n";
513  }
514 
515  // Create implementation of the GroupCreate WSMs
516  //
517  for (auto&& it : wsv_group_names) {
518  if (it != "Any") {
519  ofs << "/* Workspace method: Doxygen documentation will be auto-generated */\n"
520  << "void " << it << "Create(" << it << "& var, const Verbosity&)\n"
521  << "{ ";
522 
523  // Treat atomic types separately.
524  // For objects the default constructor is used.
525  if (it == "Index")
526  ofs << "var = 0;";
527  else if (it == "Numeric")
528  ofs << "var = 0.;";
529  else
530  ofs << "var = " << it << "();";
531 
532  ofs << " }\n\n";
533  }
534  }
535  } catch (const std::runtime_error& x) {
536  cout << "Something went wrong. Message text:\n";
537  cout << x.what() << '\n';
538  return 1;
539  }
540 
541  return 0;
542 }
agenda_record.h
Declarations for AgRecord, storing lookup information for one agenda.
main
int main()
Definition: make_auto_md_cc.cc:38
write_agenda_wrapper_header
void write_agenda_wrapper_header(ofstream &ofs, const AgRecord &agr, bool is_agenda_array)
Write a agenda wrapper header.
Definition: agenda_record.cc:270
Workspace::wsv_data
static Array< WsvRecord > wsv_data
Global WSV data.
Definition: workspace_ng.h:58
MdRecord::Supergeneric
bool Supergeneric() const
Definition: methods.h:107
MdRecord::GOutType
const ArrayOfIndex & GOutType() const
Definition: methods.h:93
define_agenda_data
void define_agenda_data()
Definition: agendas.cc:44
MdRecord::GInType
const ArrayOfIndex & GInType() const
Definition: methods.h:98
MdRecord::PassWsvNames
bool PassWsvNames() const
Definition: methods.h:110
get_wsv_id
Index get_wsv_id(const String &name)
Get index of WSV.
Definition: workspace.cc:5751
MdRecord::SetMethod
bool SetMethod() const
Definition: methods.h:105
align
void align(ofstream &ofs, bool &is_first_parameter, const String &indent)
Definition: make_auto_md_cc.cc:27
array.h
This file contains the definition of Array.
Group
Definition: make_autoarts_h.cc:10
Array< WsvRecord >
Absorption::nelem
Index nelem(const Lines &l)
Number of lines.
Definition: absorptionlines.h:1820
MdRecord::ActualGroups
const String & ActualGroups() const
Definition: methods.h:111
AgRecord
Lookup information for one agenda.
Definition: agenda_record.h:43
my_basic_string< char >
MdRecord::AgendaMethod
bool AgendaMethod() const
Definition: methods.h:106
AgRecord::Name
const String & Name() const
Definition: agenda_record.h:58
Workspace::define_wsv_data
static void define_wsv_data()
Define workspace variables.
Definition: workspace.cc:39
is_agenda_group_id
bool is_agenda_group_id(const Index group)
Check if group is an agenda group.
Definition: groups.cc:218
expand_md_data_raw_to_md_data
void expand_md_data_raw_to_md_data()
Expand supergeneric methods.
Definition: methods_aux.cc:410
define_wsv_group_names
void define_wsv_group_names()
Define the array of workspace variable group names.
Definition: groups.cc:77
global_data.h
MdRecord::Name
const String & Name() const
Definition: methods.h:88
MdRecord::In
const ArrayOfIndex & In() const
Definition: methods.h:96
MdRecord::InOnly
const ArrayOfIndex & InOnly() const
Definition: methods.h:102
open_output_file
void open_output_file(ofstream &file, const String &name)
Open a file for writing.
Definition: file.cc:93
my_basic_string::nelem
Index nelem() const
Number of elements.
Definition: mystring.h:246
global_data::md_data
const Array< MdRecord > md_data
Lookup information for workspace methods.
Definition: interactive_workspace.cc:19
AgRecord::In
const ArrayOfIndex & In() const
Definition: agenda_record.h:61
workspace_ng.h
This file contains the Workspace class.
MdRecord
All information for one workspace method.
Definition: methods.h:41
String
my_basic_string< char > String
The String type for ARTS.
Definition: mystring.h:280
global_data::agenda_data
const Array< AgRecord > agenda_data
The lookup information for the agendas.
Definition: agendas.cc:41
file.h
This file contains basic functions to handle ASCII files.
ARTS::Var::x
Vector x(Workspace &ws) noexcept
Definition: autoarts.h:7346
Index
INDEX Index
The type to use for all integer numbers and indices.
Definition: matpack.h:39
MdRecord::Out
const ArrayOfIndex & Out() const
Definition: methods.h:91
global_data::wsv_group_names
const ArrayOfString wsv_group_names
The names associated with Wsv groups as Strings.
Definition: global_data.h:93
Workspace::define_wsv_map
static void define_wsv_map()
Map WSV names to indices.
Definition: workspace_ng.cc:48
get_wsv_group_id
Index get_wsv_group_id(const String &name)
Returns the id of the given group.
Definition: groups.cc:223
AgRecord::Out
const ArrayOfIndex & Out() const
Definition: agenda_record.h:60
MdRecord::PassWorkspace
bool PassWorkspace() const
Definition: methods.h:109
Array::nelem
Index nelem() const
Number of elements.
Definition: array.h:195
methods.h
Declaration of the class MdRecord.
define_md_data_raw
void define_md_data_raw()
Definition: methods.cc:191
arts.h
The global header file for ARTS.