ARTS 2.5.0 (git: 9ee3ac6c)
m_basic_types.cc
Go to the documentation of this file.
1/* Copyright (C) 2002-2012
2 Patrick Eriksson <Patrick.Eriksson@chalmers.se>
3 Stefan Buehler <sbuehler@ltu.se>
4
5 This program is free software; you can redistribute it and/or modify it
6 under the terms of the GNU General Public License as published by the
7 Free Software Foundation; either version 2, or (at your option) any
8 later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
18 USA. */
19
20/*===========================================================================
21 === File description
22 ===========================================================================*/
23
41/*===========================================================================
42 === External declarations
43 ===========================================================================*/
44
45#include <cmath>
46#include "array.h"
47#include "arts.h"
48#include "artstime.h"
49#include "energylevelmap.h"
50#include "exceptions.h"
51#include "gridded_fields.h"
52#include "lin_alg.h"
53#include "logic.h"
54#include "math_funcs.h"
55#include "matpackI.h"
56#include "matpackII.h"
57#include "matpackIII.h"
58#include "matpackIV.h"
59#include "matpackV.h"
60#include "matpackVI.h"
61#include "matpackVII.h"
62#include "messages.h"
63#include "mystring.h"
64#include "optproperties.h"
65#include "quantum.h"
66#include "sorting.h"
67
68/*===========================================================================
69 === The functions (in alphabetical order)
70 ===========================================================================*/
71
72/* Workspace method: Doxygen documentation will be auto-generated */
74 const ArrayOfIndex& values,
75 const Verbosity&) {
76 aoi = values;
77}
78
79/* Workspace method: Doxygen documentation will be auto-generated */
81 const Index& nelem,
82 const Index& value,
83 const Verbosity&) {
84 aoi.resize(nelem);
85 for (Index i = 0; i < nelem; i++) aoi[i] = value;
86}
87
88/* Workspace method: Doxygen documentation will be auto-generated */
90 const Index& start,
91 const Index& stop,
92 const Index& step,
93 const Verbosity& verbosity) {
96
97 Index n = (Index)floor((stop - start) / step) + 1;
98 if (n < 1) n = 1;
99
100 x.resize(n);
101
102 for (Index i = 0; i < n; i++) x[i] = start + i * step;
103
104 out2 << " Creating a linearly spaced ArrayOfIndex.\n";
105 out3 << " length : " << x.nelem() << "\n";
106 out3 << " first value : " << x[0] << "\n";
107
108 if (x.nelem() > 1) {
109 out3 << " step size : " << x[1] - x[0] << "\n";
110 out3 << " last value : " << x[x.nelem() - 1] << "\n";
111 }
112}
113
114/* Workspace method: Doxygen documentation will be auto-generated */
116 const ArrayOfString& sa2,
117 const Verbosity&) {
118 sa.resize(sa2.nelem());
119 sa = sa2;
120}
121
122/* Workspace method: Doxygen documentation will be auto-generated */
123void FlagOff(Index& x, const Verbosity&) { x = 0; }
124
125/* Workspace method: Doxygen documentation will be auto-generated */
126void FlagOn(Index& x, const Verbosity&) { x = 1; }
127
128/* Workspace method: Doxygen documentation will be auto-generated */
129void IndexAdd(Index& out,
130 const Index& in,
131 const Index& value,
132 const Verbosity&) {
133 out = in + value;
134}
135
136/* Workspace method: Doxygen documentation will be auto-generated */
138 const Index& in,
139 const Index& value,
140 const Verbosity&) {
141 out = in / value;
142}
143
144/* Workspace method: Doxygen documentation will be auto-generated */
146 const Index& in,
147 const Index& value,
148 const Verbosity&) {
149 out = in * value;
150}
151
152/* Workspace method: Doxygen documentation will be auto-generated */
153void IndexSet(Index& x, const Index& value, const Verbosity&) { x = value; }
154
155/* Workspace method: Doxygen documentation will be auto-generated */
156void IndexStepDown(Index& xout, const Index& xin, const Verbosity&) {
157 xout = xin - 1;
158}
159
160/* Workspace method: Doxygen documentation will be auto-generated */
161void IndexStepUp(Index& xout, const Index& xin, const Verbosity&) {
162 xout = xin + 1;
163}
164
165/* Workspace method: Doxygen documentation will be auto-generated */
167 const Index& in,
168 const Index& value,
169 const Verbosity&) {
170 out = in - value;
171}
172
173/* Workspace method: Doxygen documentation will be auto-generated */
175 const Matrix& in,
176 const Numeric& value,
177 const Verbosity&) {
178 // Note that in and out can be the same vector
179 if (&out == &in) {
180 // Out and in are the same. Just add the scalar value.
181 out += value;
182 } else {
183 // Out and in are different. We first have to copy in to out,
184 // then add the scalar value.
185 out.resize(in.nrows(), in.ncols());
186 out = in;
187 out += value;
188 }
189}
190
191/* Workspace method: Doxygen documentation will be auto-generated */
193 const Matrix& in,
194 const Numeric& value,
195 const Verbosity&) {
196 // Note that in and out can be the same matrix
197 if (&out == &in) {
198 // Out and in are the same. Just multiply by the scalar value.
199 out /= value;
200 } else {
201 // Out and in are different. We first have to copy in to out,
202 // then multiply by the scalar value.
203 out.resize(in.nrows(), in.ncols());
204 out = in;
205 out /= value;
206 }
207}
208
209/* Workspace method: Doxygen documentation will be auto-generated */
211 const Matrix& in,
212 const Numeric& value,
213 const Verbosity&) {
214 // Note that in and out can be the same matrix
215 if (&out == &in) {
216 // Out and in are the same. Just multiply by the scalar value.
217 out *= value;
218 } else {
219 // Out and in are different. We first have to copy in to out,
220 // then multiply by the scalar value.
221 out.resize(in.nrows(), in.ncols());
222 out = in;
223 out *= value;
224 }
225}
226
227/* Workspace method: Doxygen documentation will be auto-generated */
229 const Matrix& in,
230 const Numeric& value,
231 const Verbosity&) {
232 // Note that in and out can be the same matrix
233 if (&out == &in) {
234 // Out and in are the same. Just multiply by the scalar value.
235 out -= value;
236 } else {
237 // Out and in are different. We first have to copy in to out,
238 // then multiply by the scalar value.
239 out.resize(in.nrows(), in.ncols());
240 out = in;
241 out -= value;
242 }
243}
244
245/* Workspace method: Doxygen documentation will be auto-generated */
246void MatrixCopySparse(Matrix& out, const Sparse& in, const Verbosity&) {
247 // There is probably a more efficient way to do this
248 out.resize(in.nrows(), in.ncols());
249 for (Index r = 0; r < in.nrows(); r++) {
250 for (Index c = 0; c < in.ncols(); c++) {
251 out(r, c) = in(r, c);
252 }
253 }
254}
255
256/* Workspace method: Doxygen documentation will be auto-generated */
258 // WS Generic Output:
259 Matrix& m,
260 // WS Input:
261 // WS Generic Input:
262 const Tensor3& t3,
263 const Index& index,
264 // Control Parameters:
265 const String& direction,
266 const Verbosity&) {
267 if (direction == "page") {
268 if (index >= t3.npages()) {
269 ostringstream os;
270 os << "The index " << index
271 << " is outside the page range of the Matrix.";
272 throw runtime_error(os.str());
273 }
274
275 m.resize(t3.nrows(), t3.ncols());
276 m = t3(index, joker, joker);
277 } else if (direction == "row") {
278 if (index >= t3.nrows()) {
279 ostringstream os;
280 os << "The index " << index << " is outside the row range of the Matrix.";
281 throw runtime_error(os.str());
282 }
283
284 m.resize(t3.npages(), t3.ncols());
285 m = t3(joker, index, joker);
286 } else if (direction == "column") {
287 if (index >= t3.ncols()) {
288 ostringstream os;
289 os << "The index " << index
290 << " is outside the column range of the Matrix.";
291 throw runtime_error(os.str());
292 }
293
294 m.resize(t3.npages(), t3.nrows());
295 m = t3(joker, joker, index);
296 } else {
297 ostringstream os;
298 os << "Keyword *direction* must be either *page* or *row* or *column*,"
299 << "but you gave: " << direction << ".";
300 throw runtime_error(os.str());
301 }
302}
303
304/* Workspace method: Doxygen documentation will be auto-generated */
305void MatrixMatrixMultiply( // WS Generic Output:
306 Matrix& Y,
307 // WS Generic Input:
308 const Matrix& M,
309 const Matrix& X,
310 const Verbosity&) {
311 // Check that dimensions are right, M.ncols() must match X.nrows():
312 if (M.ncols() != X.nrows()) {
313 ostringstream os;
314 os << "Matrix dimensions must be consistent!\n"
315 << "Matrix1.ncols() = " << M.ncols() << "\n"
316 << "Matrix2.nrows() = " << X.nrows();
317 throw runtime_error(os.str());
318 }
319
320 // Temporary for the result:
321 Matrix dummy(M.nrows(), X.ncols());
322
323 mult(dummy, M, X);
324
325 // Copy result to Y:
326
327 Y.resize(dummy.nrows(), dummy.ncols());
328
329 Y = dummy;
330}
331
332/* Workspace method: Doxygen documentation will be auto-generated */
333void Matrix1ColFromVector( // WS Generic Output:
334 Matrix& m,
335 // WS Generic Input:
336 const Vector& v,
337 const Verbosity&) {
338 const Index nv = v.nelem();
339
340 m.resize(nv, 1);
341 m(joker, 0) = v;
342}
343
344/* Workspace method: Doxygen documentation will be auto-generated */
345void Matrix2ColFromVectors( // WS Generic Output:
346 Matrix& m,
347 // WS Generic Input:
348 const Vector& v1,
349 const Vector& v2,
350 const Verbosity&) {
351 const Index nv = v1.nelem();
352
353 if (v2.nelem() != nv)
354 throw runtime_error("Vectors must be of the same size.");
355
356 m.resize(nv, 2);
357 m(joker, 0) = v1;
358 m(joker, 1) = v2;
359}
360
361/* Workspace method: Doxygen documentation will be auto-generated */
362void Matrix3ColFromVectors( // WS Generic Output:
363 Matrix& m,
364 // WS Generic Input:
365 const Vector& v1,
366 const Vector& v2,
367 const Vector& v3,
368 const Verbosity&) {
369 const Index nv = v1.nelem();
370
371 if (v3.nelem() != nv || v2.nelem() != nv)
372 throw runtime_error("Vectors must be of the same size.");
373
374 m.resize(nv, 3);
375 m(joker, 0) = v1;
376 m(joker, 1) = v2;
377 m(joker, 2) = v3;
378}
379
380/* Workspace method: Doxygen documentation will be auto-generated */
381void Matrix1RowFromVector( // WS Generic Output:
382 Matrix& m,
383 // WS Generic Input:
384 const Vector& v,
385 const Verbosity&) {
386 const Index nv = v.nelem();
387
388 m.resize(1, nv);
389 m(0, joker) = v;
390}
391
392/* Workspace method: Doxygen documentation will be auto-generated */
393void Matrix2RowFromVectors( // WS Generic Output:
394 Matrix& m,
395 // WS Generic Input:
396 const Vector& v1,
397 const Vector& v2,
398 const Verbosity&) {
399 const Index nv = v1.nelem();
400
401 if (v2.nelem() != nv)
402 throw runtime_error("Vectors must be of the same size.");
403
404 m.resize(2, nv);
405 m(0, joker) = v1;
406 m(1, joker) = v2;
407}
408
409/* Workspace method: Doxygen documentation will be auto-generated */
410void Matrix3RowFromVectors( // WS Generic Output:
411 Matrix& m,
412 // WS Generic Input:
413 const Vector& v1,
414 const Vector& v2,
415 const Vector& v3,
416 const Verbosity&) {
417 const Index nv = v1.nelem();
418
419 if (v3.nelem() != nv || v2.nelem() != nv)
420 throw runtime_error("Vectors must be of the same size.");
421
422 m.resize(3, nv);
423 m(0, joker) = v1;
424 m(1, joker) = v2;
425 m(2, joker) = v3;
426}
427
428/* Workspace method: Doxygen documentation will be auto-generated */
430 const Index& n,
431 const Numeric& value,
432 const Verbosity&) {
433 out.resize(n, n);
434 id_mat(out);
435 if (value != 1) {
436 out *= value;
437 }
438}
439
440/* Workspace method: Doxygen documentation will be auto-generated */
441void MatrixSet(Matrix& x, const Matrix& values, const Verbosity&) {
442 x = values;
443}
444
445/* Workspace method: Doxygen documentation will be auto-generated */
447 const Index& nrows,
448 const Index& ncols,
449 const Numeric& value,
450 const Verbosity&) {
451 x.resize(nrows, ncols);
452 x = value;
453}
454
455/* Workspace method: Doxygen documentation will be auto-generated */
457 const Numeric& in,
458 const Numeric& value,
459 const Verbosity&) {
460 out = in + value;
461}
462
463/* Workspace method: Doxygen documentation will be auto-generated */
465 const Numeric& in,
466 const Numeric& limit_low,
467 const Numeric& limit_high,
468 const Verbosity&) {
469 if (in < limit_low)
470 out = limit_low;
471 else if (in > limit_high)
472 out = limit_high;
473 else
474 out = in;
475}
476
477/* Workspace method: Doxygen documentation will be auto-generated */
479 const Numeric& in,
480 const Numeric& value,
481 const Verbosity&) {
482 out = in / value;
483}
484
485/* Workspace method: Doxygen documentation will be auto-generated */
487 const Vector& in,
488 const String& op,
489 const Verbosity&) {
490 if (op == "first")
491 out = in[0];
492 else if (op == "last")
493 out = in[in.nelem() - 1];
494 else if (op == "max")
495 out = max(in);
496 else if (op == "min")
497 out = min(in);
498 else if (op == "mean")
499 out = mean(in);
500 else {
501 ostringstream os;
502 os << "Your choice, *op* = \"" << op << "\", is not recognised.\n"
503 << "Valid options are: \"first\", \"last\", \"max\", \"min\" and \"mean\".";
504 throw runtime_error(os.str());
505 }
506}
507
508/* Workspace method: Doxygen documentation will be auto-generated */
510 const Numeric& in,
511 const Numeric& value,
512 const Verbosity&) {
513 out = in * value;
514}
515
516/* Workspace method: Doxygen documentation will be auto-generated */
517void NumericSet(Numeric& x, const Numeric& value, const Verbosity&) {
518 x = value;
519}
520
521/* Workspace method: Doxygen documentation will be auto-generated */
523 const Numeric& in,
524 const Numeric& value,
525 const Verbosity&) {
526 out = in - value;
527}
528
529/* Workspace method: Doxygen documentation will be auto-generated */
531 const String& value,
532 const Verbosity&) {
533 x = QuantumIdentifier(value);
534}
535
536/* Workspace method: Doxygen documentation will be auto-generated */
538 const ArrayOfString& values,
539 const Verbosity& verbosity) {
540 x.resize(values.nelem());
541 for (Index i = 0; i < x.nelem(); i++)
542 QuantumIdentifierSet(x[i], values[i], verbosity);
543}
544
545/* Workspace method: Doxygen documentation will be auto-generated */
547 const Rational& in,
548 const Rational& value,
549 const Verbosity&) {
550 out = in + value;
551}
552
553/* Workspace method: Doxygen documentation will be auto-generated */
555 const Rational& in,
556 const Rational& value,
557 const Verbosity&) {
558 out = in / value;
559}
560
561/* Workspace method: Doxygen documentation will be auto-generated */
563 const Rational& in,
564 const Rational& value,
565 const Verbosity&) {
566 out = in * value;
567}
568
569/* Workspace method: Doxygen documentation will be auto-generated */
571 const Index& numerator,
572 const Index& denominator,
573 const Verbosity&) {
574 x = Rational(numerator, denominator);
575}
576
577/* Workspace method: Doxygen documentation will be auto-generated */
579 const Rational& in,
580 const Rational& value,
581 const Verbosity&) {
582 out = in - value;
583}
584
585
586/* Workspace method: Doxygen documentation will be auto-generated */
587void SparseSparseMultiply( // WS Generic Output:
588 Sparse& Y,
589 // WS Generic Input:
590 const Sparse& M,
591 const Sparse& X,
592 const Verbosity&) {
593 // Check that dimensions are right, M.ncols() must match X.nrows():
594 if (M.ncols() != X.nrows()) {
595 ostringstream os;
596 os << "Matrix dimensions must be consistent!\n"
597 << "Matrix1.ncols() = " << M.ncols() << "\n"
598 << "Matrix2.nrows() = " << X.nrows();
599 throw runtime_error(os.str());
600 }
601
602 // Temporary for the result:
603 Sparse dummy(M.nrows(), X.ncols());
604
605 mult(dummy, M, X);
606
607 // Copy result to Y:
608 Y = dummy;
609}
610
611/* Workspace method: Doxygen documentation will be auto-generated */
613 const Index& n,
614 const Numeric& value,
615 const Verbosity&) {
616 X.resize(n, n);
617 id_mat(X);
618
619 if (value != 1.0) X *= value;
620}
621
622/* Workspace method: Doxygen documentation will be auto-generated */
623void DiagonalMatrix(Matrix& X, const Vector& diag, const Verbosity& /*v*/) {
624 Index n = diag.nelem();
625 X.resize(n, n);
626 X = 0.0;
627
628 for (Index i = 0; i < n; ++i) {
629 X(i, i) = diag[i];
630 }
631}
632
633/* Workspace method: Doxygen documentation will be auto-generated */
634void DiagonalMatrix(Sparse& X, const Vector& diag, const Verbosity& /*v*/) {
635 Index n = diag.nelem();
636 X.resize(n, n);
637
638 ArrayOfIndex indices(n);
639
640 for (Index i = 0; i < n; ++i) {
641 indices[i] = i;
642 }
643
644 X.insert_elements(n, indices, indices, diag);
645}
646
647/* Workspace method: Doxygen documentation will be auto-generated */
648void StringSet(String& s, const String& s2, const Verbosity&) { s = s2; }
649
650/* Workspace method: Doxygen documentation will be auto-generated */
652 const Tensor3& in,
653 const Numeric& value,
654 const Verbosity&) {
655 // Note that in and out can be the same vector
656 if (&out == &in) {
657 // Out and in are the same. Just multiply by the scalar value.
658 out += value;
659 } else {
660 // Out and in are different. We first have to copy in to out,
661 // then multiply by the scalar value.
662 out.resize(in.npages(), in.nrows(), in.ncols());
663 out = in;
664 out += value;
665 }
666}
667
668/* Workspace method: Doxygen documentation will be auto-generated */
669void Tensor3FromVector( // WS Generic Output:
670 Tensor3& m,
671 // WS Generic Input:
672 const Vector& v,
673 const Verbosity&) {
674 const Index nv = v.nelem();
675
676 m.resize(nv, 1, 1);
677 m(joker, 0, 0) = v;
678}
679
680/* Workspace method: Doxygen documentation will be auto-generated */
682 const Tensor3& in,
683 const Numeric& value,
684 const Verbosity&) {
685 // Note that in and out can be the same vector
686 if (&out == &in) {
687 // Out and in are the same. Just multiply by the scalar value.
688 out *= value;
689 } else {
690 // Out and in are different. We first have to copy in to out,
691 // then multiply by the scalar value.
692 out.resize(in.npages(), in.nrows(), in.ncols());
693 out = in;
694 out *= value;
695 }
696}
697
698/* Workspace method: Doxygen documentation will be auto-generated */
700 const Index& npages,
701 const Index& nrows,
702 const Index& ncols,
703 const Numeric& value,
704 const Verbosity& verbosity) {
707
709 x = value;
710
711 out2 << " Tensor3 = " << value << "\n";
712 out3 << " npages : " << npages << "\n";
713 out3 << " nrows : " << nrows << "\n";
714 out3 << " ncols : " << ncols << "\n";
715}
716
717/* Workspace method: Doxygen documentation will be auto-generated */
719 // WS Generic Output:
720 Tensor3& t3,
721 // WS Input:
722 // WS Generic Input:
723 const Tensor4& t4,
724 const Index& index,
725 // Control Parameters:
726 const String& direction,
727 const Verbosity&) {
728 if (direction == "book") {
729 if (index >= t4.nbooks()) {
730 ostringstream os;
731 os << "The index " << index
732 << " is outside the book range of the Tensor4.";
733 throw runtime_error(os.str());
734 }
735
736 t3.resize(t4.npages(), t4.nrows(), t4.ncols());
737 t3 = t4(index, joker, joker, joker);
738 } else if (direction == "page") {
739 if (index >= t4.npages()) {
740 ostringstream os;
741 os << "The index " << index
742 << " is outside the pages range of the Tensor4.";
743 throw runtime_error(os.str());
744 }
745
746 t3.resize(t4.nbooks(), t4.nrows(), t4.ncols());
747 t3 = t4(joker, index, joker, joker);
748 } else if (direction == "row") {
749 if (index >= t4.nrows()) {
750 ostringstream os;
751 os << "The index " << index
752 << " is outside the row range of the Tensor4.";
753 throw runtime_error(os.str());
754 }
755
756 t3.resize(t4.npages(), t4.nbooks(), t4.ncols());
757 t3 = t4(joker, joker, index, joker);
758 } else if (direction == "column") {
759 if (index >= t4.ncols()) {
760 ostringstream os;
761 os << "The index " << index
762 << " is outside the column range of the Tensor4.";
763 throw runtime_error(os.str());
764 }
765
766 t3.resize(t4.npages(), t4.nbooks(), t4.nrows());
767 t3 = t4(joker, joker, joker, index);
768 } else {
769 ostringstream os;
770 os << "Keyword *direction* must be either *page*, *book*, *row* or *column*,"
771 << "but you gave: " << direction << ".";
772 throw runtime_error(os.str());
773 }
774}
775
776/* Workspace method: Doxygen documentation will be auto-generated */
778 const Tensor4& in,
779 const Numeric& value,
780 const Verbosity&) {
781 // Note that in and out can be the same vector
782 if (&out == &in) {
783 // Out and in are the same. Just multiply by the scalar value.
784 out += value;
785 } else {
786 // Out and in are different. We first have to copy in to out,
787 // then multiply by the scalar value.
788 out.resize(in.nbooks(), in.npages(), in.nrows(), in.ncols());
789 out = in;
790 out += value;
791 }
792}
793
794/* Workspace method: Doxygen documentation will be auto-generated */
796 const Tensor4& in,
797 const Numeric& value,
798 const Verbosity&) {
799 // Note that in and out can be the same vector
800 if (&out == &in) {
801 // Out and in are the same. Just multiply by the scalar value.
802 out *= value;
803 } else {
804 // Out and in are different. We first have to copy in to out,
805 // then multiply by the scalar value.
806 out.resize(in.nbooks(), in.npages(), in.nrows(), in.ncols());
807 out = in;
808 out *= value;
809 }
810}
811
812/* Workspace method: Doxygen documentation will be auto-generated */
814 const Index& nbooks,
815 const Index& npages,
816 const Index& nrows,
817 const Index& ncols,
818 const Numeric& value,
819 const Verbosity& verbosity) {
822
824 x = value;
825
826 out2 << " Tensor4 = " << value << "\n";
827 out3 << " nbooks : " << nbooks << "\n";
828 out3 << " npages : " << npages << "\n";
829 out3 << " nrows : " << nrows << "\n";
830 out3 << " ncols : " << ncols << "\n";
831}
832
833/* Workspace method: Doxygen documentation will be auto-generated */
835 const Tensor5& in,
836 const Numeric& value,
837 const Verbosity&) {
838 // Note that in and out can be the same vector
839 if (&out == &in) {
840 // Out and in are the same. Just multiply by the scalar value.
841 out *= value;
842 } else {
843 // Out and in are different. We first have to copy in to out,
844 // then multiply by the scalar value.
845 out.resize(in.nshelves(), in.nbooks(), in.npages(), in.nrows(), in.ncols());
846 out = in;
847 out *= value;
848 }
849}
850
851/* Workspace method: Doxygen documentation will be auto-generated */
853 const Index& nshelves,
854 const Index& nbooks,
855 const Index& npages,
856 const Index& nrows,
857 const Index& ncols,
858 const Numeric& value,
859 const Verbosity& verbosity) {
862
864 x = value;
865
866 out2 << " Tensor5 = " << value << "\n";
867 out3 << " nshelves : " << nshelves << "\n";
868 out3 << " nbooks : " << nbooks << "\n";
869 out3 << " npages : " << npages << "\n";
870 out3 << " nrows : " << nrows << "\n";
871 out3 << " ncols : " << ncols << "\n";
872}
873
874/* Workspace method: Doxygen documentation will be auto-generated */
876 const Tensor6& in,
877 const Numeric& value,
878 const Verbosity&) {
879 // Note that in and out can be the same vector
880 if (&out == &in) {
881 // Out and in are the same. Just multiply by the scalar value.
882 out *= value;
883 } else {
884 // Out and in are different. We first have to copy in to out,
885 // then multiply by the scalar value.
886 out.resize(in.nvitrines(),
887 in.nshelves(),
888 in.nbooks(),
889 in.npages(),
890 in.nrows(),
891 in.ncols());
892 out = in;
893 out *= value;
894 }
895}
896
897/* Workspace method: Doxygen documentation will be auto-generated */
899 const Index& nvitrines,
900 const Index& nshelves,
901 const Index& nbooks,
902 const Index& npages,
903 const Index& nrows,
904 const Index& ncols,
905 const Numeric& value,
906 const Verbosity& verbosity) {
909
911 x = value;
912
913 out2 << " Tensor6 = " << value << "\n";
914 out3 << " nvitrines : " << nvitrines << "\n";
915 out3 << " nshelves : " << nshelves << "\n";
916 out3 << " nbooks : " << nbooks << "\n";
917 out3 << " npages : " << npages << "\n";
918 out3 << " nrows : " << nrows << "\n";
919 out3 << " ncols : " << ncols << "\n";
920}
921
922/* Workspace method: Doxygen documentation will be auto-generated */
924 const Tensor7& in,
925 const Numeric& value,
926 const Verbosity&) {
927 // Note that in and out can be the same vector
928 if (&out == &in) {
929 // Out and in are the same. Just multiply by the scalar value.
930 out *= value;
931 } else {
932 // Out and in are different. We first have to copy in to out,
933 // then multiply by the scalar value.
934 out.resize(in.nlibraries(),
935 in.nvitrines(),
936 in.nshelves(),
937 in.nbooks(),
938 in.npages(),
939 in.nrows(),
940 in.ncols());
941 out = in;
942 out *= value;
943 }
944}
945
946/* Workspace method: Doxygen documentation will be auto-generated */
948 const Index& nlibraries,
949 const Index& nvitrines,
950 const Index& nshelves,
951 const Index& nbooks,
952 const Index& npages,
953 const Index& nrows,
954 const Index& ncols,
955 const Numeric& value,
956 const Verbosity& verbosity) {
959
960 x.resize(nlibraries, nvitrines, nshelves, nbooks, npages, nrows, ncols);
961 x = value;
962
963 out2 << " Tensor7 = " << value << "\n";
964 out3 << " nlibraries : " << nlibraries << "\n";
965 out3 << " nvitrines : " << nvitrines << "\n";
966 out3 << " nshelves : " << nshelves << "\n";
967 out3 << " nbooks : " << nbooks << "\n";
968 out3 << " npages : " << npages << "\n";
969 out3 << " nrows : " << nrows << "\n";
970 out3 << " ncols : " << ncols << "\n";
971}
972
973/* Workspace method: Doxygen documentation will be auto-generated */
974void Trapz(
975 Numeric& out,
976 const Vector& x,
977 const Vector& y,
978 const Verbosity&) {
979 const Index n = x.nelem();
980 if (y.nelem() != n)
981 throw runtime_error("The vectors *x* and *y* must have the same length.");
982
983 out = 0;
984 for (Index i=1; i<n; i++)
985 out += 0.5*(y[i-1]+y[i]) * (x[i]-x[i-1]);
986}
987
988/* Workspace method: Doxygen documentation will be auto-generated */
990 const Vector& in,
991 const Numeric& value,
992 const Verbosity&) {
993 // Note that in and out can be the same vector
994 if (&out == &in) {
995 // Out and in are the same. Just add the scalar value.
996 out += value;
997 } else {
998 // Out and in are different. We first have to copy in to out,
999 // then add the scalar value.
1000 out.resize(in.nelem());
1001 out = in;
1002 out += value;
1003 }
1004}
1005
1006/* Workspace method: Doxygen documentation will be auto-generated */
1008 const Vector& in,
1009 const Numeric& value,
1010 const Verbosity&) {
1011 // Note that in and out can be the same vector
1012 if (&out == &in) {
1013 // Out and in are the same. Just add the scalar value.
1014 out /= value;
1015 } else {
1016 // Out and in are different. We first have to copy in to out,
1017 // then add the scalar value.
1018 out.resize(in.nelem());
1019 out = in;
1020 out /= value;
1021 }
1022}
1023
1024/* Workspace method: Doxygen documentation will be auto-generated */
1026 const Vector& in,
1027 const Numeric& value,
1028 const Verbosity&) {
1029 // Note that in and out can be the same vector
1030 if (&out == &in) {
1031 // Out and in are the same. Just multiply by the scalar value.
1032 out *= value;
1033 } else {
1034 // Out and in are different. We first have to copy in to out,
1035 // then multiply by the scalar value.
1036 out.resize(in.nelem());
1037 out = in;
1038 out *= value;
1039 }
1040}
1041
1042/* Workspace method: Doxygen documentation will be auto-generated */
1044 const Vector& in,
1045 const Numeric& value,
1046 const Verbosity&) {
1047 // Note that in and out can be the same vector
1048 if (&out == &in) {
1049 // Out and in are the same. Just add the scalar value.
1050 out -= value;
1051 } else {
1052 // Out and in are different. We first have to copy in to out,
1053 // then add the scalar value.
1054 out.resize(in.nelem());
1055 out = in;
1056 out -= value;
1057 }
1058}
1059
1060/* Workspace method: Doxygen documentation will be auto-generated */
1062 const Vector& a,
1063 const Vector& b,
1064 const Verbosity&) {
1065 // b has length 1. Here we easily can avoid just adding 0.
1066 if (b.nelem() == 1) {
1067 // a and c are the same WSV
1068 if (&c == &a) {
1069 if (b[0] != 0) {
1070 c += b[0];
1071 }
1072 } else {
1073 c = a;
1074 if (b[0] != 0) {
1075 c += b[0];
1076 }
1077 }
1078 }
1079
1080 // b is a vector
1081 else if (b.nelem() == a.nelem()) {
1082 // a and c are the same WSV
1083 if (&c == &a) {
1084 c += b;
1085 } else {
1086 c = a;
1087 c += b;
1088 }
1089 }
1090
1091 else
1092 throw runtime_error(
1093 "The vector *b* must have length 1 or match *a* in length.");
1094}
1095
1096/* Workspace method: Doxygen documentation will be auto-generated */
1098 const Vector& a,
1099 const Vector& b,
1100 const Verbosity&) {
1101 // b has length 1. Here we easily can avoid just adding 0.
1102 if (b.nelem() == 1) {
1103 // a and c are the same WSV
1104 if (&c == &a) {
1105 if (b[0] != 0) {
1106 c -= b[0];
1107 }
1108 } else {
1109 c = a;
1110 if (b[0] != 0) {
1111 c -= b[0];
1112 }
1113 }
1114 }
1115
1116 // b is a vector
1117 else if (b.nelem() == a.nelem()) {
1118 // a and c are the same WSV
1119 if (&c == &a) {
1120 c -= b;
1121 } else {
1122 c = a;
1123 c -= b;
1124 }
1125 }
1126
1127 else
1128 throw runtime_error(
1129 "The vector *b* must have length 1 or match *a* in length.");
1130}
1131
1132/* Workspace method: Doxygen documentation will be auto-generated */
1134 const Vector& a,
1135 const Vector& b,
1136 const Verbosity&) {
1137 // b has length 1. Here we easily can avoid just adding 0.
1138 if (b.nelem() == 1) {
1139 // a and c are the same WSV
1140 if (&c == &a) {
1141 if (b[0] != 0) {
1142 c *= b[0];
1143 }
1144 } else {
1145 c = a;
1146 if (b[0] != 0) {
1147 c *= b[0];
1148 }
1149 }
1150 }
1151
1152 // b is a vector
1153 else if (b.nelem() == a.nelem()) {
1154 // a and c are the same WSV
1155 if (&c == &a) {
1156 c *= b;
1157 } else {
1158 c = a;
1159 c *= b;
1160 }
1161 }
1162
1163 else
1164 throw runtime_error(
1165 "The vector *b* must have length 1 or match *a* in length.");
1166}
1167
1168/* Workspace method: Doxygen documentation will be auto-generated */
1170 const Vector& a,
1171 const Vector& b,
1172 const Verbosity&) {
1173 // b has length 1. Here we easily can avoid just adding 0.
1174 if (b.nelem() == 1) {
1175 // a and c are the same WSV
1176 if (&c == &a) {
1177 if (b[0] != 0) {
1178 c /= b[0];
1179 }
1180 } else {
1181 c = a;
1182 if (b[0] != 0) {
1183 c /= b[0];
1184 }
1185 }
1186 }
1187
1188 // b is a vector
1189 else if (b.nelem() == a.nelem()) {
1190 // a and c are the same WSV
1191 if (&c == &a) {
1192 c /= b;
1193 } else {
1194 c = a;
1195 c /= b;
1196 }
1197 }
1198
1199 else
1200 throw runtime_error(
1201 "The vector *b* must have length 1 or match *a* in length.");
1202}
1203
1204/* Workspace method: Doxygen documentation will be auto-generated */
1206 const Vector& in,
1207 const Numeric& limit_low,
1208 const Numeric& limit_high,
1209 const Verbosity&) {
1210 const Index l = in.nelem();
1211 if (out.nelem() != l)
1212 out.resize(l);
1213
1214 for (Index i=0; i<l; i++) {
1215 if (in[i] < limit_low)
1216 out[i] = limit_low;
1217 else if (in[i] > limit_high)
1218 out[i] = limit_high;
1219 else
1220 out[i] = in[i];
1221 }
1222}
1223
1224/* Workspace method: Doxygen documentation will be auto-generated */
1226 const Vector& in,
1227 const Numeric& min_value,
1228 const Numeric& max_value,
1229 const Verbosity&) {
1230 const Index nin = in.nelem();
1231
1232 Index nout = 0;
1233 //
1234 for (Index i = 0; i < nin; i++) {
1235 if (in[i] >= min_value && in[i] <= max_value) {
1236 nout += 1;
1237 }
1238 }
1239
1240 // Make copy if in-vector, as it also can be the out one
1241 Vector c(in);
1242
1243 out.resize(nout);
1244
1245 nout = 0;
1246 //
1247 for (Index i = 0; i < nin; i++) {
1248 if (c[i] >= min_value && c[i] <= max_value) {
1249 out[nout] = c[i];
1250 nout += 1;
1251 }
1252 }
1253}
1254
1255/* Workspace method: Doxygen documentation will be auto-generated
1256
1257 2004-09-15 Patrick Eriksson
1258
1259 Added keyword to control if row or column is extracted.
1260
1261 2007-07-24 Stefan Buehler */
1263 // WS Generic Output:
1264 Vector& v,
1265 // WS Input:
1266 // WS Generic Input:
1267 const Matrix& m,
1268 const Index& index,
1269 // Control Parameters:
1270 const String& direction,
1271 const Verbosity&) {
1272 if (direction == "row") {
1273 if (index >= m.nrows()) {
1274 ostringstream os;
1275 os << "The index " << index << " is outside the row range of the Matrix.";
1276 throw runtime_error(os.str());
1277 }
1278
1279 v.resize(m.ncols());
1280 v = m(index, joker);
1281 } else if (direction == "column") {
1282 if (index >= m.ncols()) {
1283 ostringstream os;
1284 os << "The index " << index
1285 << " is outside the column range of the Matrix.";
1286 throw runtime_error(os.str());
1287 }
1288
1289 v.resize(m.nrows());
1290 v = m(joker, index);
1291 } else {
1292 ostringstream os;
1293 os << "Keyword *direction* must be either *row* or *column*,"
1294 << "but you gave: " << direction << ".";
1295 throw runtime_error(os.str());
1296 }
1297}
1298
1299/* Workspace method: Doxygen documentation will be auto-generated */
1300void VectorFlip(Vector& out, const Vector& in, const Verbosity&) {
1301 const Index n = in.nelem();
1302
1303 // Note that in and out can be the same vector
1304 if (&out == &in) {
1305 // Out and in are the same. A copy is needed
1306 const Vector v = in;
1307 for (Index i = 0; i < n; i++) out[i] = v[n - 1 - i];
1308 } else {
1309 // Out and in are different.
1310 out.resize(n);
1311 for (Index i = 0; i < n; i++) out[i] = in[n - 1 - i];
1312 }
1313}
1314
1315/* Workspace method: Doxygen documentation will be auto-generated */
1316void VectorInsertGridPoints( // WS Generic Output:
1317 Vector& og, // Output grid
1318 // WS Generic Input:
1319 const Vector& ingrid, // Input grid
1320 const Vector& points, // Points to insert
1321 const Verbosity& verbosity) {
1324
1325 // First make duplicates of the input vectors, in case one of them
1326 // happens to be identical to the output vector. Also, we can fool
1327 // around with these, if we want.
1328 Vector ig(ingrid);
1329 Vector p(points);
1330
1331 // Check how the input grid is sorted. If the grid is sorted in
1332 // descending order, we simply turn it around. (But don't
1333 // forget to turn it back at the end!)
1334 Index ascending; // 1=ascending, 0=descending
1335 if (is_increasing(ig)) {
1336 ascending = 1;
1337 } else if (is_decreasing(ig)) {
1338 ascending = 0;
1339
1340 // Turn grid round.
1341
1342 // Copy ig to dummy vector in reverse order:
1343 const Vector dummy = ig[Range(ig.nelem() - 1, ig.nelem(), -1)];
1344
1345 // Copy dummy back to ig vector:
1346 ig = dummy;
1347 } else {
1348 ostringstream os;
1349 os << "The input Vector must be either\n"
1350 << "strictly increasing or strictly decreasing,\n"
1351 << "but this is not the case.\n";
1352 os << "The vector contains:\n" << ig;
1353 throw runtime_error(os.str());
1354 }
1355
1356 // Sort also the vector of points to insert in increasing order:
1357 {
1358 ArrayOfIndex si; // Sorted indices
1359 get_sorted_indexes(si, p); // Get sorted p indices
1360 const Vector dummy = p; // Copy p to dummy
1361 // Copy back dummy to p in right order:
1362 for (Index j = 0; j < p.nelem(); j++) p[j] = dummy[si[j]];
1363 }
1364
1365 // The idea is to step through both ig and p, and build up the
1366 // output in a temporary array.
1368 Index iig = 0, ip = 0; // indices to ig and p
1369 Index sk = 0; // skip count
1370 while (iig < ig.nelem() && ip < p.nelem()) {
1371 if (p[ip] < ig[iig]) {
1372 x.push_back(p[ip]);
1373 ++ip;
1374 } else if (p[ip] > ig[iig]) {
1375 x.push_back(ig[iig]);
1376 ++iig;
1377 } else {
1378 out3 << " Skipping point " << p[ip] << ", which is already "
1379 << "in the original grid.\n";
1380 ++ip;
1381 ++sk;
1382 }
1383 }
1384
1385 out2 << " " << sk << " points skipped.\n";
1386
1387 // Add remaining points of either p or ig, depending on which is
1388 // longer:
1389 if (ip == p.nelem()) {
1390 // p has reached its end.
1391 while (iig < ig.nelem()) {
1392 x.push_back(ig[iig]);
1393 ++iig;
1394 }
1395 } else if (iig == ig.nelem()) {
1396 // ig has reached its end
1397 while (ip < p.nelem()) {
1398 x.push_back(p[ip]);
1399 ++ip;
1400 }
1401 } else {
1402 // We should never be here.
1403 ARTS_ASSERT(false);
1404 arts_exit();
1405 }
1406
1407 // Ok, x should now contain the new grid.
1408
1409 og.resize(x.nelem());
1410
1411 // Copy to result vector, turn around if necessary.
1412 if (ascending)
1413 for (Index i = 0; i < x.nelem(); ++i) og[i] = x[i]; // Just copy.
1414 else
1415 for (Index i = 0; i < x.nelem(); ++i)
1416 og[i] = x[x.nelem() - 1 - i]; // Copy in reverse order.
1417}
1418
1419/* Workspace method: Doxygen documentation will be auto-generated */
1421 const Numeric& start,
1422 const Numeric& stop,
1423 const Numeric& step,
1424 const Verbosity& verbosity) {
1427
1428 linspace(x, start, stop, step);
1429
1430 out2 << " Creating a linearly spaced vector.\n";
1431 out3 << " length : " << x.nelem() << "\n";
1432 out3 << " first value : " << x[0] << "\n";
1433
1434 if (x.nelem() > 1) {
1435 out3 << " step size : " << x[1] - x[0] << "\n";
1436 out3 << " last value : " << x[x.nelem() - 1] << "\n";
1437 }
1438}
1439
1440/* Workspace method: Doxygen documentation will be auto-generated */
1442 const Numeric& start,
1443 const Numeric& stop,
1444 const Numeric& step,
1445 const Verbosity& verbosity) {
1448
1449 linspace(x, log(start), log(stop), step);
1450 transform(x, exp, x);
1451
1452 out2 << " Creating a logarithmically spaced vector.\n";
1453 out3 << " length : " << x.nelem() << "\n";
1454 out3 << " first value : " << x[0] << "\n";
1455
1456 if (x.nelem() > 1) {
1457 out3 << " step size : " << x[1] - x[0] << "\n";
1458 out3 << " last value : " << x[x.nelem() - 1] << "\n";
1459 }
1460}
1461
1462/* Workspace method: Doxygen documentation will be auto-generated */
1463void VectorMatrixMultiply( // WS Generic Output:
1464 Vector& y,
1465 // WS Generic Input:
1466 const Matrix& M,
1467 const Vector& x,
1468 const Verbosity&) {
1469 // Check that dimensions are right, x must match columns of M:
1470 if (M.ncols() != x.nelem()) {
1471 ostringstream os;
1472 os << "Matrix and vector dimensions must be consistent!\n"
1473 << "Matrix.ncols() = " << M.ncols() << "\n"
1474 << "Vector.nelem() = " << x.nelem();
1475 throw runtime_error(os.str());
1476 }
1477
1478 // Temporary for the result:
1479 Vector dummy(M.nrows());
1480
1481 mult(dummy, M, x);
1482
1483 y.resize(dummy.nelem());
1484
1485 y = dummy;
1486}
1487
1488/* Workspace method: Doxygen documentation will be auto-generated */
1489void VectorSparseMultiply( // WS Generic Output:
1490 Vector& y,
1491 // WS Generic Input:
1492 const Sparse& M,
1493 const Vector& x,
1494 const Verbosity&) {
1495 // Check that dimensions are right, x must match columns of M:
1496 if (M.ncols() != x.nelem()) {
1497 ostringstream os;
1498 os << "Sparse and vector dimensions must be consistent!\n"
1499 << "Sparse.ncols() = " << M.ncols() << "\n"
1500 << "Vector.nelem() = " << x.nelem();
1501 throw runtime_error(os.str());
1502 }
1503
1504 // Temporary for the result:
1505 Vector dummy(M.nrows());
1506
1507 mult(dummy, M, x);
1508
1509 y.resize(dummy.nelem());
1510
1511 y = dummy;
1512}
1513
1514/* Workspace method: Doxygen documentation will be auto-generated */
1516 const Index& n,
1517 const Numeric& start,
1518 const Numeric& stop,
1519 const Verbosity& verbosity) {
1522
1523 if (n < 2) throw runtime_error("The number of points must be > 1.");
1524 nlinspace(x, start, stop, n);
1525
1526 out2 << " Creating a linearly spaced vector.\n";
1527 out3 << " length : " << n << "\n";
1528 out3 << " first value : " << x[0] << "\n";
1529
1530 if (x.nelem() > 1) {
1531 out3 << " step size : " << x[1] - x[0] << "\n";
1532 out3 << " last value : " << x[x.nelem() - 1] << "\n";
1533 }
1534}
1535
1536/* Workspace method: Doxygen documentation will be auto-generated */
1538 const Index& n,
1539 const String& start,
1540 const String& stop,
1541 const Verbosity&) {
1542 Vector seconds;
1543 Time t0(start), t1(stop);
1544
1545 ARTS_USER_ERROR_IF (n < 2, "The number of points must be > 1.");
1546 nlinspace(seconds, t0.Seconds(), t1.Seconds(), n);
1547
1548 x = time_vector(seconds);
1549}
1550
1551/* Workspace method: Doxygen documentation will be auto-generated */
1552void VectorNLogSpace(Vector& x,
1553 const Index& n,
1554 const Numeric& start,
1555 const Numeric& stop,
1556 const Verbosity& verbosity) {
1557 CREATE_OUT2;
1558 CREATE_OUT3;
1559
1560 if (n < 2) throw runtime_error("The number of points must be > 1.");
1561 if ((start <= 0) || (stop <= 0))
1562 throw runtime_error("Only positive numbers are allowed.");
1563
1564 nlogspace(x, start, stop, n);
1565
1566 out2 << " Creating a logarithmically spaced vector.\n";
1567 out3 << " length : " << n << "\n";
1568 out3 << " first value : " << x[0] << "\n";
1569
1570 if (x.nelem() > 1)
1571 out3 << " last value : " << x[x.nelem() - 1] << "\n";
1572}
1573
1574/* Workspace method: Doxygen documentation will be auto-generated */
1575void VectorPower(Vector& out,
1576 const Vector& in,
1577 const Numeric& value,
1578 const Verbosity&) {
1579 const Index n = in.nelem();
1580 // Note that in and out can be the same vector
1581 if (&out == &in) {
1582 // Out and in are the same.
1583 } else {
1584 out.resize(n);
1585 }
1586 for (Index i=0; i<n; i++) {
1587 out[i] = pow( in[i], value );
1588 }
1589}
1590
1591/* Workspace method: Doxygen documentation will be auto-generated */
1592void VectorReshapeMatrix(Vector& v,
1593 const Matrix& m,
1594 const String& direction,
1595 const Verbosity&) {
1596 const Index nrows = m.nrows();
1597 const Index ncols = m.ncols();
1598
1599 v.resize(nrows * ncols);
1600
1601 Index iv = 0;
1602
1603 if (direction == "column") {
1604 for (Index col = 0; col < ncols; col++) {
1605 for (Index row = 0; row < nrows; row++) {
1606 v[iv] = m(row, col);
1607 iv++;
1608 }
1609 }
1610 } else if (direction == "row") {
1611 for (Index row = 0; row < nrows; row++) {
1612 for (Index col = 0; col < ncols; col++) {
1613 v[iv] = m(row, col);
1614 iv++;
1615 }
1616 }
1617 } else {
1618 ostringstream os;
1619 os << "Keyword *direction* must be either *row* or *column*,"
1620 << "but you gave: " << direction << ".";
1621 throw runtime_error(os.str());
1622 }
1623}
1624
1625/* Workspace method: Doxygen documentation will be auto-generated */
1626void VectorSetConstant(Vector& x,
1627 const Index& n,
1628 const Numeric& value,
1629 const Verbosity& verbosity) {
1630 CREATE_OUT2;
1631 CREATE_OUT3;
1632
1633 x.resize(n);
1634 x = value;
1635
1636 out2 << " Creating a constant vector.\n";
1637 out3 << " length : " << n << "\n";
1638 out3 << " value : " << value << "\n";
1639}
1640
1641/* Workspace method: Doxygen documentation will be auto-generated */
1642void ArrayOfTimeSetConstant(ArrayOfTime& x,
1643 const Index& n,
1644 const Time& value,
1645 const Verbosity& verbosity) {
1646 CREATE_OUT2;
1647 CREATE_OUT3;
1648
1649 x.resize(n);
1650 x = value;
1651
1652 out2 << " Creating a constant vector.\n";
1653 out3 << " length : " << n << "\n";
1654 out3 << " value : " << value << "\n";
1655}
1656
1657/* Workspace method: Doxygen documentation will be auto-generated */
1658void VectorSet(Vector& x, const Vector& values, const Verbosity&) {
1659 x = values;
1660}
1661
1662/* Workspace method: Doxygen documentation will be auto-generated */
1663void Compare(const Numeric& var1,
1664 const Numeric& var2,
1665 const Numeric& maxabsdiff,
1666 const String& error_message,
1667 const String& var1name,
1668 const String& var2name,
1669 const String&,
1670 const String&,
1671 const Verbosity& verbosity) {
1672 Numeric maxdiff = var1 - var2;
1673
1674 if (std::isnan(var1) || std::isnan(var2)) {
1675 if (std::isnan(var1) && std::isnan(var2)) {
1676 maxdiff = 0;
1677 } else if (std::isnan(var1)) {
1678 ostringstream os;
1679 os << "Nan found in " << var1name << ", but there is no "
1680 << "NaN at same position in " << var2name << ".\nThis "
1681 << "is not allowed.";
1682 throw runtime_error(os.str());
1683 } else {
1684 ostringstream os;
1685 os << "Nan found in " << var2name << ", but there is no "
1686 << "NaN at same position in " << var1name << ".\nThis "
1687 << "is not allowed.";
1688 throw runtime_error(os.str());
1689 }
1690 }
1691
1692 if (abs(maxdiff) > maxabsdiff) {
1693 ostringstream os;
1694 os << var1name << "-" << var2name << " FAILED!\n";
1695 if (error_message.length()) os << error_message << "\n";
1696 os << "Max allowed deviation set to: " << maxabsdiff << endl
1697 << "but the value deviates with: " << maxdiff << endl;
1698 throw runtime_error(os.str());
1699 }
1700
1701 CREATE_OUT2;
1702 out2 << " " << var1name << "-" << var2name
1703 << " OK (maximum difference = " << maxdiff << ").\n";
1704}
1705
1706/* Workspace method: Doxygen documentation will be auto-generated */
1707void Compare(const Vector& var1,
1708 const Vector& var2,
1709 const Numeric& maxabsdiff,
1710 const String& error_message,
1711 const String& var1name,
1712 const String& var2name,
1713 const String&,
1714 const String&,
1715 const Verbosity& verbosity) {
1716 const Index n = var1.nelem();
1717
1718 if (var2.nelem() != n) {
1719 ostringstream os;
1720 os << var1name << " (" << n << ") and " << var2name << " (" << var2.nelem()
1721 << ") do not have the same size.";
1722 throw runtime_error(os.str());
1723 }
1724
1725 Numeric maxdiff = 0.0;
1726 for (Index i = 0; i < n; i++) {
1727 Numeric diff = var1[i] - var2[i];
1728
1729 if (std::isnan(var1[i]) || std::isnan(var2[i])) {
1730 if (std::isnan(var1[i]) && std::isnan(var2[i])) {
1731 diff = 0;
1732 } else if (std::isnan(var1[i])) {
1733 ostringstream os;
1734 os << "Nan found in " << var1name << ", but there is no "
1735 << "NaN at same position in " << var2name << ".\nThis "
1736 << "is not allowed.";
1737 throw runtime_error(os.str());
1738 } else {
1739 ostringstream os;
1740 os << "Nan found in " << var2name << ", but there is no "
1741 << "NaN at same position in " << var1name << ".\nThis "
1742 << "is not allowed.";
1743 throw runtime_error(os.str());
1744 }
1745 }
1746
1747 if (abs(diff) > abs(maxdiff)) {
1748 maxdiff = diff;
1749 }
1750 }
1751
1752 if (std::isnan(maxdiff) || abs(maxdiff) > maxabsdiff) {
1753 ostringstream os;
1754 os << var1name << "-" << var2name << " FAILED!\n";
1755 if (error_message.length()) os << error_message << "\n";
1756 os << "Max allowed deviation set to: " << maxabsdiff << endl
1757 << "but the vectors deviate with: " << maxdiff << endl;
1758 throw runtime_error(os.str());
1759 }
1760
1761 CREATE_OUT2;
1762 out2 << " " << var1name << "-" << var2name
1763 << " OK (maximum difference = " << maxdiff << ").\n";
1764}
1765
1766/* Workspace method: Doxygen documentation will be auto-generated */
1767void Compare(const Matrix& var1,
1768 const Matrix& var2,
1769 const Numeric& maxabsdiff,
1770 const String& error_message,
1771 const String& var1name,
1772 const String& var2name,
1773 const String&,
1774 const String&,
1775 const Verbosity& verbosity) {
1776 const Index nrows = var1.nrows();
1777 const Index ncols = var1.ncols();
1778
1779 if (var2.nrows() != nrows || var2.ncols() != ncols) {
1780 ostringstream os;
1781 os << var1name << " (" << nrows << "," << ncols << ") and " << var2name
1782 << " (" << var2.nrows() << "," << var2.ncols()
1783 << ") do not have the same size.";
1784 throw runtime_error(os.str());
1785 }
1786
1787 Numeric maxdiff = 0.0;
1788
1789 for (Index r = 0; r < nrows; r++) {
1790 for (Index c = 0; c < ncols; c++) {
1791 Numeric diff = var1(r, c) - var2(r, c);
1792
1793 if (std::isnan(var1(r, c)) || std::isnan(var2(r, c))) {
1794 if (std::isnan(var1(r, c)) && std::isnan(var2(r, c))) {
1795 diff = 0;
1796 } else if (std::isnan(var1(r, c))) {
1797 ostringstream os;
1798 os << "Nan found in " << var1name << ", but there is no "
1799 << "NaN at same position in " << var2name << ".\nThis "
1800 << "is not allowed.";
1801 throw runtime_error(os.str());
1802 } else {
1803 ostringstream os;
1804 os << "Nan found in " << var2name << ", but there is no "
1805 << "NaN at same position in " << var1name << ".\nThis "
1806 << "is not allowed.";
1807 throw runtime_error(os.str());
1808 }
1809 }
1810
1811 if (abs(diff) > abs(maxdiff)) {
1812 maxdiff = diff;
1813 }
1814 }
1815 }
1816
1817 if (abs(maxdiff) > maxabsdiff) {
1818 ostringstream os;
1819 os << var1name << "-" << var2name << " FAILED!\n";
1820 if (error_message.length()) os << error_message << "\n";
1821 os << "Max allowed deviation set to : " << maxabsdiff << endl
1822 << "but the matrices deviate with: " << maxdiff << endl;
1823 throw runtime_error(os.str());
1824 }
1825
1826 CREATE_OUT2;
1827 out2 << " " << var1name << "-" << var2name
1828 << " OK (maximum difference = " << maxdiff << ").\n";
1829}
1830
1831/* Workspace method: Doxygen documentation will be auto-generated */
1832void Compare(const Tensor3& var1,
1833 const Tensor3& var2,
1834 const Numeric& maxabsdiff,
1835 const String& error_message,
1836 const String& var1name,
1837 const String& var2name,
1838 const String&,
1839 const String&,
1840 const Verbosity& verbosity) {
1841 const Index ncols = var1.ncols();
1842 const Index nrows = var1.nrows();
1843 const Index npages = var1.npages();
1844
1845 if (var2.ncols() != ncols || var2.nrows() != nrows ||
1846 var2.npages() != npages) {
1847 ostringstream os;
1848 os << var1name << " and " << var2name << " do not have the same size.";
1849 throw runtime_error(os.str());
1850 }
1851
1852 Numeric maxdiff = 0.0;
1853
1854 for (Index c = 0; c < ncols; c++)
1855 for (Index r = 0; r < nrows; r++)
1856 for (Index p = 0; p < npages; p++) {
1857 Numeric diff = var1(p, r, c) - var2(p, r, c);
1858
1859 if (std::isnan(var1(p, r, c)) || std::isnan(var2(p, r, c))) {
1860 if (std::isnan(var1(p, r, c)) && std::isnan(var2(p, r, c))) {
1861 diff = 0;
1862 } else if (std::isnan(var1(p, r, c))) {
1863 ostringstream os;
1864 os << "Nan found in " << var1name << ", but there is no "
1865 << "NaN at same position in " << var2name << ".\nThis "
1866 << "is not allowed.";
1867 throw runtime_error(os.str());
1868 } else {
1869 ostringstream os;
1870 os << "Nan found in " << var2name << ", but there is no "
1871 << "NaN at same position in " << var1name << ".\nThis "
1872 << "is not allowed.";
1873 throw runtime_error(os.str());
1874 }
1875 }
1876
1877 if (abs(diff) > abs(maxdiff)) {
1878 maxdiff = diff;
1879 }
1880 }
1881
1882 if (abs(maxdiff) > maxabsdiff) {
1883 ostringstream os;
1884 os << var1name << "-" << var2name << " FAILED!\n";
1885 if (error_message.length()) os << error_message << "\n";
1886 os << "Max allowed deviation set to : " << maxabsdiff << endl
1887 << "but the tensors deviate with: " << maxdiff << endl;
1888 throw runtime_error(os.str());
1889 }
1890
1891 CREATE_OUT2;
1892 out2 << " " << var1name << "-" << var2name
1893 << " OK (maximum difference = " << maxdiff << ").\n";
1894}
1895
1896/* Workspace method: Doxygen documentation will be auto-generated */
1897void Compare(const Tensor4& var1,
1898 const Tensor4& var2,
1899 const Numeric& maxabsdiff,
1900 const String& error_message,
1901 const String& var1name,
1902 const String& var2name,
1903 const String&,
1904 const String&,
1905 const Verbosity& verbosity) {
1906 const Index ncols = var1.ncols();
1907 const Index nrows = var1.nrows();
1908 const Index npages = var1.npages();
1909 const Index nbooks = var1.nbooks();
1910
1911 if (var2.ncols() != ncols || var2.nrows() != nrows ||
1912 var2.npages() != npages || var2.nbooks() != nbooks) {
1913 ostringstream os;
1914 os << var1name << " and " << var2name << " do not have the same size.";
1915 throw runtime_error(os.str());
1916 }
1917
1918 Numeric maxdiff = 0.0;
1919
1920 for (Index c = 0; c < ncols; c++)
1921 for (Index r = 0; r < nrows; r++)
1922 for (Index p = 0; p < npages; p++)
1923 for (Index b = 0; b < nbooks; b++) {
1924 Numeric diff = var1(b, p, r, c) - var2(b, p, r, c);
1925
1926 if (std::isnan(var1(b, p, r, c)) || std::isnan(var2(b, p, r, c))) {
1927 if (std::isnan(var1(b, p, r, c)) && std::isnan(var2(b, p, r, c))) {
1928 diff = 0;
1929 } else if (std::isnan(var1(b, p, r, c))) {
1930 ostringstream os;
1931 os << "Nan found in " << var1name << ", but there is no "
1932 << "NaN at same position in " << var2name << ".\nThis "
1933 << "is not allowed.";
1934 throw runtime_error(os.str());
1935 } else {
1936 ostringstream os;
1937 os << "Nan found in " << var2name << ", but there is no "
1938 << "NaN at same position in " << var1name << ".\nThis "
1939 << "is not allowed.";
1940 throw runtime_error(os.str());
1941 }
1942 }
1943
1944 if (abs(diff) > abs(maxdiff)) {
1945 maxdiff = diff;
1946 }
1947 }
1948
1949 if (abs(maxdiff) > maxabsdiff) {
1950 ostringstream os;
1951 os << var1name << "-" << var2name << " FAILED!\n";
1952 if (error_message.length()) os << error_message << "\n";
1953 os << "Max allowed deviation set to : " << maxabsdiff << endl
1954 << "but the tensors deviate with: " << maxdiff << endl;
1955 throw runtime_error(os.str());
1956 }
1957
1958 CREATE_OUT2;
1959 out2 << " " << var1name << "-" << var2name
1960 << " OK (maximum difference = " << maxdiff << ").\n";
1961}
1962
1963/* Workspace method: Doxygen documentation will be auto-generated */
1964void Compare(const Tensor5& var1,
1965 const Tensor5& var2,
1966 const Numeric& maxabsdiff,
1967 const String& error_message,
1968 const String& var1name,
1969 const String& var2name,
1970 const String&,
1971 const String&,
1972 const Verbosity& verbosity) {
1973 const Index ncols = var1.ncols();
1974 const Index nrows = var1.nrows();
1975 const Index npages = var1.npages();
1976 const Index nbooks = var1.nbooks();
1977 const Index nshelves = var1.nshelves();
1978
1979 if (var2.ncols() != ncols || var2.nrows() != nrows ||
1980 var2.npages() != npages || var2.nbooks() != nbooks ||
1981 var2.nshelves() != nshelves) {
1982 ostringstream os;
1983 os << var1name << " and " << var2name << " do not have the same size.";
1984 throw runtime_error(os.str());
1985 }
1986
1987 Numeric maxdiff = 0.0;
1988
1989 for (Index c = 0; c < ncols; c++)
1990 for (Index r = 0; r < nrows; r++)
1991 for (Index p = 0; p < npages; p++)
1992 for (Index b = 0; b < nbooks; b++)
1993 for (Index s = 0; s < nshelves; s++) {
1994 Numeric diff = var1(s, b, p, r, c) - var2(s, b, p, r, c);
1995
1996 if (std::isnan(var1(s, b, p, r, c)) ||
1997 std::isnan(var2(s, b, p, r, c))) {
1998 if (std::isnan(var1(s, b, p, r, c)) &&
1999 std::isnan(var2(s, b, p, r, c))) {
2000 diff = 0;
2001 } else if (std::isnan(var1(s, b, p, r, c))) {
2002 ostringstream os;
2003 os << "Nan found in " << var1name << ", but there is no "
2004 << "NaN at same position in " << var2name << ".\nThis "
2005 << "is not allowed.";
2006 throw runtime_error(os.str());
2007 } else {
2008 ostringstream os;
2009 os << "Nan found in " << var2name << ", but there is no "
2010 << "NaN at same position in " << var1name << ".\nThis "
2011 << "is not allowed.";
2012 throw runtime_error(os.str());
2013 }
2014 }
2015
2016 if (abs(diff) > abs(maxdiff)) {
2017 maxdiff = diff;
2018 }
2019 }
2020
2021 if (abs(maxdiff) > maxabsdiff) {
2022 ostringstream os;
2023 os << var1name << "-" << var2name << " FAILED!\n";
2024 if (error_message.length()) os << error_message << "\n";
2025 os << "Max allowed deviation set to : " << maxabsdiff << endl
2026 << "but the tensors deviate with: " << maxdiff << endl;
2027 throw runtime_error(os.str());
2028 }
2029
2030 CREATE_OUT2;
2031 out2 << " " << var1name << "-" << var2name
2032 << " OK (maximum difference = " << maxdiff << ").\n";
2033}
2034
2035/* Workspace method: Doxygen documentation will be auto-generated */
2036void Compare(const Tensor7& var1,
2037 const Tensor7& var2,
2038 const Numeric& maxabsdiff,
2039 const String& error_message,
2040 const String& var1name,
2041 const String& var2name,
2042 const String&,
2043 const String&,
2044 const Verbosity& verbosity) {
2045 const Index ncols = var1.ncols();
2046 const Index nrows = var1.nrows();
2047 const Index npages = var1.npages();
2048 const Index nbooks = var1.nbooks();
2049 const Index nshelves = var1.nshelves();
2050 const Index nvitrines = var1.nvitrines();
2051 const Index nlibraries = var1.nlibraries();
2052
2053 if (var2.ncols() != ncols || var2.nrows() != nrows ||
2054 var2.npages() != npages || var2.nbooks() != nbooks ||
2055 var2.nshelves() != nshelves || var2.nvitrines() != nvitrines ||
2056 var2.nlibraries() != nlibraries) {
2057 ostringstream os;
2058 os << var1name << " and " << var2name << " do not have the same size.";
2059 throw runtime_error(os.str());
2060 }
2061
2062 Numeric maxdiff = 0.0;
2063
2064 for (Index c = 0; c < ncols; c++)
2065 for (Index r = 0; r < nrows; r++)
2066 for (Index p = 0; p < npages; p++)
2067 for (Index b = 0; b < nbooks; b++)
2068 for (Index s = 0; s < nshelves; s++)
2069 for (Index v = 0; v < nvitrines; v++)
2070 for (Index l = 0; l < nlibraries; l++) {
2071 Numeric diff =
2072 var1(l, v, s, b, p, r, c) - var2(l, v, s, b, p, r, c);
2073
2074 if (std::isnan(var1(l, v, s, b, p, r, c)) ||
2075 std::isnan(var2(l, v, s, b, p, r, c))) {
2076 if (std::isnan(var1(l, v, s, b, p, r, c)) &&
2077 std::isnan(var2(l, v, s, b, p, r, c))) {
2078 diff = 0;
2079 } else if (std::isnan(var1(l, v, s, b, p, r, c))) {
2080 ostringstream os;
2081 os << "Nan found in " << var1name << ", but there is no "
2082 << "NaN at same position in " << var2name << ".\nThis "
2083 << "is not allowed.";
2084 throw runtime_error(os.str());
2085 } else {
2086 ostringstream os;
2087 os << "Nan found in " << var2name << ", but there is no "
2088 << "NaN at same position in " << var1name << ".\nThis "
2089 << "is not allowed.";
2090 throw runtime_error(os.str());
2091 }
2092 }
2093
2094 if (abs(diff) > abs(maxdiff)) {
2095 maxdiff = diff;
2096 }
2097 }
2098
2099 if (abs(maxdiff) > maxabsdiff) {
2100 ostringstream os;
2101 os << var1name << "-" << var2name << " FAILED!\n";
2102 if (error_message.length()) os << error_message << "\n";
2103 os << "Max allowed deviation set to : " << maxabsdiff << endl
2104 << "but the tensors deviate with: " << maxdiff << endl;
2105 throw runtime_error(os.str());
2106 }
2107
2108 CREATE_OUT2;
2109 out2 << " " << var1name << "-" << var2name
2110 << " OK (maximum difference = " << maxdiff << ").\n";
2111}
2112
2113/* Workspace method: Doxygen documentation will be auto-generated */
2114void Compare(const ArrayOfVector& var1,
2115 const ArrayOfVector& var2,
2116 const Numeric& maxabsdiff,
2117 const String& error_message,
2118 const String& var1name,
2119 const String& var2name,
2120 const String&,
2121 const String&,
2122 const Verbosity& verbosity) {
2123 if (var1.nelem() != var2.nelem()) {
2124 ostringstream os;
2125 os << "The two arrays do not have the same size." << endl
2126 << var1name << " nelem: " << var1.nelem() << endl
2127 << var2name << " nelem: " << var2.nelem() << endl;
2128 throw runtime_error(os.str());
2129 }
2130
2131 bool failed = false;
2132 ostringstream fail_msg;
2133 for (Index i = 0; i < var1.nelem(); i++) {
2134 try {
2135 ostringstream vn1, vn2;
2136 vn1 << var1name << "[" << i << "]";
2137 vn2 << var2name << "[" << i << "]";
2138 Compare(var1[i],
2139 var2[i],
2140 maxabsdiff,
2141 error_message,
2142 vn1.str(),
2143 vn2.str(),
2144 "",
2145 "",
2146 verbosity);
2147 } catch (const std::runtime_error& e) {
2148 failed = true;
2149 fail_msg << endl
2150 << e.what() << endl
2151 << "Mismatch at array index: " << i << endl;
2152 }
2153 }
2154
2155 if (failed) throw runtime_error(fail_msg.str());
2156}
2157
2158/* Workspace method: Doxygen documentation will be auto-generated */
2159void Compare(const ArrayOfMatrix& var1,
2160 const ArrayOfMatrix& var2,
2161 const Numeric& maxabsdiff,
2162 const String& error_message,
2163 const String& var1name,
2164 const String& var2name,
2165 const String&,
2166 const String&,
2167 const Verbosity& verbosity) {
2168 if (var1.nelem() != var2.nelem()) {
2169 ostringstream os;
2170 os << "The two arrays do not have the same size." << endl
2171 << var1name << " nelem: " << var1.nelem() << endl
2172 << var2name << " nelem: " << var2.nelem() << endl;
2173 throw runtime_error(os.str());
2174 }
2175
2176 bool failed = false;
2177 ostringstream fail_msg;
2178 for (Index i = 0; i < var1.nelem(); i++) {
2179 try {
2180 ostringstream vn1, vn2;
2181 vn1 << var1name << "[" << i << "]";
2182 vn2 << var2name << "[" << i << "]";
2183 Compare(var1[i],
2184 var2[i],
2185 maxabsdiff,
2186 error_message,
2187 vn1.str(),
2188 vn2.str(),
2189 "",
2190 "",
2191 verbosity);
2192 } catch (const std::runtime_error& e) {
2193 failed = true;
2194 fail_msg << endl
2195 << e.what() << endl
2196 << "Mismatch at array index: " << i << endl;
2197 }
2198 }
2199
2200 if (failed) throw runtime_error(fail_msg.str());
2201}
2202
2203/* Workspace method: Doxygen documentation will be auto-generated */
2204void Compare(const ArrayOfTensor7& var1,
2205 const ArrayOfTensor7& var2,
2206 const Numeric& maxabsdiff,
2207 const String& error_message,
2208 const String& var1name,
2209 const String& var2name,
2210 const String&,
2211 const String&,
2212 const Verbosity& verbosity) {
2213 if (var1.nelem() != var2.nelem()) {
2214 ostringstream os;
2215 os << "The two arrays do not have the same size." << endl
2216 << var1name << " nelem: " << var1.nelem() << endl
2217 << var2name << " nelem: " << var2.nelem() << endl;
2218 throw runtime_error(os.str());
2219 }
2220
2221 bool failed = false;
2222 ostringstream fail_msg;
2223 for (Index i = 0; i < var1.nelem(); i++) {
2224 try {
2225 ostringstream vn1, vn2;
2226 vn1 << var1name << "[" << i << "]";
2227 vn2 << var2name << "[" << i << "]";
2228 Compare(var1[i],
2229 var2[i],
2230 maxabsdiff,
2231 error_message,
2232 vn1.str(),
2233 vn2.str(),
2234 "",
2235 "",
2236 verbosity);
2237 } catch (const std::runtime_error& e) {
2238 failed = true;
2239 fail_msg << endl
2240 << e.what() << endl
2241 << "Mismatch at array index: " << i << endl;
2242 }
2243 }
2244
2245 if (failed) throw runtime_error(fail_msg.str());
2246}
2247
2248/* Workspace method: Doxygen documentation will be auto-generated */
2249void Compare(const GriddedField3& var1,
2250 const GriddedField3& var2,
2251 const Numeric& maxabsdiff,
2252 const String& error_message,
2253 const String& var1name,
2254 const String& var2name,
2255 const String&,
2256 const String&,
2257 const Verbosity& verbosity) {
2258 for (Index i = 0; i < var1.get_dim(); i++) {
2259 if (var1.get_grid_size(i) != var2.get_grid_size(i)) {
2260 ostringstream os;
2261 os << var1name << " and " << var2name << " grid " << i
2262 << " do not have the same size: " << var1.get_grid_size(i)
2263 << " != " << var2.get_grid_size(i);
2264 throw runtime_error(os.str());
2265 }
2266 if (var1.get_grid_name(i) != var2.get_grid_name(i)) {
2267 ostringstream os;
2268 os << var1name << " and " << var2name << " grid " << i
2269 << " do not have the same name: " << var1.get_grid_name(i)
2270 << " != " << var2.get_grid_name(i);
2271 throw runtime_error(os.str());
2272 }
2273 }
2274
2275 Compare(var1.data,
2276 var2.data,
2277 maxabsdiff,
2278 error_message,
2279 var1name,
2280 var2name,
2281 "",
2282 "",
2283 verbosity);
2284}
2285
2286/* Workspace method: Doxygen documentation will be auto-generated */
2287void Compare(const Sparse& var1,
2288 const Sparse& var2,
2289 const Numeric& maxabsdiff,
2290 const String& error_message,
2291 const String& var1name,
2292 const String& var2name,
2293 const String&,
2294 const String&,
2295 const Verbosity& verbosity) {
2296 const Index nrows = var1.nrows();
2297 const Index ncols = var1.ncols();
2298
2299 if (var2.nrows() != nrows || var2.ncols() != ncols) {
2300 ostringstream os;
2301 os << var1name << " (" << nrows << "," << ncols << ") and " << var2name
2302 << " (" << var2.nrows() << "," << var2.ncols()
2303 << ") do not have the same size.";
2304 throw runtime_error(os.str());
2305 }
2306
2307 Numeric maxdiff = 0.0;
2308
2309 for (Index r = 0; r < nrows; r++) {
2310 for (Index c = 0; c < ncols; c++) {
2311 Numeric diff = var1(r, c) - var2(r, c);
2312
2313 if (std::isnan(var1(r, c)) || std::isnan(var2(r, c))) {
2314 if (std::isnan(var1(r, c)) && std::isnan(var2(r, c))) {
2315 diff = 0;
2316 } else if (std::isnan(var1(r, c))) {
2317 ostringstream os;
2318 os << "Nan found in " << var1name << ", but there is no "
2319 << "NaN at same position in " << var2name << ".\nThis "
2320 << "is not allowed.";
2321 throw runtime_error(os.str());
2322 } else {
2323 ostringstream os;
2324 os << "Nan found in " << var2name << ", but there is no "
2325 << "NaN at same position in " << var1name << ".\nThis "
2326 << "is not allowed.";
2327 throw runtime_error(os.str());
2328 }
2329 }
2330
2331 if (abs(diff) > abs(maxdiff)) {
2332 maxdiff = diff;
2333 }
2334 }
2335 }
2336
2337 if (abs(maxdiff) > maxabsdiff) {
2338 ostringstream os;
2339 os << var1name << "-" << var2name << " FAILED!\n";
2340 if (error_message.length()) os << error_message << "\n";
2341 os << "Max allowed deviation set to : " << maxabsdiff << endl
2342 << "but the matrices deviate with: " << maxdiff << endl;
2343 throw runtime_error(os.str());
2344 }
2345
2346 CREATE_OUT2;
2347 out2 << " " << var1name << "-" << var2name
2348 << " OK (maximum difference = " << maxdiff << ").\n";
2349}
2350
2351/* Workspace method: Doxygen documentation will be auto-generated */
2352void Compare(const SingleScatteringData& var1,
2353 const SingleScatteringData& var2,
2354 const Numeric& maxabsdiff,
2355 const String& error_message,
2356 const String& var1name,
2357 const String& var2name,
2358 const String&,
2359 const String&,
2360 const Verbosity& verbosity) {
2361 if (var1.ptype != var2.ptype) {
2362 std::ostringstream os;
2363 os << "The particle types don't match: " << std::endl
2364 << var1name << " = " << PTypeToString(var1.ptype) << ", " << var2name
2365 << " = " << PTypeToString(var2.ptype) << std::endl;
2366 throw std::runtime_error(os.str());
2367 }
2368 Compare(var1.f_grid,
2369 var2.f_grid,
2370 maxabsdiff,
2371 error_message,
2372 var1name + ".f_grid",
2373 var2name + ".f_grid",
2374 "",
2375 "",
2376 verbosity);
2377 Compare(var1.T_grid,
2378 var2.T_grid,
2379 maxabsdiff,
2380 error_message,
2381 var1name + ".T_grid",
2382 var2name + ".T_grid",
2383 "",
2384 "",
2385 verbosity);
2386 Compare(var1.za_grid,
2387 var2.za_grid,
2388 maxabsdiff,
2389 error_message,
2390 var1name + ".za_grid",
2391 var2name + ".za_grid",
2392 "",
2393 "",
2394 verbosity);
2395 Compare(var1.aa_grid,
2396 var2.aa_grid,
2397 maxabsdiff,
2398 error_message,
2399 var1name + ".aa_grid",
2400 var2name + ".aa_grid",
2401 "",
2402 "",
2403 verbosity);
2404 Compare(var1.pha_mat_data,
2405 var2.pha_mat_data,
2406 maxabsdiff,
2407 error_message,
2408 var1name + ".pha_mat_data",
2409 var2name + ".pha_mat_data",
2410 "",
2411 "",
2412 verbosity);
2413 Compare(var1.ext_mat_data,
2414 var2.ext_mat_data,
2415 maxabsdiff,
2416 error_message,
2417 var1name + ".ext_mat_data",
2418 var2name + ".ext_mat_data",
2419 "",
2420 "",
2421 verbosity);
2422 Compare(var1.abs_vec_data,
2423 var2.abs_vec_data,
2424 maxabsdiff,
2425 error_message,
2426 var1name + ".abs_vec_data",
2427 var2name + ".abs_vec_data",
2428 "",
2429 "",
2430 verbosity);
2431}
2432
2433inline void _cr_internal_(const Numeric& var1,
2434 const Numeric& var2,
2435 const Numeric& maxabsreldiff,
2436 const String& error_message,
2437 const String& var1name,
2438 const String& var2name,
2439 const String&,
2440 const String&,
2441 const Verbosity&) {
2442 if (var1 not_eq 0. and var2 not_eq 0.) {
2443 const Numeric absreldiff = abs(var1 / var2 - 1);
2444 if (absreldiff > maxabsreldiff) {
2445 ostringstream os;
2446 os << var1name << "-" << var2name << " FAILED!\n";
2447 if (error_message.length()) os << error_message << "\n";
2448 os << "Max allowed deviation set to: " << maxabsreldiff * 100.0 << "%"
2449 << endl
2450 << "but the input deviate with: " << absreldiff * 100.0 << "%\n"
2451 << "If you compare non-scalar variables, the reported deviation is\n"
2452 << "the first one found violating the criterion. The maximum\n"
2453 << "difference can be higher.\n";
2454 throw runtime_error(os.str());
2455 }
2456 }
2457}
2458
2459inline void _cr_internal_(const ConstVectorView var1,
2460 const ConstVectorView var2,
2461 const Numeric& maxabsreldiff,
2462 const String& error_message,
2463 const String& var1name,
2464 const String& var2name,
2465 const String&,
2466 const String&,
2467 const Verbosity& verbosity) {
2468 const Index n = var1.nelem();
2469 if (var2.nelem() not_eq n)
2470 throw std::runtime_error("Cannot compare variables of different size");
2471 for (Index i = 0; i < n; i++)
2472 _cr_internal_(var1[i],
2473 var2[i],
2474 maxabsreldiff,
2475 error_message,
2476 var1name,
2477 var2name,
2478 "",
2479 "",
2480 verbosity);
2481}
2482
2483inline void _cr_internal_(const ConstMatrixView var1,
2484 const ConstMatrixView var2,
2485 const Numeric& maxabsreldiff,
2486 const String& error_message,
2487 const String& var1name,
2488 const String& var2name,
2489 const String&,
2490 const String&,
2491 const Verbosity& verbosity) {
2492 const Index n = var1.nrows();
2493 if (var2.nrows() not_eq n)
2494 throw std::runtime_error("Cannot compare variables of different size");
2495 for (Index i = 0; i < n; i++)
2496 _cr_internal_(var1(i, joker),
2497 var2(i, joker),
2498 maxabsreldiff,
2499 error_message,
2500 var1name,
2501 var2name,
2502 "",
2503 "",
2504 verbosity);
2505}
2506
2507inline void _cr_internal_(const ConstTensor3View var1,
2508 const ConstTensor3View var2,
2509 const Numeric& maxabsreldiff,
2510 const String& error_message,
2511 const String& var1name,
2512 const String& var2name,
2513 const String&,
2514 const String&,
2515 const Verbosity& verbosity) {
2516 const Index n = var1.npages();
2517 if (var2.npages() not_eq n)
2518 throw std::runtime_error("Cannot compare variables of different size");
2519 for (Index i = 0; i < n; i++)
2520 _cr_internal_(var1(i, joker, joker),
2521 var2(i, joker, joker),
2522 maxabsreldiff,
2523 error_message,
2524 var1name,
2525 var2name,
2526 "",
2527 "",
2528 verbosity);
2529}
2530
2531inline void _cr_internal_(const ConstTensor4View var1,
2532 const ConstTensor4View var2,
2533 const Numeric& maxabsreldiff,
2534 const String& error_message,
2535 const String& var1name,
2536 const String& var2name,
2537 const String&,
2538 const String&,
2539 const Verbosity& verbosity) {
2540 const Index n = var1.nbooks();
2541 if (var2.nbooks() not_eq n)
2542 throw std::runtime_error("Cannot compare variables of different size");
2543 for (Index i = 0; i < n; i++)
2544 _cr_internal_(var1(i, joker, joker, joker),
2545 var2(i, joker, joker, joker),
2546 maxabsreldiff,
2547 error_message,
2548 var1name,
2549 var2name,
2550 "",
2551 "",
2552 verbosity);
2553}
2554
2555inline void _cr_internal_(const ConstTensor5View var1,
2556 const ConstTensor5View var2,
2557 const Numeric& maxabsreldiff,
2558 const String& error_message,
2559 const String& var1name,
2560 const String& var2name,
2561 const String&,
2562 const String&,
2563 const Verbosity& verbosity) {
2564 const Index n = var1.nshelves();
2565 if (var2.nshelves() not_eq n)
2566 throw std::runtime_error("Cannot compare variables of different size");
2567 for (Index i = 0; i < n; i++)
2568 _cr_internal_(var1(i, joker, joker, joker, joker),
2569 var2(i, joker, joker, joker, joker),
2570 maxabsreldiff,
2571 error_message,
2572 var1name,
2573 var2name,
2574 "",
2575 "",
2576 verbosity);
2577}
2578
2579inline void _cr_internal_(const ConstTensor6View var1,
2580 const ConstTensor6View var2,
2581 const Numeric& maxabsreldiff,
2582 const String& error_message,
2583 const String& var1name,
2584 const String& var2name,
2585 const String&,
2586 const String&,
2587 const Verbosity& verbosity) {
2588 const Index n = var1.nvitrines();
2589 if (var2.nvitrines() not_eq n)
2590 throw std::runtime_error("Cannot compare variables of different size");
2591 for (Index i = 0; i < n; i++)
2592 _cr_internal_(var1(i, joker, joker, joker, joker, joker),
2593 var2(i, joker, joker, joker, joker, joker),
2594 maxabsreldiff,
2595 error_message,
2596 var1name,
2597 var2name,
2598 "",
2599 "",
2600 verbosity);
2601}
2602
2603inline void _cr_internal_(const ConstTensor7View var1,
2604 const ConstTensor7View var2,
2605 const Numeric& maxabsreldiff,
2606 const String& error_message,
2607 const String& var1name,
2608 const String& var2name,
2609 const String&,
2610 const String&,
2611 const Verbosity& verbosity) {
2612 const Index n = var1.nlibraries();
2613 if (var2.nlibraries() not_eq n)
2614 throw std::runtime_error("Cannot compare variables of different size");
2615 for (Index i = 0; i < n; i++)
2616 _cr_internal_(var1(i, joker, joker, joker, joker, joker, joker),
2617 var2(i, joker, joker, joker, joker, joker, joker),
2618 maxabsreldiff,
2619 error_message,
2620 var1name,
2621 var2name,
2622 "",
2623 "",
2624 verbosity);
2625}
2626
2627inline void _cr_internal_(const PropagationMatrix& var1,
2628 const PropagationMatrix& var2,
2629 const Numeric& maxabsreldiff,
2630 const String& error_message,
2631 const String& var1name,
2632 const String& var2name,
2633 const String&,
2634 const String&,
2635 const Verbosity& verbosity) {
2636 _cr_internal_(var1.Data(),
2637 var2.Data(),
2638 maxabsreldiff,
2639 error_message,
2640 var1name,
2641 var2name,
2642 "",
2643 "",
2644 verbosity);
2645}
2646
2647inline void _cr_internal_(const StokesVector& var1,
2648 const StokesVector& var2,
2649 const Numeric& maxabsreldiff,
2650 const String& error_message,
2651 const String& var1name,
2652 const String& var2name,
2653 const String&,
2654 const String&,
2655 const Verbosity& verbosity) {
2656 _cr_internal_(var1.Data(),
2657 var2.Data(),
2658 maxabsreldiff,
2659 error_message,
2660 var1name,
2661 var2name,
2662 "",
2663 "",
2664 verbosity);
2665}
2666
2667template <class T>
2668inline void _cr_internal_(const Array<T>& var1,
2669 const Array<T>& var2,
2670 const Numeric& maxabsreldiff,
2671 const String& error_message,
2672 const String& var1name,
2673 const String& var2name,
2674 const String&,
2675 const String&,
2676 const Verbosity& verbosity) {
2677 const Index n = var1.nelem();
2678 if (var2.nelem() not_eq n)
2679 throw std::runtime_error("Cannot compare arrays of different length");
2680 for (Index i = 0; i < n; i++)
2681 _cr_internal_(var1[i],
2682 var2[i],
2683 maxabsreldiff,
2684 error_message,
2685 var1name,
2686 var2name,
2687 "",
2688 "",
2689 verbosity);
2690}
2691
2692/* Workspace method: Doxygen documentation will be auto-generated */
2693void CompareRelative(const Numeric& var1,
2694 const Numeric& var2,
2695 const Numeric& maxabsreldiff,
2696 const String& error_message,
2697 const String& var1name,
2698 const String& var2name,
2699 const String&,
2700 const String&,
2701 const Verbosity& verbosity) {
2702 _cr_internal_(var1,
2703 var2,
2704 maxabsreldiff,
2705 error_message,
2706 var1name,
2707 var2name,
2708 "",
2709 "",
2710 verbosity);
2711}
2712void CompareRelative(const Vector& var1,
2713 const Vector& var2,
2714 const Numeric& maxabsreldiff,
2715 const String& error_message,
2716 const String& var1name,
2717 const String& var2name,
2718 const String&,
2719 const String&,
2720 const Verbosity& verbosity) {
2721 _cr_internal_(var1,
2722 var2,
2723 maxabsreldiff,
2724 error_message,
2725 var1name,
2726 var2name,
2727 "",
2728 "",
2729 verbosity);
2730}
2731void CompareRelative(const Matrix& var1,
2732 const Matrix& var2,
2733 const Numeric& maxabsreldiff,
2734 const String& error_message,
2735 const String& var1name,
2736 const String& var2name,
2737 const String&,
2738 const String&,
2739 const Verbosity& verbosity) {
2740 _cr_internal_(var1,
2741 var2,
2742 maxabsreldiff,
2743 error_message,
2744 var1name,
2745 var2name,
2746 "",
2747 "",
2748 verbosity);
2749}
2750void CompareRelative(const Tensor3& var1,
2751 const Tensor3& var2,
2752 const Numeric& maxabsreldiff,
2753 const String& error_message,
2754 const String& var1name,
2755 const String& var2name,
2756 const String&,
2757 const String&,
2758 const Verbosity& verbosity) {
2759 _cr_internal_(var1,
2760 var2,
2761 maxabsreldiff,
2762 error_message,
2763 var1name,
2764 var2name,
2765 "",
2766 "",
2767 verbosity);
2768}
2769void CompareRelative(const Tensor4& var1,
2770 const Tensor4& var2,
2771 const Numeric& maxabsreldiff,
2772 const String& error_message,
2773 const String& var1name,
2774 const String& var2name,
2775 const String&,
2776 const String&,
2777 const Verbosity& verbosity) {
2778 _cr_internal_(var1,
2779 var2,
2780 maxabsreldiff,
2781 error_message,
2782 var1name,
2783 var2name,
2784 "",
2785 "",
2786 verbosity);
2787}
2788void CompareRelative(const Tensor5& var1,
2789 const Tensor5& var2,
2790 const Numeric& maxabsreldiff,
2791 const String& error_message,
2792 const String& var1name,
2793 const String& var2name,
2794 const String&,
2795 const String&,
2796 const Verbosity& verbosity) {
2797 _cr_internal_(var1,
2798 var2,
2799 maxabsreldiff,
2800 error_message,
2801 var1name,
2802 var2name,
2803 "",
2804 "",
2805 verbosity);
2806}
2807void CompareRelative(const Tensor6& var1,
2808 const Tensor6& var2,
2809 const Numeric& maxabsreldiff,
2810 const String& error_message,
2811 const String& var1name,
2812 const String& var2name,
2813 const String&,
2814 const String&,
2815 const Verbosity& verbosity) {
2816 _cr_internal_(var1,
2817 var2,
2818 maxabsreldiff,
2819 error_message,
2820 var1name,
2821 var2name,
2822 "",
2823 "",
2824 verbosity);
2825}
2826void CompareRelative(const Tensor7& var1,
2827 const Tensor7& var2,
2828 const Numeric& maxabsreldiff,
2829 const String& error_message,
2830 const String& var1name,
2831 const String& var2name,
2832 const String&,
2833 const String&,
2834 const Verbosity& verbosity) {
2835 _cr_internal_(var1,
2836 var2,
2837 maxabsreldiff,
2838 error_message,
2839 var1name,
2840 var2name,
2841 "",
2842 "",
2843 verbosity);
2844}
2845void CompareRelative(const ArrayOfVector& var1,
2846 const ArrayOfVector& var2,
2847 const Numeric& maxabsreldiff,
2848 const String& error_message,
2849 const String& var1name,
2850 const String& var2name,
2851 const String&,
2852 const String&,
2853 const Verbosity& verbosity) {
2854 _cr_internal_(var1,
2855 var2,
2856 maxabsreldiff,
2857 error_message,
2858 var1name,
2859 var2name,
2860 "",
2861 "",
2862 verbosity);
2863}
2864void CompareRelative(const ArrayOfMatrix& var1,
2865 const ArrayOfMatrix& var2,
2866 const Numeric& maxabsreldiff,
2867 const String& error_message,
2868 const String& var1name,
2869 const String& var2name,
2870 const String&,
2871 const String&,
2872 const Verbosity& verbosity) {
2873 _cr_internal_(var1,
2874 var2,
2875 maxabsreldiff,
2876 error_message,
2877 var1name,
2878 var2name,
2879 "",
2880 "",
2881 verbosity);
2882}
2883void CompareRelative(const ArrayOfTensor3& var1,
2884 const ArrayOfTensor3& var2,
2885 const Numeric& maxabsreldiff,
2886 const String& error_message,
2887 const String& var1name,
2888 const String& var2name,
2889 const String&,
2890 const String&,
2891 const Verbosity& verbosity) {
2892 _cr_internal_(var1,
2893 var2,
2894 maxabsreldiff,
2895 error_message,
2896 var1name,
2897 var2name,
2898 "",
2899 "",
2900 verbosity);
2901}
2902void CompareRelative(const ArrayOfTensor4& var1,
2903 const ArrayOfTensor4& var2,
2904 const Numeric& maxabsreldiff,
2905 const String& error_message,
2906 const String& var1name,
2907 const String& var2name,
2908 const String&,
2909 const String&,
2910 const Verbosity& verbosity) {
2911 _cr_internal_(var1,
2912 var2,
2913 maxabsreldiff,
2914 error_message,
2915 var1name,
2916 var2name,
2917 "",
2918 "",
2919 verbosity);
2920}
2921void CompareRelative(const ArrayOfTensor5& var1,
2922 const ArrayOfTensor5& var2,
2923 const Numeric& maxabsreldiff,
2924 const String& error_message,
2925 const String& var1name,
2926 const String& var2name,
2927 const String&,
2928 const String&,
2929 const Verbosity& verbosity) {
2930 _cr_internal_(var1,
2931 var2,
2932 maxabsreldiff,
2933 error_message,
2934 var1name,
2935 var2name,
2936 "",
2937 "",
2938 verbosity);
2939}
2940void CompareRelative(const ArrayOfTensor6& var1,
2941 const ArrayOfTensor6& var2,
2942 const Numeric& maxabsreldiff,
2943 const String& error_message,
2944 const String& var1name,
2945 const String& var2name,
2946 const String&,
2947 const String&,
2948 const Verbosity& verbosity) {
2949 _cr_internal_(var1,
2950 var2,
2951 maxabsreldiff,
2952 error_message,
2953 var1name,
2954 var2name,
2955 "",
2956 "",
2957 verbosity);
2958}
2959void CompareRelative(const ArrayOfTensor7& var1,
2960 const ArrayOfTensor7& var2,
2961 const Numeric& maxabsreldiff,
2962 const String& error_message,
2963 const String& var1name,
2964 const String& var2name,
2965 const String&,
2966 const String&,
2967 const Verbosity& verbosity) {
2968 _cr_internal_(var1,
2969 var2,
2970 maxabsreldiff,
2971 error_message,
2972 var1name,
2973 var2name,
2974 "",
2975 "",
2976 verbosity);
2977}
2978void CompareRelative(const ArrayOfArrayOfVector& var1,
2979 const ArrayOfArrayOfVector& var2,
2980 const Numeric& maxabsreldiff,
2981 const String& error_message,
2982 const String& var1name,
2983 const String& var2name,
2984 const String&,
2985 const String&,
2986 const Verbosity& verbosity) {
2987 _cr_internal_(var1,
2988 var2,
2989 maxabsreldiff,
2990 error_message,
2991 var1name,
2992 var2name,
2993 "",
2994 "",
2995 verbosity);
2996}
2997void CompareRelative(const ArrayOfArrayOfMatrix& var1,
2998 const ArrayOfArrayOfMatrix& var2,
2999 const Numeric& maxabsreldiff,
3000 const String& error_message,
3001 const String& var1name,
3002 const String& var2name,
3003 const String&,
3004 const String&,
3005 const Verbosity& verbosity) {
3006 _cr_internal_(var1,
3007 var2,
3008 maxabsreldiff,
3009 error_message,
3010 var1name,
3011 var2name,
3012 "",
3013 "",
3014 verbosity);
3015}
3016void CompareRelative(const ArrayOfArrayOfTensor3& var1,
3017 const ArrayOfArrayOfTensor3& var2,
3018 const Numeric& maxabsreldiff,
3019 const String& error_message,
3020 const String& var1name,
3021 const String& var2name,
3022 const String&,
3023 const String&,
3024 const Verbosity& verbosity) {
3025 _cr_internal_(var1,
3026 var2,
3027 maxabsreldiff,
3028 error_message,
3029 var1name,
3030 var2name,
3031 "",
3032 "",
3033 verbosity);
3034}
3035void CompareRelative(const ArrayOfArrayOfTensor4& var1,
3036 const ArrayOfArrayOfTensor4& var2,
3037 const Numeric& maxabsreldiff,
3038 const String& error_message,
3039 const String& var1name,
3040 const String& var2name,
3041 const String&,
3042 const String&,
3043 const Verbosity& verbosity) {
3044 _cr_internal_(var1,
3045 var2,
3046 maxabsreldiff,
3047 error_message,
3048 var1name,
3049 var2name,
3050 "",
3051 "",
3052 verbosity);
3053}
3054void CompareRelative(const ArrayOfArrayOfTensor5& var1,
3055 const ArrayOfArrayOfTensor5& var2,
3056 const Numeric& maxabsreldiff,
3057 const String& error_message,
3058 const String& var1name,
3059 const String& var2name,
3060 const String&,
3061 const String&,
3062 const Verbosity& verbosity) {
3063 _cr_internal_(var1,
3064 var2,
3065 maxabsreldiff,
3066 error_message,
3067 var1name,
3068 var2name,
3069 "",
3070 "",
3071 verbosity);
3072}
3073void CompareRelative(const ArrayOfArrayOfTensor6& var1,
3074 const ArrayOfArrayOfTensor6& var2,
3075 const Numeric& maxabsreldiff,
3076 const String& error_message,
3077 const String& var1name,
3078 const String& var2name,
3079 const String&,
3080 const String&,
3081 const Verbosity& verbosity) {
3082 _cr_internal_(var1,
3083 var2,
3084 maxabsreldiff,
3085 error_message,
3086 var1name,
3087 var2name,
3088 "",
3089 "",
3090 verbosity);
3091}
3092void CompareRelative(const ArrayOfArrayOfTensor7& var1,
3093 const ArrayOfArrayOfTensor7& var2,
3094 const Numeric& maxabsreldiff,
3095 const String& error_message,
3096 const String& var1name,
3097 const String& var2name,
3098 const String&,
3099 const String&,
3100 const Verbosity& verbosity) {
3101 _cr_internal_(var1,
3102 var2,
3103 maxabsreldiff,
3104 error_message,
3105 var1name,
3106 var2name,
3107 "",
3108 "",
3109 verbosity);
3110}
3111
3112void CompareRelative(const PropagationMatrix& var1,
3113 const PropagationMatrix& var2,
3114 const Numeric& maxabsreldiff,
3115 const String& error_message,
3116 const String& var1name,
3117 const String& var2name,
3118 const String&,
3119 const String&,
3120 const Verbosity& verbosity) {
3121 _cr_internal_(var1,
3122 var2,
3123 maxabsreldiff,
3124 error_message,
3125 var1name,
3126 var2name,
3127 "",
3128 "",
3129 verbosity);
3130}
3131
3132void CompareRelative(const ArrayOfPropagationMatrix& var1,
3133 const ArrayOfPropagationMatrix& var2,
3134 const Numeric& maxabsreldiff,
3135 const String& error_message,
3136 const String& var1name,
3137 const String& var2name,
3138 const String&,
3139 const String&,
3140 const Verbosity& verbosity) {
3141 _cr_internal_(var1,
3142 var2,
3143 maxabsreldiff,
3144 error_message,
3145 var1name,
3146 var2name,
3147 "",
3148 "",
3149 verbosity);
3150}
3151
3152void CompareRelative(const ArrayOfArrayOfPropagationMatrix& var1,
3153 const ArrayOfArrayOfPropagationMatrix& var2,
3154 const Numeric& maxabsreldiff,
3155 const String& error_message,
3156 const String& var1name,
3157 const String& var2name,
3158 const String&,
3159 const String&,
3160 const Verbosity& verbosity) {
3161 _cr_internal_(var1,
3162 var2,
3163 maxabsreldiff,
3164 error_message,
3165 var1name,
3166 var2name,
3167 "",
3168 "",
3169 verbosity);
3170}
3171
3172void CompareRelative(const StokesVector& var1,
3173 const StokesVector& var2,
3174 const Numeric& maxabsreldiff,
3175 const String& error_message,
3176 const String& var1name,
3177 const String& var2name,
3178 const String&,
3179 const String&,
3180 const Verbosity& verbosity) {
3181 _cr_internal_(var1,
3182 var2,
3183 maxabsreldiff,
3184 error_message,
3185 var1name,
3186 var2name,
3187 "",
3188 "",
3189 verbosity);
3190}
3191
3192void CompareRelative(const ArrayOfStokesVector& var1,
3193 const ArrayOfStokesVector& var2,
3194 const Numeric& maxabsreldiff,
3195 const String& error_message,
3196 const String& var1name,
3197 const String& var2name,
3198 const String&,
3199 const String&,
3200 const Verbosity& verbosity) {
3201 _cr_internal_(var1,
3202 var2,
3203 maxabsreldiff,
3204 error_message,
3205 var1name,
3206 var2name,
3207 "",
3208 "",
3209 verbosity);
3210}
3211
3212void CompareRelative(const ArrayOfArrayOfStokesVector& var1,
3213 const ArrayOfArrayOfStokesVector& var2,
3214 const Numeric& maxabsreldiff,
3215 const String& error_message,
3216 const String& var1name,
3217 const String& var2name,
3218 const String&,
3219 const String&,
3220 const Verbosity& verbosity) {
3221 _cr_internal_(var1,
3222 var2,
3223 maxabsreldiff,
3224 error_message,
3225 var1name,
3226 var2name,
3227 "",
3228 "",
3229 verbosity);
3230}
3231
3232/* Workspace method: Doxygen documentation will be auto-generated */
3233void CompareRelative(const EnergyLevelMap& var1,
3234 const EnergyLevelMap& var2,
3235 const Numeric& maxabsreldiff,
3236 const String& error_message,
3237 const String& var1name,
3238 const String& var2name,
3239 const String&,
3240 const String&,
3241 const Verbosity& verbosity) {
3242 _cr_internal_(var1.Data(),
3243 var2.Data(),
3244 maxabsreldiff,
3245 error_message,
3246 var1name,
3247 var2name,
3248 "",
3249 "",
3250 verbosity);
3251 _cr_internal_(var1.Energies(),
3252 var2.Energies(),
3253 maxabsreldiff,
3254 error_message,
3255 var1name,
3256 var2name,
3257 "",
3258 "",
3259 verbosity);
3260}
3261
3262void PrintPhysicalConstants(const Verbosity& verbosity) {
3263 CREATE_OUT0;
3264
3265 extern const Numeric AVOGADROS_NUMB;
3266 extern const Numeric BOHR_MAGNETON;
3267 extern const Numeric BOLTZMAN_CONST;
3268 extern const Numeric ELECTRON_CHARGE;
3269 extern const Numeric ELECTRON_MASS;
3270 extern const Numeric GAS_CONSTANT;
3271 extern const Numeric PLANCK_CONST;
3272 extern const Numeric SPEED_OF_LIGHT;
3273 extern const Numeric VACUUM_PERMITTIVITY;
3274 extern const Numeric DOPPLER_CONST;
3275
3276 out0 << std::setprecision(15) << std::scientific;
3277 out0 << "---------------------------------------------------------\n"
3278 << "Numerical const in ARTS \tValue\n"
3279 << "Avogadro's constant: \t " << AVOGADROS_NUMB << '\n'
3280 << "Bohr's magneton: \t " << BOHR_MAGNETON << '\n'
3281 << "Boltzmann's constant: \t " << BOLTZMAN_CONST << '\n'
3282 << "Electron charge: \t" << ELECTRON_CHARGE << '\n'
3283 << "Electron mass: \t " << ELECTRON_MASS << '\n'
3284 << "Ideal gas constant: \t " << GAS_CONSTANT << '\n'
3285 << "Planck's constant: \t " << PLANCK_CONST << '\n'
3286 << "Speed of light: \t " << SPEED_OF_LIGHT << '\n'
3287 << "Vacuum permittivity: \t " << VACUUM_PERMITTIVITY << '\n'
3288 << "Doppler constant: \t " << DOPPLER_CONST << '\n'
3289 << "---------------------------------------------------------\n";
3290}
3291
3292
3293
3294/* Workspace method: Doxygen documentation will be auto-generated */
3295void ArrayOfSpeciesTagSet(ArrayOfSpeciesTag& sst,
3296 const ArrayOfSpeciesTag& sst2,
3297 const Verbosity&) {
3298 sst = sst2;
3299}
This file contains the definition of Array.
void arts_exit(int status)
This is the exit function of ARTS.
Definition: arts.cc:42
The global header file for ARTS.
Index nrows
Index nbooks
Index npages
Index nvitrines
Index nshelves
Index ncols
TimeStep mean(const ArrayOfTimeStep &dt)
Returns the mean time step.
Definition: artstime.cc:190
Stuff related to time in ARTS.
Index nelem() const ARTS_NOEXCEPT
Number of elements.
Definition: array.h:195
Index nrows() const ARTS_NOEXCEPT
Returns the number of rows.
Definition: matpackI.cc:433
Index ncols() const ARTS_NOEXCEPT
Returns the number of columns.
Definition: matpackI.cc:436
Index npages() const
Returns the number of pages.
Definition: matpackIII.h:144
Index nrows() const
Returns the number of rows.
Definition: matpackIII.h:147
Index ncols() const
Returns the number of columns.
Definition: matpackIII.h:150
Index npages() const
Returns the number of pages.
Definition: matpackIV.cc:58
Index nbooks() const
Returns the number of books.
Definition: matpackIV.cc:55
Index ncols() const
Returns the number of columns.
Definition: matpackIV.cc:64
Index nrows() const
Returns the number of rows.
Definition: matpackIV.cc:61
Index ncols() const
Returns the number of columns.
Definition: matpackV.cc:56
Index nshelves() const
Returns the number of shelves.
Definition: matpackV.cc:44
Index npages() const
Returns the number of pages.
Definition: matpackV.cc:50
Index nrows() const
Returns the number of rows.
Definition: matpackV.cc:53
Index nbooks() const
Returns the number of books.
Definition: matpackV.cc:47
Index ncols() const
Returns the number of columns.
Definition: matpackVI.cc:57
Index npages() const
Returns the number of pages.
Definition: matpackVI.cc:51
Index nrows() const
Returns the number of rows.
Definition: matpackVI.cc:54
Index nshelves() const
Returns the number of shelves.
Definition: matpackVI.cc:45
Index nbooks() const
Returns the number of books.
Definition: matpackVI.cc:48
Index nvitrines() const
Returns the number of vitrines.
Definition: matpackVI.cc:42
Index nshelves() const
Returns the number of shelves.
Definition: matpackVII.cc:48
Index nrows() const
Returns the number of rows.
Definition: matpackVII.cc:57
Index nvitrines() const
Returns the number of vitrines.
Definition: matpackVII.cc:45
Index npages() const
Returns the number of pages.
Definition: matpackVII.cc:54
Index ncols() const
Returns the number of columns.
Definition: matpackVII.cc:60
Index nlibraries() const
Returns the number of libraries.
Definition: matpackVII.cc:42
Index nbooks() const
Returns the number of books.
Definition: matpackVII.cc:51
Index nelem() const ARTS_NOEXCEPT
Returns the number of elements.
Definition: matpackI.cc:48
The Matrix class.
Definition: matpackI.h:1225
void resize(Index r, Index c)
Resize function.
Definition: matpackI.cc:1056
The range class.
Definition: matpackI.h:165
Implements rational numbers to work with other ARTS types.
Definition: rational.h:52
The Sparse class.
Definition: matpackII.h:67
void resize(Index r, Index c)
Resize function.
Definition: matpackII.cc:361
Index nrows() const
Returns the number of rows.
Definition: matpackII.cc:66
Index ncols() const
Returns the number of columns.
Definition: matpackII.cc:69
void insert_elements(Index nnz, const ArrayOfIndex &rowind, const ArrayOfIndex &colind, ConstVectorView data)
Insert vector of elements with given row and column indices.
Definition: matpackII.cc:337
The Tensor3 class.
Definition: matpackIII.h:339
void resize(Index p, Index r, Index c)
Resize function.
Definition: matpackIII.cc:658
The Tensor4 class.
Definition: matpackIV.h:421
void resize(Index b, Index p, Index r, Index c)
Resize function.
Definition: matpackIV.cc:1058
The Tensor5 class.
Definition: matpackV.h:506
void resize(Index s, Index b, Index p, Index r, Index c)
Resize function.
Definition: matpackV.cc:1741
The Tensor6 class.
Definition: matpackVI.h:1088
void resize(Index v, Index s, Index b, Index p, Index r, Index c)
Resize function.
Definition: matpackVI.cc:2171
The Tensor7 class.
Definition: matpackVII.h:2382
void resize(Index l, Index v, Index s, Index b, Index p, Index r, Index c)
Resize function.
Definition: matpackVII.cc:5482
Class to handle time in ARTS.
Definition: artstime.h:41
The Vector class.
Definition: matpackI.h:876
void resize(Index n)
Resize function.
Definition: matpackI.cc:408
void mult(MatrixView C, ConstMatrixView A, const Block &B)
#define ARTS_ASSERT(condition,...)
Definition: debug.h:83
#define ARTS_USER_ERROR_IF(condition,...)
Definition: debug.h:134
Class to map energy levels.
The declarations of all the exception classes.
Implementation of gridded fields.
#define min(a, b)
#define max(a, b)
void id_mat(MatrixView I)
Identity Matrix.
Definition: lin_alg.cc:2235
Linear algebra functions.
bool is_increasing(ConstVectorView x)
Checks if a vector is sorted and strictly increasing.
Definition: logic.cc:215
bool is_decreasing(ConstVectorView x)
Checks if a vector is sorted in reversed order and is strictly decreasing.
Definition: logic.cc:252
Header file for logic.cc.
std::vector< T > linspace(T s, T e, typename std::vector< T >::size_type count) noexcept
void VectorLinSpace(Vector &x, const Numeric &start, const Numeric &stop, const Numeric &step, const Verbosity &verbosity)
WORKSPACE METHOD: VectorLinSpace.
void IndexStepUp(Index &xout, const Index &xin, const Verbosity &)
WORKSPACE METHOD: IndexStepUp.
void VectorDivide(Vector &out, const Vector &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: VectorDivide.
void Tensor4Multiply(Tensor4 &out, const Tensor4 &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: Tensor4Multiply.
void MatrixSubtract(Matrix &out, const Matrix &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: MatrixSubtract.
void VectorCrop(Vector &out, const Vector &in, const Numeric &min_value, const Numeric &max_value, const Verbosity &)
WORKSPACE METHOD: VectorCrop.
void Matrix1ColFromVector(Matrix &m, const Vector &v, const Verbosity &)
WORKSPACE METHOD: Matrix1ColFromVector.
void Tensor7SetConstant(Tensor7 &x, const Index &nlibraries, const Index &nvitrines, const Index &nshelves, const Index &nbooks, const Index &npages, const Index &nrows, const Index &ncols, const Numeric &value, const Verbosity &verbosity)
WORKSPACE METHOD: Tensor7SetConstant.
void ArrayOfIndexSetConstant(ArrayOfIndex &aoi, const Index &nelem, const Index &value, const Verbosity &)
WORKSPACE METHOD: ArrayOfIndexSetConstant.
void IndexSubtract(Index &out, const Index &in, const Index &value, const Verbosity &)
WORKSPACE METHOD: IndexSubtract.
void Tensor3Multiply(Tensor3 &out, const Tensor3 &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: Tensor3Multiply.
void VectorFlip(Vector &out, const Vector &in, const Verbosity &)
WORKSPACE METHOD: VectorFlip.
void NumericSet(Numeric &x, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: NumericSet.
void IndexDivide(Index &out, const Index &in, const Index &value, const Verbosity &)
WORKSPACE METHOD: IndexDivide.
void Matrix2RowFromVectors(Matrix &m, const Vector &v1, const Vector &v2, const Verbosity &)
WORKSPACE METHOD: Matrix2RowFromVectors.
void NumericClip(Numeric &out, const Numeric &in, const Numeric &limit_low, const Numeric &limit_high, const Verbosity &)
WORKSPACE METHOD: NumericClip.
void Tensor5SetConstant(Tensor5 &x, const Index &nshelves, const Index &nbooks, const Index &npages, const Index &nrows, const Index &ncols, const Numeric &value, const Verbosity &verbosity)
WORKSPACE METHOD: Tensor5SetConstant.
void ArrayOfTimeNLinSpace(ArrayOfTime &x, const Index &n, const String &start, const String &stop, const Verbosity &)
WORKSPACE METHOD: ArrayOfTimeNLinSpace.
void Trapz(Numeric &out, const Vector &x, const Vector &y, const Verbosity &)
WORKSPACE METHOD: Trapz.
void DiagonalMatrix(Matrix &X, const Vector &diag, const Verbosity &)
WORKSPACE METHOD: DiagonalMatrix.
void Tensor3ExtractFromTensor4(Tensor3 &t3, const Tensor4 &t4, const Index &index, const String &direction, const Verbosity &)
WORKSPACE METHOD: Tensor3ExtractFromTensor4.
void MatrixMultiply(Matrix &out, const Matrix &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: MatrixMultiply.
void SparseSparseMultiply(Sparse &Y, const Sparse &M, const Sparse &X, const Verbosity &)
WORKSPACE METHOD: SparseSparseMultiply.
void MatrixSetConstant(Matrix &x, const Index &nrows, const Index &ncols, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: MatrixSetConstant.
void VectorMultiply(Vector &out, const Vector &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: VectorMultiply.
void ArrayOfIndexSet(ArrayOfIndex &aoi, const ArrayOfIndex &values, const Verbosity &)
WORKSPACE METHOD: ArrayOfIndexSet.
void Tensor6SetConstant(Tensor6 &x, const Index &nvitrines, const Index &nshelves, const Index &nbooks, const Index &npages, const Index &nrows, const Index &ncols, const Numeric &value, const Verbosity &verbosity)
WORKSPACE METHOD: Tensor6SetConstant.
void IndexAdd(Index &out, const Index &in, const Index &value, const Verbosity &)
WORKSPACE METHOD: IndexAdd.
void VectorSubtractElementwise(Vector &c, const Vector &a, const Vector &b, const Verbosity &)
WORKSPACE METHOD: VectorSubtractElementwise.
void VectorExtractFromMatrix(Vector &v, const Matrix &m, const Index &index, const String &direction, const Verbosity &)
WORKSPACE METHOD: VectorExtractFromMatrix.
void Tensor3Add(Tensor3 &out, const Tensor3 &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: Tensor3Add.
void VectorAddElementwise(Vector &c, const Vector &a, const Vector &b, const Verbosity &)
WORKSPACE METHOD: VectorAddElementwise.
void RationalDivide(Rational &out, const Rational &in, const Rational &value, const Verbosity &)
WORKSPACE METHOD: RationalDivide.
void Matrix1RowFromVector(Matrix &m, const Vector &v, const Verbosity &)
WORKSPACE METHOD: Matrix1RowFromVector.
void MatrixSet(Matrix &x, const Matrix &values, const Verbosity &)
WORKSPACE METHOD: MatrixSet.
void Tensor3FromVector(Tensor3 &m, const Vector &v, const Verbosity &)
WORKSPACE METHOD: Tensor3FromVector.
void Tensor6Multiply(Tensor6 &out, const Tensor6 &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: Tensor6Multiply.
void NumericMultiply(Numeric &out, const Numeric &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: NumericMultiply.
void NumericSubtract(Numeric &out, const Numeric &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: NumericSubtract.
void RationalSubtract(Rational &out, const Rational &in, const Rational &value, const Verbosity &)
WORKSPACE METHOD: RationalSubtract.
void VectorSubtract(Vector &out, const Vector &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: VectorSubtract.
void VectorDivideElementwise(Vector &c, const Vector &a, const Vector &b, const Verbosity &)
WORKSPACE METHOD: VectorDivideElementwise.
void IndexMultiply(Index &out, const Index &in, const Index &value, const Verbosity &)
WORKSPACE METHOD: IndexMultiply.
void Matrix2ColFromVectors(Matrix &m, const Vector &v1, const Vector &v2, const Verbosity &)
WORKSPACE METHOD: Matrix2ColFromVectors.
void ArrayOfStringSet(ArrayOfString &sa, const ArrayOfString &sa2, const Verbosity &)
WORKSPACE METHOD: ArrayOfStringSet.
void NumericDivide(Numeric &out, const Numeric &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: NumericDivide.
void ArrayOfIndexLinSpace(ArrayOfIndex &x, const Index &start, const Index &stop, const Index &step, const Verbosity &verbosity)
WORKSPACE METHOD: ArrayOfIndexLinSpace.
void MatrixDivide(Matrix &out, const Matrix &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: MatrixDivide.
void QuantumIdentifierSet(QuantumIdentifier &x, const String &value, const Verbosity &)
WORKSPACE METHOD: QuantumIdentifierSet.
void VectorMultiplyElementwise(Vector &c, const Vector &a, const Vector &b, const Verbosity &)
WORKSPACE METHOD: VectorMultiplyElementwise.
void VectorSparseMultiply(Vector &y, const Sparse &M, const Vector &x, const Verbosity &)
WORKSPACE METHOD: VectorSparseMultiply.
void RationalSet(Rational &x, const Index &numerator, const Index &denominator, const Verbosity &)
WORKSPACE METHOD: RationalSet.
void VectorNLinSpace(Vector &x, const Index &n, const Numeric &start, const Numeric &stop, const Verbosity &verbosity)
WORKSPACE METHOD: VectorNLinSpace.
void Tensor4SetConstant(Tensor4 &x, const Index &nbooks, const Index &npages, const Index &nrows, const Index &ncols, const Numeric &value, const Verbosity &verbosity)
WORKSPACE METHOD: Tensor4SetConstant.
void Tensor5Multiply(Tensor5 &out, const Tensor5 &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: Tensor5Multiply.
void Tensor4Add(Tensor4 &out, const Tensor4 &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: Tensor4Add.
void StringSet(String &s, const String &s2, const Verbosity &)
WORKSPACE METHOD: StringSet.
void VectorLogSpace(Vector &x, const Numeric &start, const Numeric &stop, const Numeric &step, const Verbosity &verbosity)
WORKSPACE METHOD: VectorLogSpace.
void Matrix3RowFromVectors(Matrix &m, const Vector &v1, const Vector &v2, const Vector &v3, const Verbosity &)
WORKSPACE METHOD: Matrix3RowFromVectors.
void Tensor7Multiply(Tensor7 &out, const Tensor7 &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: Tensor7Multiply.
void VectorMatrixMultiply(Vector &y, const Matrix &M, const Vector &x, const Verbosity &)
WORKSPACE METHOD: VectorMatrixMultiply.
void IndexStepDown(Index &xout, const Index &xin, const Verbosity &)
WORKSPACE METHOD: IndexStepDown.
void VectorInsertGridPoints(Vector &og, const Vector &ingrid, const Vector &points, const Verbosity &verbosity)
WORKSPACE METHOD: VectorInsertGridPoints.
void FlagOff(Index &x, const Verbosity &)
WORKSPACE METHOD: FlagOff.
void IndexSet(Index &x, const Index &value, const Verbosity &)
WORKSPACE METHOD: IndexSet.
void VectorAdd(Vector &out, const Vector &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: VectorAdd.
void RationalAdd(Rational &out, const Rational &in, const Rational &value, const Verbosity &)
WORKSPACE METHOD: RationalAdd.
void Matrix3ColFromVectors(Matrix &m, const Vector &v1, const Vector &v2, const Vector &v3, const Verbosity &)
WORKSPACE METHOD: Matrix3ColFromVectors.
void MatrixIdentity(Matrix &out, const Index &n, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: MatrixIdentity.
void VectorClip(Vector &out, const Vector &in, const Numeric &limit_low, const Numeric &limit_high, const Verbosity &)
WORKSPACE METHOD: VectorClip.
void Tensor3SetConstant(Tensor3 &x, const Index &npages, const Index &nrows, const Index &ncols, const Numeric &value, const Verbosity &verbosity)
WORKSPACE METHOD: Tensor3SetConstant.
void SparseIdentity(Sparse &X, const Index &n, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: SparseIdentity.
void MatrixMatrixMultiply(Matrix &Y, const Matrix &M, const Matrix &X, const Verbosity &)
WORKSPACE METHOD: MatrixMatrixMultiply.
void MatrixExtractFromTensor3(Matrix &m, const Tensor3 &t3, const Index &index, const String &direction, const Verbosity &)
WORKSPACE METHOD: MatrixExtractFromTensor3.
void FlagOn(Index &x, const Verbosity &)
WORKSPACE METHOD: FlagOn.
void MatrixCopySparse(Matrix &out, const Sparse &in, const Verbosity &)
WORKSPACE METHOD: MatrixCopySparse.
void MatrixAdd(Matrix &out, const Matrix &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: MatrixAdd.
void NumericFromVector(Numeric &out, const Vector &in, const String &op, const Verbosity &)
WORKSPACE METHOD: NumericFromVector.
void ArrayOfQuantumIdentifierSet(ArrayOfQuantumIdentifier &x, const ArrayOfString &values, const Verbosity &verbosity)
WORKSPACE METHOD: ArrayOfQuantumIdentifierSet.
void RationalMultiply(Rational &out, const Rational &in, const Rational &value, const Verbosity &)
WORKSPACE METHOD: RationalMultiply.
void NumericAdd(Numeric &out, const Numeric &in, const Numeric &value, const Verbosity &)
WORKSPACE METHOD: NumericAdd.
void nlinspace(Vector &x, const Numeric start, const Numeric stop, const Index n)
nlinspace
Definition: math_funcs.cc:225
Numeric last(ConstVectorView x)
last
Definition: math_funcs.cc:159
Header file for sparse matrices.
void transform(VectorView y, double(&my_func)(double), ConstVectorView x)
A generic transform function for vectors, which can be used to implement mathematical functions opera...
Definition: matpackI.cc:1472
Implementation of Matrix, Vector, and such stuff.
INDEX Index
The type to use for all integer numbers and indices.
Definition: matpack.h:39
NUMERIC Numeric
The type to use for all floating point numbers.
Definition: matpack.h:33
const Joker joker
Declarations having to do with the four output streams.
#define CREATE_OUT3
Definition: messages.h:207
#define CREATE_OUT2
Definition: messages.h:206
This file contains the definition of String, the ARTS string class.
Index nelem(const Lines &l)
Number of lines.
constexpr Numeric l(const Index p0, const Index n, const Numeric x, const SortedVectorType &xi, const Index j, const std::pair< Numeric, Numeric > cycle={ -180, 180}) noexcept
Vector mass(const ConstVectorView &atmospheric_vmrs, const ArrayOfArrayOfSpeciesTag &atmospheric_species, const ArrayOfSpecies &lineshape_species, const SpeciesIsotopologueRatios &ir) ARTS_NOEXCEPT
Returns a mass vector for this model's main calculations.
constexpr Rational start(Rational Ju, Rational Jl, Polarization type) noexcept
Gives the lowest M for a polarization type of this transition.
Definition: zeemandata.h:78
Scattering database structure and functions.
#define v
#define a
#define c
#define b
Quantum::Identifier QuantumIdentifier
Definition: quantum.h:471
#define M
Definition: rng.cc:165
Contains sorting routines.
void get_sorted_indexes(ArrayOfIndex &sorted, const T &data)
get_sorted_indexes
Definition: sorting.h:73