Browse Source

Lemma is compiling with the exception of TEMIntegrationKernel.

enhancement_3
Trevor Irons 8 years ago
parent
commit
5d1239564a
100 changed files with 19751 additions and 28 deletions
  1. 5
    3
      CMakeLists.txt
  2. 13
    2
      LemmaCore/CMakeLists.txt
  3. 112
    0
      LemmaCore/include/AEMSurvey.h
  4. 137
    0
      LemmaCore/include/AEMSurveyReader.h
  5. 142
    0
      LemmaCore/include/ASCIIParser.h
  6. 181
    0
      LemmaCore/include/CubicSplineInterpolator.h
  7. 127
    0
      LemmaCore/include/DCIPElectrode.h
  8. 240
    0
      LemmaCore/include/DCSurvey.h
  9. 112
    0
      LemmaCore/include/FHTKey.h
  10. 112
    0
      LemmaCore/include/FHTKey101.h
  11. 112
    0
      LemmaCore/include/FHTKey51.h
  12. 76
    0
      LemmaCore/include/GridReader.h
  13. 87
    0
      LemmaCore/include/GroundedElectricDipole.h
  14. 105
    0
      LemmaCore/include/LayeredEarthEMReader.h
  15. 223
    0
      LemmaCore/include/LemmaObject.h
  16. 88
    0
      LemmaCore/include/MagneticDipole.h
  17. 109
    0
      LemmaCore/include/ParticleSwarmOptimizer.h
  18. 169
    0
      LemmaCore/include/PolygonalWireAntenna.h
  19. 197
    0
      LemmaCore/include/QWEKey.h
  20. 112
    0
      LemmaCore/include/RectilinearGridReader.h
  21. 120
    0
      LemmaCore/include/RectilinearGridVTKExporter.h
  22. 106
    0
      LemmaCore/include/TEMInductiveReceiver.h
  23. 183
    0
      LemmaCore/include/TEMReceiver.h
  24. 137
    0
      LemmaCore/include/TEMSurvey.h
  25. 161
    0
      LemmaCore/include/TEMSurveyData.h
  26. 117
    0
      LemmaCore/include/TEMSurveyLine.h
  27. 146
    0
      LemmaCore/include/TEMSurveyLineData.h
  28. 140
    0
      LemmaCore/include/TEMSurveyLineRecord.h
  29. 141
    0
      LemmaCore/include/TEMSurveyLineRecordData.h
  30. 125
    0
      LemmaCore/include/TEMTransmitter.h
  31. 88
    0
      LemmaCore/include/UngroundedElectricDipole.h
  32. 249
    0
      LemmaCore/include/WireAntenna.h
  33. 24
    0
      LemmaCore/include/banner.h
  34. 98
    0
      LemmaCore/include/bicgstab.h
  35. 437
    0
      LemmaCore/include/cg.h
  36. 101
    0
      LemmaCore/include/costransintegrationkernel.h
  37. 85
    0
      LemmaCore/include/data.h
  38. 181
    0
      LemmaCore/include/datafem.h
  39. 67
    0
      LemmaCore/include/datareader.h
  40. 67
    0
      LemmaCore/include/datareaderfem.h
  41. 100
    0
      LemmaCore/include/datareaderfemubc.h
  42. 82
    0
      LemmaCore/include/datareadertem.h
  43. 131
    0
      LemmaCore/include/datatem.h
  44. 83
    0
      LemmaCore/include/digitalfiltercostrans.h
  45. 542
    0
      LemmaCore/include/digitalfilterintegrator.h
  46. 81
    0
      LemmaCore/include/digitalfiltersintrans.h
  47. 335
    0
      LemmaCore/include/dipolesource.h
  48. 142
    0
      LemmaCore/include/earthmodel.h
  49. 232
    0
      LemmaCore/include/emearth1d.h
  50. 78
    0
      LemmaCore/include/emearth3d.h
  51. 62
    0
      LemmaCore/include/filter.h
  52. 139
    0
      LemmaCore/include/gaussianquadrature.h
  53. 64
    0
      LemmaCore/include/grid.h
  54. 90
    0
      LemmaCore/include/hankeltransform.h
  55. 349
    0
      LemmaCore/include/hankeltransformgaussianquadrature.h
  56. 246
    0
      LemmaCore/include/hankeltransformhankel2.h
  57. 277
    0
      LemmaCore/include/helper.h
  58. 62
    0
      LemmaCore/include/instrument.h
  59. 144
    0
      LemmaCore/include/instrumentfem.h
  60. 213
    0
      LemmaCore/include/instrumenttem.h
  61. 92
    0
      LemmaCore/include/integrationkernel.h
  62. 66
    0
      LemmaCore/include/integrator.h
  63. 118
    0
      LemmaCore/include/inversesolver.h
  64. 146
    0
      LemmaCore/include/inversesolvertem1d.h
  65. 85
    0
      LemmaCore/include/kernel.h
  66. 111
    0
      LemmaCore/include/kernelem1dbase.h
  67. 217
    0
      LemmaCore/include/kernelem1dmanager.h
  68. 253
    0
      LemmaCore/include/kernelem1dreflbase.h
  69. 373
    0
      LemmaCore/include/kernelem1dreflspec.h
  70. 1485
    0
      LemmaCore/include/kernelem1dspec.h
  71. 166
    0
      LemmaCore/include/layeredearth.h
  72. 314
    0
      LemmaCore/include/layeredearthem.h
  73. 333
    0
      LemmaCore/include/lemma.h
  74. 1369
    0
      LemmaCore/include/logbarriercg.h
  75. 1959
    0
      LemmaCore/include/logbarriercg_newton.h
  76. 73
    0
      LemmaCore/include/modelreader.h
  77. 68
    0
      LemmaCore/include/modelreaderfem1d.h
  78. 83
    0
      LemmaCore/include/modelreadertem1d.h
  79. 116
    0
      LemmaCore/include/modelreadertem1dubc.h
  80. 25
    0
      LemmaCore/include/modules.h
  81. 352
    0
      LemmaCore/include/octreegrid.h
  82. 62
    0
      LemmaCore/include/pulse.h
  83. 111
    0
      LemmaCore/include/quasinewtonbfgs.h
  84. 169
    0
      LemmaCore/include/receivercubes.h
  85. 281
    0
      LemmaCore/include/receiverpoints.h
  86. 237
    0
      LemmaCore/include/rectilineargrid.h
  87. 97
    0
      LemmaCore/include/sintransintegrationkernel.h
  88. 103
    0
      LemmaCore/include/temintegrationkernel.h
  89. 82
    0
      LemmaCore/include/timer.h
  90. 130
    0
      LemmaCore/include/windowfilter.h
  91. 0
    23
      LemmaCore/lemma.h
  92. 111
    0
      LemmaCore/src/AEMSurvey.cpp
  93. 169
    0
      LemmaCore/src/AEMSurveyReader.cpp
  94. 216
    0
      LemmaCore/src/ASCIIParser.cpp
  95. 335
    0
      LemmaCore/src/CubicSplineInterpolator.cpp
  96. 165
    0
      LemmaCore/src/DCIPElectrode.cpp
  97. 377
    0
      LemmaCore/src/DCSurvey.cpp
  98. 359
    0
      LemmaCore/src/FHTKey.cpp
  99. 259
    0
      LemmaCore/src/FHTKey101.cpp
  100. 0
    0
      LemmaCore/src/FHTKey51.cpp

+ 5
- 3
CMakeLists.txt View File

@@ -76,8 +76,10 @@ configure_file (
76 76
 )
77 77
 include_directories("${PROJECT_BINARY_DIR}/include")
78 78
 
79
-
80
-include_directories ("${PROJECT_SOURCE_DIR}/LemmaCore")
79
+include_directories ("${PROJECT_SOURCE_DIR}/LemmaCore/include")
80
+include_directories ("${CMAKE_INSTALL_PREFIX}/include/eigen3")
81
+include_directories ("${CMAKE_INSTALL_PREFIX}/include/")
82
+link_directories ("${CMAKE_INSTALL_PREFIX}/lib/")
81 83
 add_subdirectory (LemmaCore) 
82 84
 
83 85
 # TODO add compiler specific instructions
@@ -86,6 +88,6 @@ add_compile_options(-std=c++11)
86 88
 include_directories(${CMAKE_INSTALL_PREFIX}/include)
87 89
 add_executable(Hello "${PROJECT_SOURCE_DIR}/src/test.cpp")
88 90
 target_link_libraries(Hello lemmacore)
89
-
91
+add_dependencies(Hello YAML-CPP)
90 92
 
91 93
 

+ 13
- 2
LemmaCore/CMakeLists.txt View File

@@ -1,13 +1,24 @@
1 1
 include_directories(${CMAKE_INSTALL_PREFIX}/include)
2 2
 
3
-add_compile_options(-std=c++11) 
3
+add_compile_options(-std=c++11 -DHAVE_YAMLCPP) 
4
+
5
+#file(GLOB LemmaCore_SRC
6
+#    "${CMAKE_CURRENT_DIR}/src/*.cpp"
7
+#)
8
+add_subdirectory("src")
4 9
 
5 10
 # TODO fill all the files
11
+add_library( lemmacore ${SOURCE} )  
12
+#		"src/lemma.cpp" 
13
+#		"src/dipolesource.cpp" 
14
+#		"src/GroundedElectricDipole.cpp" 
15
+#		"src/UngroundedElectricDipole.cpp"
16
+#)
6 17
 
7
-add_library( lemmacore  "lemma.cpp" )
8 18
 
9 19
 add_dependencies(lemmacore YAML-CPP)
10 20
 add_dependencies(lemmacore TINYXML2)
11 21
 add_dependencies(lemmacore MATIO)
12 22
 
13 23
 target_link_libraries(lemmacore ${VTK_LIBRARIES})
24
+target_link_libraries(lemmacore "yaml-cpp")

+ 112
- 0
LemmaCore/include/AEMSurvey.h View File

@@ -0,0 +1,112 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      09/24/2013 04:06:42 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2013, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2013, Trevor Irons
18
+ */
19
+
20
+#ifndef  AEMSURVEY_INC
21
+#define  AEMSURVEY_INC
22
+
23
+#include "LemmaObject.h"
24
+#include "dipolesource.h"
25
+
26
+namespace Lemma {
27
+
28
+/**
29
+  \brief   Contains pertinant information about an AEM survey
30
+  \details All important details about an AEM survey are stored here, but
31
+           nothing about the underlying earth model.
32
+ */
33
+class AEMSurvey : public LemmaObject {
34
+
35
+    friend std::ostream &operator<<(std::ostream &stream,
36
+            const AEMSurvey &ob);
37
+
38
+    /// AEMSurveyReader currently provides the only concrete way to use this class.
39
+    /// @todo consider making this an abstract class, that can only then exist through
40
+    ///       the reader. That is if you will not allow users to build their own.
41
+    friend class AEMSurveyReader;
42
+
43
+    public:
44
+
45
+    // ====================  LIFECYCLE     =======================
46
+
47
+    /**
48
+     * @copybrief LemmaObject::New()
49
+     * @copydetails LemmaObject::New()
50
+     */
51
+    static AEMSurvey* New();
52
+
53
+    /**
54
+     *  @copybrief   LemmaObject::Delete()
55
+     *  @copydetails LemmaObject::Delete()
56
+     */
57
+    void Delete();
58
+
59
+    // ====================  OPERATORS     =======================
60
+
61
+    // ====================  OPERATIONS    =======================
62
+
63
+    // ====================  ACCESS        =======================
64
+
65
+    /** Returns a particular EM source. For now only dipole sources are supported,
66
+     *  general loops int the new future.
67
+     *  @param[in] isource is the source fiducial to return
68
+     */
69
+    DipoleSource* GetSource(const int& isource);
70
+
71
+    /** @return the total number of sources
72
+     */
73
+    int GetNumberOfSources();
74
+
75
+    /** Returns vector of all frequencies used in the survey
76
+     *  @return a vector of the unique frequencies
77
+     */
78
+    VectorXr GetFrequencies();
79
+
80
+    // ====================  INQUIRY       =======================
81
+
82
+    protected:
83
+
84
+    // ====================  LIFECYCLE     =======================
85
+
86
+    /** Default protected constructor, use New */
87
+    AEMSurvey (const std::string& name);
88
+
89
+    /** Default protected destructor, use Delete */
90
+    ~AEMSurvey ();
91
+
92
+    /**
93
+     *  @copybrief   LemmaObject::Release()
94
+     *  @copydetails LemmaObject::Release()
95
+     */
96
+    void Release();
97
+
98
+    private:
99
+
100
+    // ====================  DATA MEMBERS  =========================
101
+
102
+    std::vector<DipoleSource*>  Sources;
103
+
104
+    VectorXr Freqs;
105
+
106
+
107
+}; // -----  end of class  AEMSurvey  -----
108
+
109
+}		// -----  end of Lemma  name  -----
110
+
111
+#endif   // ----- #ifndef AEMSURVEY_INC  -----
112
+

+ 137
- 0
LemmaCore/include/AEMSurveyReader.h View File

@@ -0,0 +1,137 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      09/24/2013 04:29:27 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2013, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2013, Trevor Irons
18
+ */
19
+
20
+#ifndef  AEMSURVEYREADER_INC
21
+#define  AEMSURVEYREADER_INC
22
+
23
+#include "LemmaObject.h"
24
+#include "AEMSurvey.h"
25
+#include "ASCIIParser.h"
26
+
27
+namespace Lemma {
28
+
29
+    /**
30
+      \brief   Reads an ASCII description of an AEM survey
31
+      \details The file format is described as follows.
32
+     */
33
+    class AEMSurveyReader : public LemmaObject {
34
+
35
+        friend std::ostream &operator<<(std::ostream &stream,
36
+                const AEMSurveyReader &ob);
37
+
38
+        public:
39
+
40
+        // ====================  LIFECYCLE     =======================
41
+
42
+        /*c
43
+         * @copybrief LemmaObject::New()
44
+         * @copydetails LemmaObject::New()
45
+         */
46
+        static AEMSurveyReader* New();
47
+
48
+        /**
49
+         *  @copybrief   LemmaObject::Delete()
50
+         *  @copydetails LemmaObject::Delete()
51
+         */
52
+        void Delete();
53
+
54
+        // ====================  OPERATORS     =======================
55
+
56
+        // ====================  OPERATIONS    =======================
57
+
58
+        /**
59
+         *
60
+@code
61
+// AEM Survey Specification file
62
+
63
+     5    // N sources
64
+
65
+400       // Source 1 frequency Hz
66
+MD        // Source 1 type
67
+-7  0 -10 // Source 1 relative position front/back, left/right, up/down
68
+1         // Source 1 moment
69
+
70
+1800      // Source 2  frequency Hz
71
+VMD       // Source 2 type
72
+-7  0 -10 // Source 2 relative position
73
+1         // Source 2 moment
74
+
75
+8200      // Source 3  freqeuncy Hz
76
+MD        // Source 3 type
77
+-7  0 -10 // Source 3 relative position
78
+1         // Source 3 moment
79
+
80
+40000     // Source 4  frequency Hz
81
+MD        // Source 4 type
82
+-7  0 -10 // Source 4 relative position
83
+1         // Source 4 moment
84
+
85
+140000    // Source 5  frequency Hz
86
+MD        // Source 5 type
87
+-7  0 -10 // Source 5 relative position
88
+1         // Source 5 moment
89
+
90
+// Flight Plan (in same coordinates as grid)
91
+2     // Number of points
92
+
93
+// location in x, y, z, polarisation [x,y,z]
94
+
95
+-200 -200 -30  0  0  1
96
+-190 -200 -30  0  0  1
97
+@endcode
98
+         */
99
+        void ReadASCIIAEMFile( const std::string& name );
100
+
101
+        // ====================  ACCESS        =======================
102
+
103
+        /**
104
+         * @return the AEMSurvey based on the file read
105
+         */
106
+        AEMSurvey* GetSurvey();
107
+
108
+        // ====================  INQUIRY       =======================
109
+
110
+        protected:
111
+
112
+        // ====================  LIFECYCLE     =======================
113
+
114
+        /** Default protected constructor, use New */
115
+        AEMSurveyReader (const std::string& name);
116
+
117
+        /** Default protected destructor, use Delete */
118
+        ~AEMSurveyReader ();
119
+
120
+        /**
121
+         *  @copybrief   LemmaObject::Release()
122
+         *  @copydetails LemmaObject::Release()
123
+         */
124
+        void Release();
125
+
126
+        private:
127
+
128
+        // ====================  DATA MEMBERS  =========================
129
+
130
+        AEMSurvey*  Survey;
131
+
132
+    }; // -----  end of class  AEMSurveyReader  -----
133
+
134
+}		// -----  end of Lemma  name  -----
135
+
136
+#endif   // ----- #ifndef AEMSURVEYREADER_INC  -----
137
+

+ 142
- 0
LemmaCore/include/ASCIIParser.h View File

@@ -0,0 +1,142 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      09/23/2013 02:31:24 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2013, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2013, Trevor Irons
18
+ */
19
+
20
+#ifndef  ASCIIPARSER_INC
21
+#define  ASCIIPARSER_INC
22
+
23
+#include "LemmaObject.h"
24
+#include <fstream>
25
+
26
+namespace Lemma {
27
+
28
+/**
29
+  \brief   Provides ASCII input file parsing
30
+  \details Able to accomodate various inputs and comment styles
31
+ */
32
+class ASCIIParser : public LemmaObject {
33
+
34
+    friend std::ostream &operator<<(std::ostream &stream,
35
+            const ASCIIParser &ob);
36
+
37
+    public:
38
+
39
+    // ====================  LIFECYCLE     =======================
40
+
41
+    /** @copybrief LemmaObject::New()
42
+     *  @copydetails LemmaObject::New()
43
+     */
44
+    static ASCIIParser* New();
45
+
46
+    /** @copybrief   LemmaObject::Delete()
47
+     *  @copydetails LemmaObject::Delete()
48
+     */
49
+    void Delete();
50
+
51
+    // ====================  OPERATORS     =======================
52
+
53
+    // ====================  OPERATIONS    =======================
54
+
55
+    /** Opens the file up for reading. Throws an exception if something bad happens.
56
+        @param[in] fname is the filename to be parsed.
57
+     */
58
+    void Open (const std::string& fname);
59
+
60
+
61
+    /** Closes the file. Throws an exception if something bad happens.
62
+     */
63
+    void Close ( );
64
+
65
+    /** Reads a series of Reals.
66
+     *  @param[in] nr is the number of reals to read. Enter -1 for the entire file
67
+     *  @todo throw exception if no file is open
68
+     */
69
+    std::vector<Real> ReadReals( const int& nr);
70
+
71
+    /** Reads a series of Reals.
72
+     *  @param[in] nr is the number of ints to read. Enter -1 for the entire file
73
+     *  @todo throw exception if no file is open
74
+     */
75
+    std::vector<int> ReadInts( const int& nr);
76
+
77
+    /** Reads a series of space delimited strings
78
+     *  @param[in] nr is the number of strings to read. Enter -1 for the entire file
79
+     *  @todo throw exception if no file is open
80
+     */
81
+    std::vector< std::string > ReadStrings( const int& nr);
82
+
83
+    /**
84
+     * @param[in] loc is the point in the file to jump to. Uses seekg
85
+     */
86
+    void JumpToLocation(const int& loc);
87
+
88
+    // ====================  ACCESS        =======================
89
+
90
+    /** Sets the comment identifier key.
91
+     * @param[in] key is a string identifying comments. All text after the key will be
92
+     *  ignored by the parser. Default is //
93
+     */
94
+    void SetCommentString( const std::string& key );
95
+
96
+    /** Sets the buffer size. This affects the maximum number of column in a line. Defaults
97
+     *  is 255.
98
+     *  @param[in] BufferSize is the size of the buffer to use
99
+     */
100
+    void SetBufferSize( const int& BufferSize);
101
+
102
+    /**
103
+     * @return the current position in the file, as reported by istream::tellg
104
+     */
105
+    int GetFileLocation();
106
+
107
+    // ====================  INQUIRY       =======================
108
+
109
+    protected:
110
+
111
+    // ====================  LIFECYCLE     =======================
112
+
113
+    /** Default protected constructor, use New */
114
+    ASCIIParser (const std::string& name);
115
+
116
+    /** Default protected destructor, use Delete */
117
+    ~ASCIIParser ();
118
+
119
+    /**
120
+     *  @copybrief   LemmaObject::Release()
121
+     *  @copydetails LemmaObject::Release()
122
+     */
123
+    void Release();
124
+
125
+    private:
126
+
127
+    // ====================  DATA MEMBERS  =========================
128
+
129
+    /** c++ style file IO */
130
+    std::fstream input;
131
+
132
+    /** comment string, defaults to c++ style // */
133
+    std::string  CommentString;
134
+
135
+    /** Buffer size, max line width supported, defaults to 255 */
136
+    int BufferSize;
137
+
138
+}; // -----  end of class  ASCIIParser  -----
139
+
140
+}		// -----  end of Lemma  name  -----
141
+
142
+#endif   // ----- #ifndef ASCIIPARSER_INC  -----

+ 181
- 0
LemmaCore/include/CubicSplineInterpolator.h View File

@@ -0,0 +1,181 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      09/25/2013 08:20:14 AM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2013, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2013, Trevor Irons
18
+ */
19
+
20
+#ifndef  CUBICSPLINEINTERPOLATOR_INC
21
+#define  CUBICSPLINEINTERPOLATOR_INC
22
+
23
+#include "LemmaObject.h"
24
+
25
+namespace Lemma {
26
+
27
+// Simple struct to hold spline terms
28
+struct SplineSet{
29
+    VectorXr a;
30
+    VectorXr b;
31
+    VectorXr c;
32
+    VectorXr d;
33
+    VectorXr x;
34
+
35
+    SplineSet( ) {
36
+    }
37
+
38
+    SplineSet(const int&n) {
39
+        a = VectorXr::Zero(n+1);
40
+        b = VectorXr::Zero(n);
41
+        c = VectorXr::Zero(n+1);
42
+        d = VectorXr::Zero(n);
43
+        x = VectorXr::Zero(n+1);
44
+    }
45
+};
46
+
47
+/**
48
+  \brief   Real 1D Natural cubic spline interpolator.
49
+  \details Splines are fit between knots \f$j\f$ according to the forulae
50
+           \f[ S_j(x) =  a_j + b_j(x - x_j) + c_j(x-x_j)^2 + d_j(x-x_y)^3  \f]
51
+           The spline must satisfy the following conditions
52
+            \f{eqnarray} {
53
+                S_i(x_i) & = & y_i = S_{i-1}(x_i), i = 1,..., n-1 \\
54
+                S'_i(x_i) & = &  S'_{i-1}(x_i), i = 1,..., n-1 \\
55
+                S''_i(x_i) & = & S''_{i-1}(x_i), i = 1,..., n-1 \\
56
+                S''_0(x_0) & = & S''_{n-1}(x_n) = 0
57
+            \f}
58
+ */
59
+class CubicSplineInterpolator : public LemmaObject {
60
+
61
+    friend std::ostream &operator<<(std::ostream &stream,
62
+            const CubicSplineInterpolator &ob);
63
+
64
+    public:
65
+
66
+    // ====================  LIFECYCLE     =======================
67
+
68
+    /**
69
+     * @copybrief LemmaObject::New()
70
+     * @copydetails LemmaObject::New()
71
+     */
72
+    static CubicSplineInterpolator* New();
73
+
74
+    /**
75
+     *  @copybrief   LemmaObject::Delete()
76
+     *  @copydetails LemmaObject::Delete()
77
+     */
78
+    void Delete();
79
+
80
+    // ====================  OPERATORS     =======================
81
+
82
+    // ====================  OPERATIONS    =======================
83
+
84
+    /** Sets the knots to use for interpolation.
85
+        @param[in] x are the absissa values
86
+        @param[in] y are the ordinate values
87
+     */
88
+    void SetKnots(const VectorXr& x, const VectorXr& y);
89
+
90
+    /** Resets the knots to use for interpolation, when abscissa values haven't changed.
91
+        @param[in] y are the ordinate values
92
+     */
93
+    void ResetKnotOrdinate( const VectorXr& y );
94
+
95
+    /** Interpolate a monotonically increasing ordered set.
96
+        @param[in] x are the interpolation abscissa points
97
+        @return the ordinate values at x
98
+     */
99
+    VectorXr InterpolateOrderedSet(const VectorXr& x);
100
+
101
+    /** integrates the spline from x0 to x1. Uses composite Simpson's rule and n is the number of segments
102
+     *  @param[in] x0 is left argument
103
+     *  @param[in] x1 is right argument
104
+     *  @param[in] n is the number of points, must be even
105
+     */
106
+    Real Integrate(const Real& x0, const Real& x1, const int& n);
107
+
108
+    /** integrates using cubic spline values. Taken from AMRIRA P223F project code Leroi, which in turn was based on
109
+        This is a modification of the FUNCTION PPVALU in the book
110
+        "A PRACTICAL GUIDE TO SPLINES"  by C. DE BOOR
111
+     */
112
+    Real Integrate(const Real& x0, const Real& x1);
113
+
114
+    /** @returns the know abscissa values
115
+     */
116
+    VectorXr GetKnotAbscissa();
117
+
118
+    /** @returns the know abscissa values
119
+     */
120
+    VectorXr GetKnotOrdinate();
121
+
122
+    /** Interpolation at a single point.
123
+        @param[in] x is the interpolation abscissa point
124
+        @param[in] i is an optional index to start searching at. Defaults to zero
125
+        @return the ordinate value at x
126
+     */
127
+    Real Interpolate(const Real& x, int& i);
128
+
129
+    /** Interpolation at a single point.
130
+        @param[in] x is the interpolation abscissa point
131
+        @return the ordinate value at x
132
+     */
133
+    Real Interpolate(const Real& x);
134
+
135
+    // ====================  ACCESS        =======================
136
+
137
+    // ====================  INQUIRY       =======================
138
+
139
+    protected:
140
+
141
+    // ====================  LIFECYCLE     =======================
142
+
143
+    /** Default protected constructor, use New */
144
+    CubicSplineInterpolator (const std::string& name);
145
+
146
+    /** Default protected destructor, use Delete */
147
+    ~CubicSplineInterpolator ();
148
+
149
+    /**
150
+     *  @copybrief   LemmaObject::Release()
151
+     *  @copydetails LemmaObject::Release()
152
+     */
153
+    void Release();
154
+
155
+    // ====================  OPERATIONS    =======================
156
+
157
+    /**
158
+        Performs spline fitting.
159
+     */
160
+    //void Spline() {
161
+    // }
162
+
163
+    /** Finds the interval of knots in spline to use for integration.
164
+     */
165
+    int Interval(const Real& x);
166
+
167
+    private:
168
+
169
+    SplineSet Spline;
170
+
171
+    int ilo;
172
+
173
+    int mflag;
174
+
175
+    // ====================  DATA MEMBERS  =========================
176
+
177
+}; // -----  end of class  CubicSplineInterpolator  -----
178
+
179
+}		// -----  end of Lemma  name  -----
180
+
181
+#endif   // ----- #ifndef CUBICSPLINEINTERPOLATOR_INC  -----

+ 127
- 0
LemmaCore/include/DCIPElectrode.h View File

@@ -0,0 +1,127 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      11/10/2014 10:53:34 AM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+
21
+#ifndef  DCIPELECTRODE_INC
22
+#define  DCIPELECTRODE_INC
23
+
24
+#include "LemmaObject.h"
25
+
26
+namespace Lemma {
27
+
28
+    /**
29
+      \brief
30
+      \details
31
+     */
32
+    class DCIPElectrode : public LemmaObject {
33
+
34
+        friend std::ostream &operator<<(std::ostream &stream,
35
+                const DCIPElectrode &ob);
36
+
37
+        public:
38
+
39
+        // ====================  LIFECYCLE     =======================
40
+
41
+        /**
42
+         * @copybrief LemmaObject::New()
43
+         * @copydetails LemmaObject::New()
44
+         */
45
+        static DCIPElectrode* New();
46
+
47
+        /**
48
+         *  @copybrief   LemmaObject::Delete()
49
+         *  @copydetails LemmaObject::Delete()
50
+         */
51
+        void Delete();
52
+
53
+        // ====================  OPERATORS     =======================
54
+
55
+        // ====================  OPERATIONS    =======================
56
+
57
+        // ====================  ACCESS        =======================
58
+
59
+        /** Sets the physical location of the electrode
60
+         *  @param[in] loc is the location
61
+         */
62
+        void SetLocation(const Vector3r& loc);
63
+
64
+        /** Sets the tag (label) for the electrode
65
+         */
66
+        void SetLabel(const std::string& tag);
67
+
68
+        /** Sets the tag (label) for the electrode
69
+         */
70
+        std::string GetLabel( );
71
+
72
+        int GetNodeID() {return Node_ID;}
73
+        // ====================  INQUIRY       =======================
74
+
75
+#ifdef HAVE_YAMLCPP
76
+        /**
77
+         *  Uses YAML to serialize this object.
78
+         *  @return a YAML::Node
79
+         */
80
+        YAML::Node Serialize() const;
81
+
82
+        /**
83
+         *   Constructs an object from a YAML::Node.
84
+         */
85
+        static DCIPElectrode* DeSerialize(const YAML::Node& node);
86
+#endif
87
+
88
+        protected:
89
+
90
+        // ====================  LIFECYCLE     =======================
91
+
92
+        /** Default protected constructor, use New */
93
+        DCIPElectrode (const std::string& name);
94
+
95
+#ifdef HAVE_YAMLCPP
96
+        /** Protected DeDerializing constructor, use factory DeSerialize  method*/
97
+        DCIPElectrode (const YAML::Node& node);
98
+#endif
99
+
100
+        /** Default protected destructor, use Delete */
101
+        ~DCIPElectrode ();
102
+
103
+        /**
104
+         *  @copybrief   LemmaObject::Release()
105
+         *  @copydetails LemmaObject::Release()
106
+         */
107
+        void Release();
108
+
109
+        private:
110
+
111
+        // ====================  DATA MEMBERS  =========================
112
+
113
+        /** The location of the electrode */
114
+        Vector3r Location;
115
+
116
+        /** Local Node_ID on a mesh */
117
+        int Node_ID;
118
+
119
+        /** String label for the electrode */
120
+        std::string Label;
121
+
122
+    }; // -----  end of class  DCIPElectrode  -----
123
+
124
+}		// -----  end of Lemma  name  -----
125
+
126
+#endif   // ----- #ifndef DCIPELECTRODE_INC  -----
127
+

+ 240
- 0
LemmaCore/include/DCSurvey.h View File

@@ -0,0 +1,240 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      10/08/2014 01:51:50 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#ifndef  DCSURVEY
21
+#define  DCSURVEY
22
+
23
+#include "LemmaObject.h"
24
+#include "DCIPElectrode.h"
25
+
26
+#ifdef HAVE_YAMLCPP
27
+#include "yaml-cpp/yaml.h"
28
+#endif
29
+
30
+#ifdef LEMMAUSEVTK
31
+#include <vtkDataSet.h>
32
+#endif
33
+
34
+namespace Lemma {
35
+
36
+    #define EINFINITY -9999
37
+
38
+    /**
39
+      \brief   Describes a DC survey.
40
+      \details This class aims to encapulate any type of DC survey.
41
+     */
42
+    class DCSurvey : public LemmaObject {
43
+
44
+        friend std::ostream &operator<<(std::ostream &stream,
45
+                const DCSurvey &ob);
46
+
47
+        public:
48
+
49
+        // ====================  LIFECYCLE     =======================
50
+
51
+        /**
52
+         * @copybrief LemmaObject::New()
53
+         * @copydetails LemmaObject::New()
54
+         */
55
+        static DCSurvey* New();
56
+
57
+        /**
58
+         *  @copybrief   LemmaObject::Delete()
59
+         *  @copydetails LemmaObject::Delete()
60
+         */
61
+        void Delete();
62
+
63
+        // ====================  OPERATORS     =======================
64
+
65
+        // ====================  OPERATIONS    =======================
66
+
67
+        /**
68
+         *   Adds new electrode to the survey.
69
+         *   @param[in] Electrode `Pounds' a new Electrode into place.
70
+         *   @return integer index to this electrode.
71
+         *   @note Single electrodes cannot be pulled once they are pounded. The reason for this is that
72
+         *         every index then would become invalid. Furthurmore these are stored in a std::vector and
73
+         *         removing arbitrary items is inefficient.
74
+         *   @see PullElectrodes
75
+         *   @param[in] label is an optional tag for electrode.
76
+         *   @param[in] nodeID is the optional node ID on a mesh
77
+         */
78
+        int PoundElectrode( DCIPElectrode* Electrode, const std::string& label = "NULL", const int& nodeID=-1 );
79
+
80
+        /** Alternative Factory method of setting electrodes. IN this manner all memoy management
81
+         *  is handled by DCSurvey.
82
+         *  @note there is no logic preventing one from pounding coincident electrodes. Don't do it.
83
+         *  @note Single electrodes cannot be pulled once they are pounded. The reason for this is that
84
+         *         every index then would become invalid. Furthurmore these are stored in a std::vector and
85
+         *         removing arbitrary items is inefficient.
86
+         *  @see PullElectrodes
87
+         *  @param[in] loc is the location of the electrode.
88
+         *  @param[in] label is an optional label for electrode.
89
+         *  @param[in] nodeID is the optional node ID on a mesh
90
+         */
91
+        DCIPElectrode* PoundElectrode( const Vector3r& loc, const std::string& label = "NULL", const int& nodeID=-1  );
92
+
93
+#ifdef LEMMAUSEVTK
94
+        DCIPElectrode* PoundElectrode( const int& nodeID, vtkDataSet* Mesh, const std::string& label = "NULL" );
95
+#endif
96
+
97
+        /**
98
+         *  Pulls all electrodes and removes connections.
99
+         */
100
+        void PullElectrodes();
101
+
102
+        /**
103
+         *   Adds an injection point.
104
+         *   @param[in] A is the positive current electrode
105
+         *   @param[in] B is the negative current electrode
106
+         *   @param[in] J is the current intensity
107
+         *   @see AddInjection(const int& iA, const int& iB, const Real& J)
108
+         *   @see AddInjection(const int& iA, const Real& J)
109
+         *   @see AddInjection(DCIPElectrode* A, const Real& J)
110
+         */
111
+        int AddInjection( DCIPElectrode* A, DCIPElectrode* B, const Real& J);
112
+
113
+        /**
114
+         *   Adds an injection point.
115
+         *   @param[in] A is the positive current electrode.
116
+         *   @param[in] J is the current intensity.
117
+         *   B,  the negative current electrode is taken to be infinity
118
+         *   @see AddInjection(const int& iA, const int& iB, const Real& J)
119
+         *   @see AddInjection(const int& iA, const Real& J)
120
+         *   @see AddInjection(DCIPElectrode* A, DCIPElectrode* B, const Real& J)
121
+         */
122
+        int AddInjection( DCIPElectrode* A, const Real& J );
123
+
124
+        /**
125
+         *   Adds an injection point.
126
+         *   @param[in] A is the positive current electrode index
127
+         *   @param[in] B is the negative current electrode index
128
+         *   @param[in] J is the current intensity
129
+         *   @see AddInjection(DCIPElectrode* A, DCIPElectrode* B, const Real& J)
130
+         *   @see AddInjection(DCIPElectrode* A, const Real& J)
131
+         *   @see AddInjection(const int& iA, const Real& J)
132
+         */
133
+        int AddInjection( const int& iA, const int& iB, const Real& J );
134
+
135
+        /**
136
+         *   Adds an injection point with the negative electrode at infinity.
137
+         *   @param[in] A is the positive current electrode index
138
+         *   @param[in] J is the current intensity
139
+         *   @see AddInjection(DCIPElectrode* A, DCIPElectrode* B, const Real& J)
140
+         *   @see AddInjection(DCIPElectrode* A, const Real& J)
141
+         *   @see AddInjection(const int& iA, const int& iB, const Real& J)
142
+         */
143
+        int AddInjection( const int& iA, const Real& J );
144
+
145
+        /** Adds a potential measurement via the electrode pair comparison \f$ M - N \f$.
146
+         *   @param[in] M is a pointer to the `positive' electrode
147
+         *   @param[in] N is a pointer to the `negative' electrode
148
+         *   @param[in] iJ is the current injection index to associate with this measurement
149
+         */
150
+        void AddMeasurement( const int& iJ, DCIPElectrode* M, DCIPElectrode* N );
151
+
152
+        /** Adds a potential measurement via the electrode pair comparison \f$ M - N \f$.
153
+         *   @param[in] M is the `positive' electrode string label name
154
+         *   @param[in] N is the `negative' electrode string label name
155
+         *   @param[in] iJ is the current injection index to associate with this measurement
156
+         *   @see AddMeasurement( const int& iJ, DCIPElectrode* M, DCIPElectrode* N )
157
+         */
158
+        void AddMeasurement( const int& ij, const std::string& M, const std::string& N);
159
+
160
+        /**
161
+         *  Used to probe for the index and current of an injection
162
+         *  @param[in] ij is the current injection indes
163
+         *  @param[out] ii is the node index
164
+         *  @param[out] jj is the current
165
+         */
166
+        void GetA( const int& ij, int& ii, Real& jj );
167
+
168
+        /**
169
+         *  Used to probe for the index and current of an injection
170
+         *  @param[in] ij is the current injection indes
171
+         *  @param[out] ii is the node index
172
+         *  @param[out] jj is the current
173
+         */
174
+        void GetB( const int& ij, int& ii, Real& jj );
175
+
176
+
177
+        // ====================  ACCESS        =======================
178
+
179
+        // ====================  INQUIRY       =======================
180
+
181
+        #ifdef HAVE_YAMLCPP
182
+        YAML::Node Serialize() const;
183
+        static DCSurvey* DeSerialize(const YAML::Node& node);
184
+        #endif
185
+
186
+        protected:
187
+
188
+        // ====================  LIFECYCLE     =======================
189
+
190
+        /** Default protected constructor, use New */
191
+        DCSurvey (const std::string& name);
192
+
193
+        #ifdef HAVE_YAMLCPP
194
+        /** Default protected constructor, use New */
195
+        DCSurvey (const YAML::Node& node);
196
+        #endif
197
+
198
+        /** Default protected destructor, use Delete */
199
+        ~DCSurvey ();
200
+
201
+        /**
202
+         *  @copybrief   LemmaObject::Release()
203
+         *  @copydetails LemmaObject::Release()
204
+         */
205
+        void Release();
206
+
207
+        private:
208
+
209
+        // ====================  DATA MEMBERS  =========================
210
+
211
+        /** The electrodes */
212
+        std::vector<DCIPElectrode*>                Electrodes;
213
+
214
+        /** Tags for the electrodes, lines etc. Ordered with Electrodes std::vector */
215
+        std::vector<std::string>                   OrderedElectrodeLabels;
216
+
217
+        /** Map of tags for the electrodes, lines etc. */
218
+        std::map<std::string, std::pair<DCIPElectrode*, int> >      ElectrodeLabelMap;
219
+
220
+        /** The A Injection electrodes */
221
+        std::vector<int>     A_Electrodes;
222
+
223
+        /** The A Injection electrodes */
224
+        std::vector<int>     B_Electrodes;
225
+
226
+        /** The A Injection electrodes */
227
+        std::vector<Real>    J_Electrodes;
228
+
229
+        /** First Potential electrodes */
230
+        std::vector< std::vector<int> > M_Electrodes;
231
+
232
+        /** Second Potential electrodes */
233
+        std::vector< std::vector<int> > N_Electrodes;
234
+
235
+    }; // -----  end of class  DCSurvey  -----
236
+
237
+
238
+}		// -----  end of Lemma  name  -----
239
+
240
+#endif   // ----- #ifndef DCSURVEY  -----

+ 112
- 0
LemmaCore/include/FHTKey.h View File

@@ -0,0 +1,112 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      02/11/2014 03:33:08 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+
21
+#ifndef  FHTKEY_INC
22
+#define  FHTKEY_INC
23
+
24
+#include "hankeltransform.h"
25
+
26
+namespace Lemma {
27
+
28
+    /**
29
+      \brief   Impliments the fast Hankel transform as outlines by Key 2011
30
+      \details This filter uses 61, 121, or 201 filter points and supports both lagged and related
31
+                kernel arguments. This algorithm is a port of code carrying the following copyright and
32
+                restriction:
33
+                %------------------------------------------------------------------%
34
+                % Copyright (c) 2012 by the Society of Exploration Geophysicists.  %
35
+                % For more information, go to http://software.seg.org/2012/0003 .  %
36
+                % You must read and accept usage terms at:                         %
37
+                % http://software.seg.org/disclaimer.txt before use.               %
38
+                %------------------------------------------------------------------%
39
+     */
40
+    class FHTKey : public HankelTransform {
41
+
42
+        friend std::ostream &operator<<(std::ostream &stream,
43
+                const FHTKey &ob);
44
+
45
+        public:
46
+
47
+        // ====================  LIFECYCLE     =======================
48
+
49
+        /**
50
+         * @copybrief LemmaObject::New()
51
+         * @copydetails LemmaObject::New()
52
+         */
53
+        static FHTKey* New();
54
+
55
+        /**
56
+         *  @copybrief   LemmaObject::Delete()
57
+         *  @copydetails LemmaObject::Delete()
58
+         */
59
+        void Delete();
60
+
61
+        // ====================  OPERATORS     =======================
62
+
63
+        // ====================  OPERATIONS    =======================
64
+
65
+        Complex Zgauss(const int &ikk, const EMMODE &imode,
66
+                            const int &itype, const Real &rho,
67
+                            const Real &wavef, KernelEm1DBase *Kernel);
68
+
69
+        /// Computes related kernels, if applicable, otherwise this is
70
+        /// just a dummy function.
71
+        void ComputeRelated(const Real& rho, KernelEm1DBase* Kernel);
72
+
73
+        void ComputeRelated(const Real& rho, std::vector< KernelEm1DBase* > KernelVec);
74
+
75
+        void ComputeRelated(const Real& rho, KernelEM1DManager* KernelManager);
76
+
77
+        // ====================  ACCESS        =======================
78
+
79
+        // ====================  INQUIRY       =======================
80
+
81
+        protected:
82
+
83
+        // ====================  LIFECYCLE     =======================
84
+
85
+        /** Default protected constructor, use New */
86
+        FHTKey (const std::string& name);
87
+
88
+        /** Default protected destructor, use Delete */
89
+        ~FHTKey ();
90
+
91
+        /**
92
+         *  @copybrief   LemmaObject::Release()
93
+         *  @copydetails LemmaObject::Release()
94
+         */
95
+        void Release();
96
+
97
+        private:
98
+
99
+        // ====================  DATA MEMBERS  =========================
100
+
101
+        // Shared Filter Weights
102
+		static const Eigen::Matrix<Real, 201, 3>  WT201;
103
+
104
+        /// Holds answer, dimensions are NumConv, and NumberRelated.
105
+        Eigen::Matrix<Complex, Eigen::Dynamic, Eigen::Dynamic> Zans;
106
+
107
+    }; // -----  end of class  FHTKey  -----
108
+
109
+}		// -----  end of Lemma  name  -----
110
+
111
+#endif   // ----- #ifndef FHTKEY_INC  -----
112
+

+ 112
- 0
LemmaCore/include/FHTKey101.h View File

@@ -0,0 +1,112 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      02/11/2014 03:33:08 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+
21
+#ifndef  FHTKEY101_INC
22
+#define  FHTKEY101_INC
23
+
24
+#include "hankeltransform.h"
25
+
26
+namespace Lemma {
27
+
28
+    /**
29
+      \brief   Impliments the fast Hankel transform as outlines by Key 2011
30
+      \details This filter uses 51, 101, or 201 filter points and supports both lagged and related
31
+                kernel arguments. This algorithm is a port of code carrying the following copyright and
32
+                restriction:
33
+                %------------------------------------------------------------------%
34
+                % Copyright (c) 2012 by the Society of Exploration Geophysicists.  %
35
+                % For more information, go to http://software.seg.org/2012/0003 .  %
36
+                % You must read and accept usage terms at:                         %
37
+                % http://software.seg.org/disclaimer.txt before use.               %
38
+                %------------------------------------------------------------------%
39
+     */
40
+    class FHTKey101 : public HankelTransform {
41
+
42
+        friend std::ostream &operator<<(std::ostream &stream,
43
+                const FHTKey101 &ob);
44
+
45
+        public:
46
+
47
+        // ====================  LIFECYCLE     =======================
48
+
49
+        /**
50
+         * @copybrief LemmaObject::New()
51
+         * @copydetails LemmaObject::New()
52
+         */
53
+        static FHTKey101* New();
54
+
55
+        /**
56
+         *  @copybrief   LemmaObject::Delete()
57
+         *  @copydetails LemmaObject::Delete()
58
+         */
59
+        void Delete();
60
+
61
+        // ====================  OPERATORS     =======================
62
+
63
+        // ====================  OPERATIONS    =======================
64
+
65
+        Complex Zgauss(const int &ikk, const EMMODE &imode,
66
+                            const int &itype, const Real &rho,
67
+                            const Real &wavef, KernelEm1DBase *Kernel);
68
+
69
+        /// Computes related kernels, if applicable, otherwise this is
70
+        /// just a dummy function.
71
+        void ComputeRelated(const Real& rho, KernelEm1DBase* Kernel);
72
+
73
+        void ComputeRelated(const Real& rho, std::vector< KernelEm1DBase* > KernelVec);
74
+
75
+        void ComputeRelated(const Real& rho, KernelEM1DManager* KernelManager);
76
+
77
+        // ====================  ACCESS        =======================
78
+
79
+        // ====================  INQUIRY       =======================
80
+
81
+        protected:
82
+
83
+        // ====================  LIFECYCLE     =======================
84
+
85
+        /** Default protected constructor, use New */
86
+        FHTKey101 (const std::string& name);
87
+
88
+        /** Default protected destructor, use Delete */
89
+        ~FHTKey101 ();
90
+
91
+        /**
92
+         *  @copybrief   LemmaObject::Release()
93
+         *  @copydetails LemmaObject::Release()
94
+         */
95
+        void Release();
96
+
97
+        private:
98
+
99
+        // ====================  DATA MEMBERS  =========================
100
+
101
+        // Shared Filter Weights
102
+		static const Eigen::Matrix<Real, 101, 3>  WT101;
103
+
104
+        /// Holds answer, dimensions are NumConv, and NumberRelated.
105
+        Eigen::Matrix<Complex, Eigen::Dynamic, Eigen::Dynamic> Zans;
106
+
107
+    }; // -----  end of class  FHTKey101  -----
108
+
109
+}		// -----  end of Lemma  name  -----
110
+
111
+#endif   // ----- #ifndef FHTKEY101_INC  -----
112
+

+ 112
- 0
LemmaCore/include/FHTKey51.h View File

@@ -0,0 +1,112 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      02/11/2014 03:33:08 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+
21
+#ifndef  FHTKEY51_INC
22
+#define  FHTKEY51_INC
23
+
24
+#include "hankeltransform.h"
25
+
26
+namespace Lemma {
27
+
28
+    /**
29
+      \brief   Impliments the fast Hankel transform as outlines by Key 2011
30
+      \details This filter uses 51, 101, or 201 filter points and supports both lagged and related
31
+                kernel arguments. This algorithm is a port of code carrying the following copyright and
32
+                restriction:
33
+                %------------------------------------------------------------------%
34
+                % Copyright (c) 2012 by the Society of Exploration Geophysicists.  %
35
+                % For more information, go to http://software.seg.org/2012/0003 .  %
36
+                % You must read and accept usage terms at:                         %
37
+                % http://software.seg.org/disclaimer.txt before use.               %
38
+                %------------------------------------------------------------------%
39
+     */
40
+    class FHTKey51 : public HankelTransform {
41
+
42
+        friend std::ostream &operator<<(std::ostream &stream,
43
+                const FHTKey51 &ob);
44
+
45
+        public:
46
+
47
+        // ====================  LIFECYCLE     =======================
48
+
49
+        /**
50
+         * @copybrief LemmaObject::New()
51
+         * @copydetails LemmaObject::New()
52
+         */
53
+        static FHTKey51* New();
54
+
55
+        /**
56
+         *  @copybrief   LemmaObject::Delete()
57
+         *  @copydetails LemmaObject::Delete()
58
+         */
59
+        void Delete();
60
+
61
+        // ====================  OPERATORS     =======================
62
+
63
+        // ====================  OPERATIONS    =======================
64
+
65
+        Complex Zgauss(const int &ikk, const EMMODE &imode,
66
+                            const int &itype, const Real &rho,
67
+                            const Real &wavef, KernelEm1DBase *Kernel);
68
+
69
+        /// Computes related kernels, if applicable, otherwise this is
70
+        /// just a dummy function.
71
+        void ComputeRelated(const Real& rho, KernelEm1DBase* Kernel);
72
+
73
+        void ComputeRelated(const Real& rho, std::vector< KernelEm1DBase* > KernelVec);
74
+
75
+        void ComputeRelated(const Real& rho, KernelEM1DManager* KernelManager);
76
+
77
+        // ====================  ACCESS        =======================
78
+
79
+        // ====================  INQUIRY       =======================
80
+
81
+        protected:
82
+
83
+        // ====================  LIFECYCLE     =======================
84
+
85
+        /** Default protected constructor, use New */
86
+        FHTKey51 (const std::string& name);
87
+
88
+        /** Default protected destructor, use Delete */
89
+        ~FHTKey51 ();
90
+
91
+        /**
92
+         *  @copybrief   LemmaObject::Release()
93
+         *  @copydetails LemmaObject::Release()
94
+         */
95
+        void Release();
96
+
97
+        private:
98
+
99
+        // ====================  DATA MEMBERS  =========================
100
+
101
+        // Shared Filter Weights
102
+		static const Eigen::Matrix<Real, 51, 3>  WT51;
103
+
104
+        /// Holds answer, dimensions are NumConv, and NumberRelated.
105
+        Eigen::Matrix<Complex, Eigen::Dynamic, Eigen::Dynamic> Zans;
106
+
107
+    }; // -----  end of class  FHTKey51  -----
108
+
109
+}		// -----  end of Lemma  name  -----
110
+
111
+#endif   // ----- #ifndef FHTKEY51_INC  -----
112
+

+ 76
- 0
LemmaCore/include/GridReader.h View File

@@ -0,0 +1,76 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
6
+ */
7
+
8
+/**
9
+  @file
10
+  @date      09/23/2013 11:25:11 AM
11
+  @version   $Id$
12
+  @author    Trevor Irons (ti)
13
+  @email     Trevor.Irons@xri-geo.com
14
+  @copyright Copyright (c) 2013, XRI Geophysics, LLC
15
+  @copyright Copyright (c) 2013, Trevor Irons
16
+ **/
17
+
18
+#ifndef  GRIDREADER_INC
19
+#define  GRIDREADER_INC
20
+
21
+#include "LemmaObject.h"
22
+#include "grid.h"
23
+
24
+namespace Lemma {
25
+
26
+    /**
27
+      @class
28
+      \brief   Abstract class for grid readers.
29
+      \details Provides a consistent interface for reading grid files in Lemma.
30
+     */
31
+    class GridReader : public LemmaObject {
32
+
33
+        friend std::ostream &operator<<(std::ostream &stream,
34
+                const GridReader &ob) {
35
+            stream << *(LemmaObject*)(&ob);
36
+            return stream;
37
+        }
38
+
39
+        public:
40
+
41
+            // ====================  LIFECYCLE     =======================
42
+
43
+            // ====================  OPERATORS     =======================
44
+
45
+            // ====================  OPERATIONS    =======================
46
+
47
+            virtual void ReadASCIIGridFile( const std::string& name )=0;
48
+
49
+            virtual Grid* GetGrid( )=0;
50
+
51
+            // ====================  ACCESS        =======================
52
+
53
+            // ====================  INQUIRY       =======================
54
+
55
+        protected:
56
+
57
+            // ====================  LIFECYCLE     =======================
58
+
59
+            /** Default protected constructor, use New */
60
+            GridReader (const std::string& name) : LemmaObject(name) {
61
+            }
62
+
63
+            /** Default protected constructor, use Delete */
64
+            ~GridReader () {
65
+            }
66
+
67
+        private:
68
+
69
+            // ====================  DATA MEMBERS  =========================
70
+
71
+    }; // -----  end of class  GridReader  -----
72
+
73
+
74
+}		// -----  end of Lemma  name  -----
75
+
76
+#endif   // ----- #ifndef GRIDREADER_INC  -----

+ 87
- 0
LemmaCore/include/GroundedElectricDipole.h View File

@@ -0,0 +1,87 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      01/29/2014 06:59:39 AM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+
21
+#ifndef  GROUNDEDELECTRICDIPOLE_INC
22
+#define  GROUNDEDELECTRICDIPOLE_INC
23
+
24
+#include "dipolesource.h"
25
+
26
+namespace Lemma {
27
+
28
+    /**
29
+      \brief   Grounded electric dipole
30
+      \details Used to model an idealised grounded electrid dipole of arbitrary
31
+               polarisation.
32
+     */
33
+    class GroundedElectricDipole : public DipoleSource {
34
+
35
+        friend std::ostream &operator<<(std::ostream &stream,
36
+                const GroundedElectricDipole &ob);
37
+
38
+        public:
39
+
40
+        // ====================  LIFECYCLE     =======================
41
+
42
+        /**
43
+         * @copybrief LemmaObject::New()
44
+         * @copydetails LemmaObject::New()
45
+         */
46
+        static GroundedElectricDipole* New();
47
+
48
+        /**
49
+         *  @copybrief   LemmaObject::Delete()
50
+         *  @copydetails LemmaObject::Delete()
51
+         */
52
+        void Delete();
53
+
54
+        // ====================  OPERATORS     =======================
55
+
56
+        // ====================  OPERATIONS    =======================
57
+
58
+        // ====================  ACCESS        =======================
59
+
60
+        // ====================  INQUIRY       =======================
61
+
62
+        protected:
63
+
64
+        // ====================  LIFECYCLE     =======================
65
+
66
+        /** Default protected constructor, use New */
67
+        GroundedElectricDipole (const std::string& name);
68
+
69
+        /** Default protected destructor, use Delete */
70
+        ~GroundedElectricDipole ();
71
+
72
+        /**
73
+         *  @copybrief   LemmaObject::Release()
74
+         *  @copydetails LemmaObject::Release()
75
+         */
76
+        void Release();
77
+
78
+        private:
79
+
80
+        // ====================  DATA MEMBERS  =========================
81
+
82
+    }; // -----  end of class  GroundedElectricDipole  -----
83
+
84
+}		// -----  end of Lemma  name  -----
85
+
86
+#endif   // ----- #ifndef GROUNDEDELECTRICDIPOLE_INC  -----
87
+

+ 105
- 0
LemmaCore/include/LayeredEarthEMReader.h View File

@@ -0,0 +1,105 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      09/27/2013 01:44:36 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2013, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2013, Trevor Irons
18
+ */
19
+
20
+#ifndef  LAYEREDEARTHEMREADER_INC
21
+#define  LAYEREDEARTHEMREADER_INC
22
+
23
+#include "LemmaObject.h"
24
+#include "ASCIIParser.h"
25
+#include "layeredearthem.h"
26
+
27
+namespace Lemma {
28
+
29
+    /**
30
+      \brief
31
+      \details
32
+     */
33
+    class LayeredEarthEMReader : public LemmaObject {
34
+
35
+        friend std::ostream &operator<<(std::ostream &stream,
36
+                const LayeredEarthEMReader &ob);
37
+
38
+        public:
39
+
40
+        // ====================  LIFECYCLE     =======================
41
+
42
+        /**
43
+         * @copybrief LemmaObject::New()
44
+         * @copydetails LemmaObject::New()
45
+         */
46
+        static LayeredEarthEMReader* New();
47
+
48
+        /**
49
+         *  @copybrief   LemmaObject::Delete()
50
+         *  @copydetails LemmaObject::Delete()
51
+         */
52
+        void Delete();
53
+
54
+        // ====================  OPERATORS     =======================
55
+
56
+        // ====================  OPERATIONS    =======================
57
+
58
+        /** Reads ASCII input file. The format is as follows
59
+@code
60
+4           // Number of NON-AIR layers
61
+200   10    // resistivity, thickness layer 1 [Ohm-m] [m]
62
+20    10    // resistivity, thickness layer 2 [Ohm-m] [m]
63
+1120  10    // resistivity, thickness layer 3 [Ohm-m] [m]
64
+200         // resistivity of bottom layer [Ohm-m]
65
+@endcode
66
+         * @param[in] name is the filename
67
+         */
68
+        void ReadASCIIInputFile( const std::string& name );
69
+
70
+        // ====================  ACCESS        =======================
71
+
72
+        /** @return the pointer address of the LayeredEarthEM
73
+         */
74
+        LayeredEarthEM* GetLayeredEarth();
75
+
76
+        // ====================  INQUIRY       =======================
77
+
78
+        protected:
79
+
80
+        // ====================  LIFECYCLE     =======================
81
+
82
+        /** Default protected constructor, use New */
83
+        LayeredEarthEMReader (const std::string& name);
84
+
85
+        /** Default protected destructor, use Delete */
86
+        ~LayeredEarthEMReader ();
87
+
88
+        /**
89
+         *  @copybrief   LemmaObject::Release()
90
+         *  @copydetails LemmaObject::Release()
91
+         */
92
+        void Release();
93
+
94
+        private:
95
+
96
+        // ====================  DATA MEMBERS  =========================
97
+
98
+        LayeredEarthEM*         LayEarth;
99
+
100
+    }; // -----  end of class  LayeredEarthEMReader  -----
101
+
102
+
103
+}		// -----  end of Lemma  name  -----
104
+
105
+#endif   // ----- #ifndef LAYEREDEARTHEMREADER_INC  -----

+ 223
- 0
LemmaCore/include/LemmaObject.h View File

@@ -0,0 +1,223 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     06/25/2009
11
+  @version  $Id: LemmaObject.h 199 2014-12-29 19:25:20Z tirons $
12
+ **/
13
+
14
+#ifndef __LEMMAOBJECT_H
15
+#define __LEMMAOBJECT_H
16
+
17
+#include "helper.h"
18
+#include "lemma.h"
19
+
20
+#ifdef HAVE_YAMLCPP
21
+#include "yaml-cpp/yaml.h"
22
+#endif
23
+
24
+namespace Lemma {
25
+
26
+// ==========================================================================
27
+//        Class:  LemmaObject
28
+/** \brief    Abstract class providing simple reference counting and memory
29
+  *           management.
30
+  * \details  Since objects can be members of other objects, and may be
31
+  *           of multiple objects it becomes useful to count the number of
32
+  *           Classes an object is a member of. Objects cannot be deleted that
33
+  *           contain references to other objects.
34
+  */
35
+// ==========================================================================
36
+
37
+/** Base class for all of Lemma. Reference counted object provides simple
38
+ * reference counting. This allows for much easier maintainance of shared
39
+ * objects among classes.
40
+ */
41
+class LemmaObject {
42
+
43
+    /** Recursively prints information about this object
44
+     */
45
+    friend std::ostream &operator<<(std::ostream &stream, const LemmaObject &ob);
46
+
47
+    #ifdef HAVE_YAMLCPP
48
+    friend YAML::Emitter& operator << (YAML::Emitter& out, const LemmaObject &ob) ;
49
+    #endif
50
+
51
+    friend class DeleteObjectWithReferences;
52
+
53
+    public:
54
+
55
+        // Needed because some derived classes have Eigen vectors as members,
56
+        // causing alignment issues when vectorisation is enabled.
57
+        EIGEN_MAKE_ALIGNED_OPERATOR_NEW
58
+
59
+        // ====================  OPERATORS     ==============================
60
+
61
+        // ====================  OPERATIONS    ==============================
62
+
63
+        /**
64
+         * Deletes this objects self reference. If there are no remaining
65
+         * references, Release is called freeing all memory. Otherwise Release
66
+         * is called if/when the last reference is removed.
67
+         */
68
+        virtual void Delete()=0;
69
+
70
+        /** Attaches this object to another object */
71
+        void AttachTo(LemmaObject *);
72
+
73
+        /** Detaches this object from another object */
74
+        void DetachFrom(LemmaObject *);
75
+
76
+        // ====================  ACCESS        ==============================
77
+
78
+        // ====================  INQUIRY       ==============================
79
+
80
+        /** Returns the number of objects attached to this. */
81
+        unsigned int GetNumberOfReferences();
82
+
83
+        /** Returns address(s) to class(es) of which this is a member
84
+         */
85
+        std::vector<LemmaObject*> GetReferences();
86
+
87
+        /** Returns name of this model */
88
+        std::string GetName();
89
+
90
+        #ifdef HAVE_YAMLCPP
91
+        /**
92
+         *  Uses YAML to serialize this object.
93
+         *  @return a YAML::Node
94
+         *  FOR NOT LemmaObject does not write out any YAML info,
95
+         *      in the future the reference count could be logged? But the utility
96
+         *      of that is minimal.
97
+         *  @note Not every Lemma class needs to be Serializable, for instance HankelTransform
98
+         *        classes will never need to be Serialized. There may be a need to differentiate these
99
+         *        two families in to a LemmaInternalClass without serializing and perhaps this class for
100
+         *        all external classes that might need to be serialized.
101
+         */
102
+        virtual YAML::Node Serialize() const{
103
+            return YAML::Node();
104
+        };
105
+        #endif
106
+
107
+    protected:
108
+
109
+        // ====================  LIFECYCLE     ==============================
110
+
111
+        /** Protected default constructor. This is an abstract class and
112
+         *  cannot be instantiated.
113
+         */
114
+        LemmaObject (const std::string &name);
115
+
116
+        #ifdef HAVE_YAMLCPP
117
+        /** Protected DeDerializing constructor, use factory DeSerialize  method*/
118
+        LemmaObject (const YAML::Node& node);
119
+        #endif
120
+
121
+        // ====================  DATA MEMBERS  ==============================
122
+        /** Protected default destructor. This is an abstract class and
123
+         *  cannot be instantiated.
124
+         */
125
+        virtual ~LemmaObject ();
126
+
127
+        /**
128
+         *  Releases all memory back to the heap. Just calls the protected
129
+         *  destructor at the derived class level.
130
+         */
131
+        virtual void Release()=0;
132
+
133
+        // ====================  OPERATIONS    ==============================
134
+
135
+        // ====================  DATA MEMBERS  ==============================
136
+
137
+        /** Number of other classes claiming this as a member. */
138
+        unsigned int NumberOfReferences;
139
+
140
+        /** List of the addresses of the other classes referencing this as a
141
+         * member
142
+         */
143
+        std::vector<LemmaObject *> RefPtrList;
144
+
145
+        /** Stores an ASCII string representation of the class name */
146
+        std::string Name;
147
+
148
+}; // -----  end of class  LemmaObject  -----
149
+
150
+    /////////////////////////////////////////////////////////////////
151
+    // BOILERPLATE MACROS
152
+    #define DESERIALIZECHECK( node, Object ) { \
153
+        if (node.Tag() != Object->GetName()) {  \
154
+            throw  DeSerializeTypeMismatch(Object, node.Tag()) ; \
155
+        } } \
156
+
157
+    /////////////////////////////////////////////////////////////////
158
+    // Error Classes
159
+
160
+    /** Error called when ReferenceCounting breaks. If an object is
161
+     * deleted that has refences still, this is thrown.
162
+     */
163
+    class DeleteObjectWithReferences : public std::runtime_error {
164
+
165
+        public:
166
+
167
+            /** Call this method internally when an object is deleted with
168
+             * references.
169
+             */
170
+            DeleteObjectWithReferences(LemmaObject *ptr);
171
+
172
+            /** @deprecated this error may be thrown, but the error message is much
173
+            * less insightful than
174
+            * DeleteObjectWithReferences(LemmaObject* ptr).
175
+            */
176
+            DeleteObjectWithReferences( );
177
+    };
178
+
179
+
180
+    /** Error called when DeSerializing breaks. If the node type is not the expected one
181
+     *  this error is thown.
182
+     */
183
+    class DeSerializeTypeMismatch : public std::runtime_error {
184
+        public:
185
+            DeSerializeTypeMismatch(LemmaObject *ptr, const std::string& got);
186
+
187
+    };
188
+
189
+    /** If an assignment is made that is out of bounts, throw this.
190
+     */
191
+    class AssignmentOutOfBounds : public std::runtime_error {
192
+        public:
193
+            /** Throw when an assignment is out of bounds.
194
+             *  @param[in] ptr is a pointer to the class throwing the exception.
195
+             */
196
+            AssignmentOutOfBounds(LemmaObject *ptr);
197
+    };
198
+
199
+    /** If a pointer to a class is requested, but it is NULL valued, throw this
200
+     */
201
+    class RequestToReturnNullPointer : public std::runtime_error {
202
+        public:
203
+            /** Thrown when the pointer is NULL
204
+             *  @param[in] ptr is a pointer to the class throwing the exception.
205
+             */
206
+            RequestToReturnNullPointer(LemmaObject *ptr);
207
+    };
208
+
209
+    /** If an error in opening a .mat file is encountered, throw this.
210
+     */
211
+    class MatFileCannotBeOpened : public std::runtime_error {
212
+        /** thown when a mat file fails to be opened.
213
+         */
214
+            public: MatFileCannotBeOpened();
215
+    };
216
+
217
+	/** Generic file I/O error. */
218
+	class GenericFileIOError : public std::runtime_error {
219
+			public: GenericFileIOError(LemmaObject *ptr, const std::string &filename);
220
+	};
221
+
222
+}
223
+#endif // __LEMMAOBJECT_H

+ 88
- 0
LemmaCore/include/MagneticDipole.h View File

@@ -0,0 +1,88 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      09/25/2013 08:20:14 AM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2013, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2013, Trevor Irons
18
+ */
19
+
20
+#ifndef  MAGNETICDIPOLE_INC
21
+#define  MAGNETICDIPOLE_INC
22
+
23
+#include "dipolesource.h"
24
+
25
+namespace Lemma {
26
+
27
+/**
28
+  @class
29
+  \brief   Magnetic Dipole
30
+  \details Used to model an idealised magnetic dipole of arbitrary
31
+           polarisation.
32
+ */
33
+class MagneticDipole : public DipoleSource {
34
+
35
+    friend std::ostream &operator<<(std::ostream &stream,
36
+            const MagneticDipole &ob);
37
+
38
+    public:
39
+
40
+    // ====================  LIFECYCLE     =======================
41
+
42
+    /**
43
+     * @copybrief LemmaObject::New()
44
+     * @copydetails LemmaObject::New()
45
+     */
46
+    static MagneticDipole* New();
47
+
48
+    /**
49
+     *  @copybrief   LemmaObject::Delete()
50
+     *  @copydetails LemmaObject::Delete()
51
+     */
52
+    void Delete();
53
+
54
+    // ====================  OPERATORS     =======================
55
+
56
+    // ====================  OPERATIONS    =======================
57
+
58
+    // ====================  ACCESS        =======================
59
+
60
+    // ====================  INQUIRY       =======================
61
+
62
+    protected:
63
+
64
+    // ====================  LIFECYCLE     =======================
65
+
66
+    /** Default protected constructor, use New */
67
+    MagneticDipole (const std::string& name);
68
+
69
+    /** Default protected destructor, use Delete */
70
+    ~MagneticDipole ();
71
+
72
+    /**
73
+     *  @copybrief   LemmaObject::Release()
74
+     *  @copydetails LemmaObject::Release()
75
+     */
76
+    void Release();
77
+
78
+    private:
79
+
80
+    // ====================  DATA MEMBERS  =========================
81
+
82
+    KernelEM1DManager*          Kernels;
83
+
84
+}; // -----  end of class  MagneticDipole  -----
85
+
86
+} // namespace Lemma
87
+
88
+#endif   // ----- #ifndef MAGNETICDIPOLE_INC  -----

+ 109
- 0
LemmaCore/include/ParticleSwarmOptimizer.h View File

@@ -0,0 +1,109 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      01/27/2015 01:50:59 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2015, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2015, Trevor Irons
18
+ */
19
+
20
+#ifndef  PARTICLESWARMOPTIMIZER_INC
21
+#define  PARTICLESWARMOPTIMIZER_INC
22
+
23
+#include "LemmaObject.h"
24
+
25
+namespace Lemma {
26
+
27
+struct Particle{
28
+    Real       fitness;
29
+    VectorXr   best;
30
+};
31
+
32
+/**
33
+  \brief
34
+  \details
35
+ */
36
+class ParticleSwarmOptimizer : public LemmaObject {
37
+
38
+    friend std::ostream &operator<<(std::ostream &stream,
39
+            const ParticleSwarmOptimizer &ob);
40
+
41
+    public:
42
+
43
+    // ====================  LIFECYCLE     =======================
44
+
45
+    /**
46
+     * @copybrief LemmaObject::New()
47
+     * @copydetails LemmaObject::New()
48
+     */
49
+    static ParticleSwarmOptimizer* New();
50
+
51
+    /**
52
+     *  @copybrief   LemmaObject::Delete()
53
+     *  @copydetails LemmaObject::Delete()
54
+     */
55
+    void Delete();
56
+
57
+    // ====================  OPERATORS     =======================
58
+
59
+    // ====================  OPERATIONS    =======================
60
+
61
+    // ====================  ACCESS        =======================
62
+
63
+    // ====================  INQUIRY       =======================
64
+
65
+#ifdef HAVE_YAMLCPP
66
+    /**
67
+     *  Uses YAML to serialize this object.
68
+     *  @return a YAML::Node
69
+     */
70
+    YAML::Node Serialize() const;
71
+
72
+    /**
73
+     *   Constructs an object from a YAML::Node.
74
+     */
75
+    static ParticleSwarmOptimizer* DeSerialize(const YAML::Node& node);
76
+#endif
77
+
78
+    protected:
79
+
80
+    // ====================  LIFECYCLE     =======================
81
+
82
+    /** Default protected constructor, use New */
83
+    ParticleSwarmOptimizer (const std::string& name);
84
+
85
+#ifdef HAVE_YAMLCPP
86
+    /** Protected DeDerializing constructor, use factory DeSerialize  method*/
87
+    ParticleSwarmOptimizer (const YAML::Node& node);
88
+#endif
89
+
90
+    /** Default protected destructor, use Delete */
91
+    ~ParticleSwarmOptimizer ();
92
+
93
+    /**
94
+     *  @copybrief   LemmaObject::Release()
95
+     *  @copydetails LemmaObject::Release()
96
+     */
97
+    void Release();
98
+
99
+    private:
100
+
101
+    // ====================  DATA MEMBERS  =========================
102
+
103
+}; // -----  end of class  ParticleSwarmOptimizer  -----
104
+
105
+
106
+}		// -----  end of Lemma  name  -----
107
+
108
+#endif   // ----- #ifndef PARTICLESWARMOPTIMIZER_INC  -----
109
+

+ 169
- 0
LemmaCore/include/PolygonalWireAntenna.h View File

@@ -0,0 +1,169 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     05/18/2010
11
+  @version  $Id: PolygonalWireAntenna.h 211 2015-02-27 05:43:26Z tirons $
12
+ **/
13
+
14
+#include "WireAntenna.h"
15
+
16
+#ifndef  POLYGONALWIREANTENNA_INC
17
+#define  POLYGONALWIREANTENNA_INC
18
+
19
+namespace Lemma {
20
+
21
+    // ===================================================================
22
+    //        Class:  PolygonalWireAntenna
23
+    /// \brief   Class representing polygonal wire antennae.
24
+    /// \details For EM calculations, dipoles representing this loop are
25
+    ///    created dynamically, depending on receiver location.
26
+    /// @todo enforce minimum dipole moment.
27
+    // ===================================================================
28
+    class PolygonalWireAntenna : public WireAntenna {
29
+
30
+        friend std::ostream &operator<<(std::ostream &stream,
31
+                const PolygonalWireAntenna &ob);
32
+
33
+        public:
34
+
35
+            // ====================  LIFECYCLE     =======================
36
+
37
+            /**
38
+             * Declares all memory and returns a new instance.
39
+             */
40
+            static PolygonalWireAntenna* New();
41
+
42
+            /**
43
+             * @copybrief LemmaObject::Delete()
44
+             * @copydetails LemmaObject::Delete()
45
+             */
46
+            void Delete();
47
+
48
+            /// Makes a deep copy of this antenna with all connections except
49
+            /// the dipole approximation.
50
+            PolygonalWireAntenna* Clone();
51
+
52
+            // ====================  OPERATORS     =======================
53
+
54
+            // ====================  OPERATIONS    =======================
55
+
56
+            /// Approximates with ungrounded electrical dipoles, such that
57
+            /// minDipoleRatio is satisfied.
58
+            virtual void ApproximateWithElectricDipoles(const Vector3r &rp);
59
+
60
+            /** Sets the minimum ratio for dipole moments to be used to
61
+             * approximate the loop. A smaller ratio yields a more accurate
62
+             * result, but is more expensive. Default is (1/5).
63
+             */
64
+            void SetMinDipoleRatio(const Real& ratio);
65
+
66
+            /** Sets the minimum moment for dipole moments to be used to
67
+             * approximate the loop.
68
+             */
69
+            void SetMinDipoleMoment(const Real& m);
70
+
71
+            /** Sets the minimum moment for dipole moments to be used to
72
+             * approximate the loop.
73
+             */
74
+            void SetMaxDipoleMoment(const Real& m);
75
+
76
+            // ====================  ACCESS        =======================
77
+
78
+            // ====================  INQUIRY       =======================
79
+
80
+            #ifdef HAVE_YAMLCPP
81
+            /**
82
+             *  Uses YAML to serialize this object.
83
+             *  @return a YAML::Node
84
+             */
85
+            YAML::Node Serialize() const;
86
+
87
+            /**
88
+             *   Constructs an object from a YAML::Node.
89
+             */
90
+            static PolygonalWireAntenna* DeSerialize(const YAML::Node& node);
91
+            #endif
92
+
93
+        protected:
94
+
95
+            // ====================  LIFECYCLE     =======================
96
+
97
+            /// Default protected constructor.
98
+            PolygonalWireAntenna (const std::string& name);
99
+
100
+#ifdef HAVE_YAMLCPP
101
+            /// Default protected constructor.
102
+            PolygonalWireAntenna (const YAML::Node& node);
103
+#endif
104
+
105
+            /// Default protected constructor.
106
+            ~PolygonalWireAntenna ();
107
+
108
+            /**
109
+             * @copybrief LemmaObject::Release()
110
+             * @copydetails LemmaObject::Release()
111
+             */
112
+            void Release();
113
+
114
+            // ====================  DATA MEMBERS  =======================
115
+
116
+            /// minimum ratio of dipole moment to distance to receiver point
117
+            Real minDipoleRatio;
118
+
119
+            /// Maximum dipole moment allowed
120
+            Real minDipoleMoment;
121
+
122
+            /// Maximum dipole moment allowed
123
+            Real maxDipoleMoment;
124
+
125
+            /// appends
126
+            void PushXYZDipoles(const Vector3r &step, const Vector3r &cp,
127
+                            const Vector3r &dir,
128
+                            std::vector<DipoleSource*> &Dipoles) ;
129
+
130
+            /// corrects for overstep
131
+            void CorrectOverstepXYZDipoles(const Vector3r &step,
132
+                            const Vector3r &cp,
133
+                            const Vector3r &dir,
134
+                            std::vector<DipoleSource*> &Dipoles );
135
+
136
+            // ====================  OPERATIONS    =======================
137
+
138
+
139
+            /// Returns the nearest point on a line segment to another point.
140
+            /// if the point is not on the line-segment, return the
141
+            /// nearest end-point
142
+            /// @param[in] p0, p1 define the line segement
143
+            /// @param[in] rp is a point in space. The function returns the
144
+            /// closest point on the line to this point.
145
+            /// @return The point (Lemma::Vector3r) on the line defined by p0,
146
+            /// and p1, closest to rp
147
+            Vector3r ClosestPointOnLine(const Vector3r &p0, const Vector3r &p1,
148
+                            const Vector3r &rp);
149
+
150
+            /// Interpolates dipoles along line segment defined by p0 and p1.
151
+            void InterpolateLineSegment(const Vector3r &p0, const Vector3r &p1,
152
+                            const Vector3r &rp);
153
+
154
+
155
+            /// List of the dipoles
156
+            //std::vector<DipoleSource*>           Dipoles;
157
+
158
+            /// Points that define this loop
159
+            //Vector3Xr                            Points;
160
+
161
+        private:
162
+
163
+            Vector3r                               rRepeat;
164
+
165
+    }; // -----  end of class  PolygonalWireAntenna  -----
166
+
167
+}       // -----  end of Lemma  name  -----
168
+
169
+#endif   // ----- #ifndef POLYGONALWIREANTENNA_INC  -----

+ 197
- 0
LemmaCore/include/QWEKey.h View File

@@ -0,0 +1,197 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      02/12/2014 10:20:18 AM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#ifndef  QWEKEY_INC
21
+#define  QWEKEY_INC
22
+
23
+#include	"hankeltransform.h"
24
+#include    <Eigen/Eigenvalues>
25
+#ifdef HAVEBOOSTSPECIALFUNCTIONS
26
+#include "boost/math/special_functions.hpp"
27
+#include "boost/math/special_functions/bessel.hpp"
28
+#endif
29
+
30
+namespace Lemma {
31
+
32
+    /** breakpoint to use in division of domain, based on zeros of bessel function or
33
+        regular nPi spacing.
34
+     */
35
+    enum sZeroType{J0, J1, NPI};
36
+
37
+    /**
38
+      \brief  Port of Key's quadrature with extrapolation Hankel transform algorithm.
39
+      \details Details of the algorithm can be found in Key2011. This code is a port
40
+               of the published algorithm, which contains the following notice:
41
+        %------------------------------------------------------------------%
42
+        % Copyright (c) 2012 by the Society of Exploration Geophysicists.  %
43
+        % For more information, go to http://software.seg.org/2012/0003 .  %
44
+        % You must read and accept usage terms at:                         %
45
+        % http://software.seg.org/disclaimer.txt before use.               %
46
+        %------------------------------------------------------------------%
47
+     */
48
+    class QWEKey : public HankelTransform {
49
+
50
+        friend std::ostream &operator<<(std::ostream &stream,
51
+                const QWEKey &ob);
52
+
53
+        public:
54
+
55
+        // ====================  LIFECYCLE     =======================
56
+
57
+        /**
58
+         * @copybrief LemmaObject::New()
59
+         * @copydetails LemmaObject::New()
60
+         */
61
+        static QWEKey* New();
62
+
63
+        /**
64
+         *  @copybrief   LemmaObject::Delete()
65
+         *  @copydetails LemmaObject::Delete()
66
+         */
67
+        void Delete();
68
+
69
+        // ====================  OPERATORS     =======================
70
+
71
+        void TestPrivate(const int& N);
72
+
73
+        // ====================  OPERATIONS    =======================
74
+
75
+
76
+        Complex Zgauss(const int &ikk, const EMMODE &imode,
77
+                            const int &itype, const Real &rho,
78
+                            const Real &wavef, KernelEm1DBase *Kernel);
79
+
80
+        /// Computes related kernels, if applicable, otherwise this is
81
+        /// just a dummy function.
82
+        void ComputeRelated(const Real& rho, KernelEm1DBase* Kernel);
83
+
84
+        void ComputeRelated(const Real& rho, std::vector< KernelEm1DBase* > KernelVec);
85
+
86
+        void ComputeRelated(const Real& rho, KernelEM1DManager* KernelManager);
87
+
88
+        // ====================  ACCESS        =======================
89
+
90
+        // ====================  INQUIRY       =======================
91
+
92
+        protected:
93
+
94
+        // ====================  LIFECYCLE     =======================
95
+
96
+        /** Default protected constructor, use New */
97
+        QWEKey (const std::string& name);
98
+
99
+        /** Default protected destructor, use Delete */
100
+        ~QWEKey ();
101
+
102
+        /**
103
+         *  @copybrief   LemmaObject::Release()
104
+         *  @copydetails LemmaObject::Release()
105
+         */
106
+        void Release();
107
+
108
+        /** Calculates Gauss quadrature weights of order N on the interval -1,1
109
+            Algorithm from p 129 in:
110
+            Trefethen, L. N., 2000, Spectral methods in MATLAB: Society for
111
+            Industrial and Applied Mathematics (SIAM), volume 10 of Software,
112
+            Environments, and Tools.
113
+        */
114
+        void GaussQuadWeights(const int& N);
115
+
116
+        /** Returns the quadrature intervals and Bessel function weights used for the
117
+            QWE method.
118
+
119
+         */
120
+        void BesselWeights( const sZeroType& sType);
121
+
122
+        /**  Computes an infinite integral using the partial sum of quadrature terms
123
+             accelerated by sequence extrapolation using the Shanks transformation
124
+             implemented with Wynn's epsilon algorithm.
125
+         */
126
+        void QWE(const Real& rho);
127
+
128
+        /** Calls the underlying kernel functions evaluated as necessary
129
+         */
130
+        void getEyKernel(const int& i, const int& idx, const Real& rho);
131
+
132
+        private:
133
+
134
+        // ====================  DATA MEMBERS  =========================
135
+
136
+        /** Relative tolerance, default is 1e-6 */
137
+        Real    RelTol;
138
+
139
+        /** Absolute tolerance, default is 1e-24 */
140
+        Real    AbsTol;
141
+
142
+        /** Quadrature order, higher is more accurate but more expensive. Eefault is 9 */
143
+        int     nQuad;
144
+
145
+        /** in QWE partial integrals before Shanks recurive algorithm. Defaults to 1  */
146
+        int nDelay;
147
+
148
+        /** Maximum number of intervals to integrate over . Defaults to 40  */
149
+        int nIntervalsMax;
150
+
151
+        /** Weighing of gaussian quadrature points */
152
+        VectorXr GaussWeights;
153
+
154
+        /** Abscissa locations of quadrature points */
155
+        VectorXr GaussAbscissa;
156
+
157
+        /** Breakpoints for dividing up the global integral */
158
+        VectorXr xInt;
159
+
160
+        /** All quadrature points between all breakpoints */
161
+        VectorXr Bx;
162
+
163
+        /** J0 weights */
164
+        VectorXr BJ0;
165
+
166
+        /** J1 weights */
167
+        VectorXr BJ1;
168
+
169
+        /** array of lambda arguments */
170
+        VectorXr Lambda;
171
+
172
+        /** array of lambda arguments */
173
+        VectorXr Intervals;
174
+
175
+        MatrixXcr TS;
176
+        VectorXi  Tn;
177
+        MatrixXcr Textrap;
178
+        MatrixXr  TrelErr;
179
+        MatrixXr  TabsErr;
180
+
181
+        /** Container to hold bessel arguments */
182
+        Eigen::Matrix<Complex, Eigen::Dynamic, Eigen::Dynamic > Zwork;
183
+
184
+        /** Container to hold bessel arguments */
185
+        Eigen::Matrix<Complex, Eigen::Dynamic, Eigen::Dynamic > Zans;
186
+
187
+        /** Manager for related kernels to evaluate */
188
+        KernelEM1DManager* KernelManager;
189
+
190
+    }; // -----  end of class  QWEKey  -----
191
+
192
+
193
+}		// -----  end of Lemma  name  -----
194
+
195
+#endif   // ----- #ifndef QWEKEY_INC  -----
196
+
197
+

+ 112
- 0
LemmaCore/include/RectilinearGridReader.h View File

@@ -0,0 +1,112 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
6
+ */
7
+
8
+/**
9
+  @file
10
+  @date      09/23/2013 11:05:11 AM
11
+  @version   $Id$
12
+  @author    Trevor Irons (ti)
13
+  @email     Trevor.Irons@xri-geo.com
14
+  @copyright Copyright (c) 2013, XRI Geophysics, LLC
15
+  @copyright Copyright (c) 2013, Trevor Irons
16
+ **/
17
+
18
+#ifndef  RECTILINEARGRIDREADER_INC
19
+#define  RECTILINEARGRIDREADER_INC
20
+
21
+#include "GridReader.h"
22
+#include "rectilineargrid.h"
23
+#include "ASCIIParser.h"
24
+
25
+namespace Lemma {
26
+
27
+    /**
28
+      @class
29
+      \brief
30
+      \details
31
+     */
32
+    class RectilinearGridReader : public GridReader {
33
+
34
+        friend std::ostream &operator<<(std::ostream &stream,
35
+                const RectilinearGridReader &ob);
36
+
37
+        public:
38
+
39
+            // ====================  LIFECYCLE     =======================
40
+
41
+            /**
42
+             * @copybrief LemmaObject::New()
43
+             * @copydetails LemmaObject::New()
44
+             */
45
+            static RectilinearGridReader* New();
46
+
47
+            /**
48
+             *  @copybrief   LemmaObject::Delete()
49
+             *  @copydetails LemmaObject::Delete()
50
+             */
51
+            void Delete();
52
+
53
+            // ====================  OPERATORS     =======================
54
+
55
+            // ====================  OPERATIONS    =======================
56
+
57
+            /**
58
+            Reads a .mod file, a simple representation of the grid. These files
59
+            have the following format:
60
+            @verbatim
61
+            nx ny nz  // number of cells in x, y, and z
62
+            ox oy oz  // grid offset of top SW corner
63
+
64
+            hx[0] hx[1] ... hx[nx-1]  // grid cell spacing in x, from 0 to nx-1
65
+            hy[0] hy[1] ... hy[ny-1]  // grid cell spacing in y, from 0 to ny-1
66
+            hz[0] hz[1] ... hz[nz-1]  // grid cell spacing in z, from 0 to nz-1
67
+
68
+            // c++ style (//) comments are allowed anywhere, c-style are not
69
+            @endverbatim
70
+            */
71
+            void ReadASCIIGridFile( const std::string& name );
72
+
73
+            // ====================  ACCESS        =======================
74
+            /**
75
+             * Accessor method for the underlying RectilinearGrid class constructed
76
+             * from the input file.
77
+             */
78
+            RectilinearGrid* GetGrid();
79
+
80
+            // ====================  INQUIRY       =======================
81
+
82
+        protected:
83
+
84
+            // ====================  LIFECYCLE     =======================
85
+
86
+            /** Default protected constructor, use New */
87
+            RectilinearGridReader (const std::string& name);
88
+
89
+            /** Default protected constructor, use Delete */
90
+            ~RectilinearGridReader ();
91
+
92
+            /**
93
+             *  @copybrief   LemmaObject::Release()
94
+             *  @copydetails LemmaObject::Release()
95
+             */
96
+            void Release();
97
+
98
+        private:
99
+
100
+            // ====================  DATA MEMBERS  =========================
101
+
102
+            /** Object holding constructed Grid */
103
+            RectilinearGrid* Grid;
104
+
105
+            /** Performs actual file parsing */
106
+            ASCIIParser* Parser;
107
+
108
+    }; // -----  end of class  RectilinearGridReader  -----
109
+
110
+}		// -----  end of Lemma  name  -----
111
+
112
+#endif   // ----- #ifndef RECTILINEARGRIDREADER_INC  -----

+ 120
- 0
LemmaCore/include/RectilinearGridVTKExporter.h View File

@@ -0,0 +1,120 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      09/25/2013 08:20:01 AM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2013, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2013, Trevor Irons
18
+ */
19
+
20
+
21
+#ifndef  RECTILINEARGRIDVTKEXPORTER_INC
22
+#define  RECTILINEARGRIDVTKEXPORTER_INC
23
+
24
+#ifdef  LEMMAUSEVTK
25
+
26
+#include "LemmaObject.h"
27
+#include "rectilineargrid.h"
28
+
29
+#include "vtkXMLRectilinearGridWriter.h"
30
+#include "vtkRectilinearGrid.h"
31
+#include "vtkDoubleArray.h"
32
+#include "vtkFieldData.h"
33
+#include "vtkCellData.h"
34
+
35
+namespace Lemma {
36
+
37
+/**
38
+  \brief   Exports a LemmaRectilinearGrid into a VTKRectilinearGrid.
39
+  \details Results can then be dumped to a VTK file or used directly.
40
+ */
41
+class RectilinearGridVTKExporter : public LemmaObject {
42
+
43
+    friend std::ostream &operator<<(std::ostream &stream,
44
+            const RectilinearGridVTKExporter &ob);
45
+
46
+    public:
47
+
48
+    // ====================  LIFECYCLE     =======================
49
+
50
+    /**
51
+     * @copybrief LemmaObject::New()
52
+     * @copydetails LemmaObject::New()
53
+     */
54
+    static RectilinearGridVTKExporter* New();
55
+
56
+    /**
57
+     *  @copybrief   LemmaObject::Delete()
58
+     *  @copydetails LemmaObject::Delete()
59
+     */
60
+    void Delete();
61
+
62
+    // ====================  OPERATORS     =======================
63
+
64
+    // ====================  OPERATIONS    =======================
65
+
66
+    // ====================  ACCESS        =======================
67
+    /**
68
+     * Sets the Grid to be exported
69
+     */
70
+    void SetGrid(RectilinearGrid* Grid);
71
+
72
+    // ====================  INQUIRY       =======================
73
+
74
+    /**
75
+     *  @return Returns a pointer to a vtkRectilinearGrid containing same information as the Lemma Grid.
76
+     */
77
+    vtkRectilinearGrid*  GetVTKGrid();
78
+
79
+    /**
80
+     *  Writes the exported VTKGrid out to a .vtr XML file
81
+     *  @param[in] name is the filename to write to. The .vtr extension will be added
82
+     */
83
+    void WriteVTKGrid( const std::string& name );
84
+
85
+    protected:
86
+
87
+    // ====================  LIFECYCLE     =======================
88
+
89
+    /** Default protected constructor, use New */
90
+    RectilinearGridVTKExporter (const std::string& name);
91
+
92
+    /** Default protected destructor, use Delete */
93
+    ~RectilinearGridVTKExporter ();
94
+
95
+    /**
96
+     *  @copybrief   LemmaObject::Release()
97
+     *  @copydetails LemmaObject::Release()
98
+     */
99
+    void Release();
100
+
101
+    private:
102
+
103
+    void BuildVTKRectilinearGrid();
104
+
105
+    // ====================  DATA MEMBERS  =========================
106
+
107
+    /** The Grid to convert from */
108
+    RectilinearGrid*    Grid;
109
+
110
+    /** The Grid to convert to */
111
+    vtkRectilinearGrid*    VTKGrid;
112
+
113
+}; // -----  end of class  RectilinearGridVTKExporter  -----
114
+
115
+}		// -----  end of Lemma  name  -----
116
+
117
+#endif     // -----  not LEMMAUSEVTK  -----
118
+
119
+#endif   // ----- #ifndef RECTILINEARGRIDVTKEXPORTER_INC  -----
120
+

+ 106
- 0
LemmaCore/include/TEMInductiveReceiver.h View File

@@ -0,0 +1,106 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      10/08/2014 03:17:52 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+
21
+#ifndef  TEMINDUCTIVERECEIVER_INC
22
+#define  TEMINDUCTIVERECEIVER_INC
23
+
24
+#include "TEMReceiver.h"
25
+
26
+namespace Lemma {
27
+
28
+    /**
29
+      \brief   Derived class of TEMReceiver.
30
+      \details An inductive receiver, measures dB/dt
31
+     */
32
+    class TEMInductiveReceiver : public TEMReceiver {
33
+
34
+        friend std::ostream &operator<<(std::ostream &stream,
35
+                const TEMInductiveReceiver &ob);
36
+
37
+        public:
38
+
39
+        // ====================  LIFECYCLE     =======================
40
+
41
+        /**
42
+         * @copybrief LemmaObject::New()
43
+         * @copydetails LemmaObject::New()
44
+         */
45
+        static TEMInductiveReceiver* New();
46
+
47
+        /**
48
+         *  @copybrief   LemmaObject::Delete()
49
+         *  @copydetails LemmaObject::Delete()
50
+         */
51
+        void Delete();
52
+
53
+        // ====================  OPERATORS     =======================
54
+
55
+        // ====================  OPERATIONS    =======================
56
+
57
+        // ====================  ACCESS        =======================
58
+
59
+        // ====================  INQUIRY       =======================
60
+
61
+#ifdef HAVE_YAMLCPP
62
+        /**
63
+         *  Uses YAML to serialize this object.
64
+         *  @return a YAML::Node
65
+         */
66
+        YAML::Node Serialize() const;
67
+
68
+        /**
69
+         *   Constructs an object from a YAML::Node.
70
+         */
71
+        static TEMInductiveReceiver* DeSerialize(const YAML::Node& node);
72
+#endif
73
+
74
+        protected:
75
+
76
+        // ====================  LIFECYCLE     =======================
77
+
78
+        /** Default protected constructor, use New */
79
+        TEMInductiveReceiver (const std::string& name);
80
+
81
+#ifdef HAVE_YAMLCPP
82
+        /** Default protected constructor, use New */
83
+        TEMInductiveReceiver (const YAML::Node& node);
84
+#endif
85
+
86
+        /** Default protected destructor, use Delete */
87
+        ~TEMInductiveReceiver ();
88
+
89
+        /**
90
+         *  @copybrief   LemmaObject::Release()
91
+         *  @copydetails LemmaObject::Release()
92
+         */
93
+        void Release();
94
+
95
+        private:
96
+
97
+        // ====================  DATA MEMBERS  =========================
98
+
99
+    }; // -----  end of class  TEMInductiveReceiver  -----
100
+
101
+
102
+}		// -----  end of Lemma  name  -----
103
+
104
+#endif   // ----- #ifndef TEMINDUCTIVERECEIVER_INC  -----
105
+
106
+

+ 183
- 0
LemmaCore/include/TEMReceiver.h View File

@@ -0,0 +1,183 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      10/08/2014 02:36:47 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#ifndef  TEMRECEIVER_INC
21
+#define  TEMRECEIVER_INC
22
+
23
+#include "receiverpoints.h"
24
+
25
+#include <boost/random.hpp>
26
+#include <boost/random/normal_distribution.hpp>
27
+
28
+namespace Lemma {
29
+
30
+#ifdef HAVE_YAMLCPP
31
+#include "yaml-cpp/yaml.h"
32
+#endif
33
+
34
+
35
+/**
36
+  \brief
37
+  \details
38
+ */
39
+class TEMReceiver : public ReceiverPoints {
40
+
41
+    friend std::ostream &operator<<(std::ostream &stream,
42
+            const TEMReceiver &ob);
43
+
44
+    public:
45
+
46
+    // ====================  LIFECYCLE     =======================
47
+
48
+    /**
49
+     * @copybrief LemmaObject::New()
50
+     * @copydetails LemmaObject::New()
51
+     */
52
+    static TEMReceiver* New();
53
+
54
+    /**
55
+     *   @return a deep copy of this
56
+     */
57
+    TEMReceiver* Clone();
58
+
59
+    /**
60
+     *  @copybrief   LemmaObject::Delete()
61
+     *  @copydetails LemmaObject::Delete()
62
+     */
63
+    void Delete();
64
+
65
+    // ====================  OPERATORS     =======================
66
+
67
+    // ====================  OPERATIONS    =======================
68
+
69
+    /**
70
+     * Uses the standard deviations provided to provide an instance
71
+     * of the expected noise. A realisation of the noise.
72
+     */
73
+    VectorXr SampleNoise();
74
+
75
+    // ====================  ACCESS        =======================
76
+
77
+    /**
78
+     *    Sets the gate integration windows
79
+     */
80
+    void SetWindows(const VectorXr& centres, const VectorXr& widths, const TIMEUNITS& Units);
81
+
82
+    /**
83
+     *   Sets the moment of the receiver. Defaults to 1 for normalized response.
84
+     */
85
+    void SetMoment( const Real&  moment);
86
+
87
+    /**
88
+     *  Sets std deviation values for noise channels.
89
+     *  @param[in] noise must be of the same length as the number of windows.
90
+     */
91
+    void SetNoiseSTD( const VectorXr& noise );
92
+
93
+    /**
94
+     *  Gets std deviation values for noise channels.
95
+     *  @return noise std dev.
96
+     */
97
+    VectorXr GetNoiseSTD(  );
98
+
99
+    /**
100
+     *  @param[in] refTime sets the reference time, defaults to 0
101
+     */
102
+    void SetReferenceTime( const Real& refTime, const TIMEUNITS& units );
103
+
104
+    /**
105
+     *  What field component to return
106
+     */
107
+    void SetComponent ( const FIELDCOMPONENT& COMP );
108
+
109
+    /**
110
+     *   @param[in] loc is the location of the dipole receiver
111
+     */
112
+    void SetRxLocation ( const Vector3r& loc );
113
+
114
+    // ====================  INQUIRY       =======================
115
+
116
+     #ifdef HAVE_YAMLCPP
117
+	/**
118
+     *  Uses YAML to serialize this object.
119
+     *  @return a YAML::Node
120
+     */
121
+    YAML::Node Serialize() const;
122
+
123
+    /**
124
+     *   Constructs an object from a YAML::Node.
125
+     */
126
+    static TEMReceiver* DeSerialize(const YAML::Node& node);
127
+     #endif
128
+
129
+    /**
130
+     * @return centre point of gates in sec
131
+     */
132
+    VectorXr GetWindowCentres();
133
+
134
+    /**
135
+     * @return width of gates in sec
136
+     */
137
+    VectorXr GetWindowWidths();
138
+
139
+    /**
140
+     *  @return the reference time
141
+     */
142
+    Real    GetReferenceTime();
143
+    protected:
144
+
145
+    // ====================  LIFECYCLE     =======================
146
+
147
+    /** Default protected constructor, use New */
148
+    TEMReceiver (const std::string& name);
149
+
150
+     #ifdef HAVE_YAMLCPP
151
+    /** Default protected de-serializing constructor, use factory DeSerialize */
152
+    TEMReceiver (const YAML::Node& node);
153
+    #endif
154
+
155
+    /** Default protected destructor, use Delete */
156
+    ~TEMReceiver ();
157
+
158
+    /**
159
+     *  @copybrief   LemmaObject::Release()
160
+     *  @copydetails LemmaObject::Release()
161
+     */
162
+    void Release();
163
+
164
+    private:
165
+
166
+    // ====================  DATA MEMBERS  =========================
167
+
168
+    Real            moment;
169
+    Real            referenceTime;
170
+    Vector3r        nHat;
171
+    FIELDCOMPONENT  component;
172
+
173
+    VectorXr        windowCentres;
174
+    VectorXr        windowWidths;
175
+    VectorXr        noiseSTD;
176
+    //Vector3r        location;
177
+
178
+}; // -----  end of class  TEMReceiver  -----
179
+
180
+}		// -----  end of Lemma  name  -----
181
+
182
+#endif   // ----- #ifndef TEMRECEIVER_INC  -----
183
+

+ 137
- 0
LemmaCore/include/TEMSurvey.h View File

@@ -0,0 +1,137 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      10/08/2014 01:51:50 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#ifndef  TEMSURVEY_INC
21
+#define  TEMSURVEY_INC
22
+
23
+#include "LemmaObject.h"
24
+#include "TEMSurveyLine.h"
25
+#include "TEMSurveyData.h"
26
+
27
+#include "layeredearthem.h"
28
+
29
+#ifdef HAVE_YAMLCPP
30
+#include "yaml-cpp/yaml.h"
31
+#endif
32
+
33
+namespace Lemma {
34
+
35
+
36
+    /**
37
+      \brief   Describes a TEM survey.
38
+      \details This class aims to encapulate any type of TEM survey.
39
+     */
40
+    class TEMSurvey : public LemmaObject {
41
+
42
+        friend std::ostream &operator<<(std::ostream &stream,
43
+                const TEMSurvey &ob);
44
+
45
+        public:
46
+
47
+        // ====================  LIFECYCLE     =======================
48
+
49
+        /**
50
+         * @copybrief LemmaObject::New()
51
+         * @copydetails LemmaObject::New()
52
+         */
53
+        static TEMSurvey* New();
54
+
55
+        /**
56
+         *  @copybrief   LemmaObject::Delete()
57
+         *  @copydetails LemmaObject::Delete()
58
+         */
59
+        void Delete();
60
+
61
+        // ====================  OPERATORS     =======================
62
+
63
+        /**  @param[in] idx the index to return
64
+         *   @return the SurveyLine with index idx
65
+         */
66
+        TEMSurveyLine* operator( ) ( const int& idx ) const ;
67
+
68
+        /**  @param[in] iline the line index to return
69
+         *   @param[in] irec the line index to return
70
+         *   @return the SurveyLine with index iline, irec
71
+         */
72
+        TEMSurveyLineRecord* operator( ) ( const int& iline, const int& irec ) const;
73
+
74
+        // ====================  OPERATIONS    =======================
75
+
76
+        /**
77
+         *  @param[in] nlines sets the number of lines (TEMSurveyLine) in the survey. A line is any kind of
78
+         *             related set of measurements. In Airborne EM, this is a flight line, but
79
+         *             the idea extends to ground based profile lines.
80
+         */
81
+        void SetNumberOfLines( const int& nlines );
82
+
83
+        /**
84
+         *  Most basic form of forward modelling. Uses input model for ALL TEMSurveyLines and
85
+         *  TEMSurveyLineRecords (atomic). Most useful in the
86
+         *  case that there is only 1 line and 1 record. But even in that case it can be called directly from
87
+         *  the record. This method will likely be replaced  soon.
88
+         */
89
+        TEMSurveyData* ForwardModel(LayeredEarthEM* model, bool additiveNoise=false);
90
+
91
+        // ====================  ACCESS        =======================
92
+
93
+        /**
94
+         *   @return pointer to requested TEMSurveyLine
95
+         */
96
+        TEMSurveyLine*  GetLine(const unsigned int& iline);
97
+
98
+        // ====================  INQUIRY       =======================
99
+
100
+        #ifdef HAVE_YAMLCPP
101
+        YAML::Node Serialize() const;
102
+        static TEMSurvey* DeSerialize(const YAML::Node& node);
103
+        #endif
104
+
105
+        protected:
106
+
107
+        // ====================  LIFECYCLE     =======================
108
+
109
+        /** Default protected constructor, use New */
110
+        TEMSurvey (const std::string& name);
111
+
112
+        #ifdef HAVE_YAMLCPP
113
+        /** Default protected constructor, use New */
114
+        TEMSurvey (const YAML::Node& node);
115
+        #endif
116
+
117
+        /** Default protected destructor, use Delete */
118
+        ~TEMSurvey ();
119
+
120
+        /**
121
+         *  @copybrief   LemmaObject::Release()
122
+         *  @copydetails LemmaObject::Release()
123
+         */
124
+        void Release();
125
+
126
+        private:
127
+
128
+        // ====================  DATA MEMBERS  =========================
129
+
130
+        std::vector<TEMSurveyLine*>     Lines;
131
+
132
+    }; // -----  end of class  TEMSurvey  -----
133
+
134
+
135
+}		// -----  end of Lemma  name  -----
136
+
137
+#endif   // ----- #ifndef TEMSURVEY_INC  -----

+ 161
- 0
LemmaCore/include/TEMSurveyData.h View File

@@ -0,0 +1,161 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      03/03/2015 09:54:25
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2015, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2015, Trevor Irons
18
+ */
19
+
20
+#ifndef  TEMSURVEYDATA_INC
21
+#define  TEMSURVEYDATA_INC
22
+
23
+#include "LemmaObject.h"
24
+#include "TEMSurveyLineData.h"
25
+
26
+namespace Lemma {
27
+
28
+    /**
29
+      \brief    Holds data from a TEMSurvey.
30
+      \details  Any form of TEMSurvey may be represented here. The
31
+                majority of the specification can be found in the associated
32
+                TEMSurvey. The TEMSurveyData object is intended to be lightweight.
33
+     */
34
+    class TEMSurveyData : public LemmaObject {
35
+
36
+        friend std::ostream &operator<<(std::ostream &stream,
37
+                const TEMSurveyData &ob);
38
+
39
+        friend class TEMSurvey;
40
+
41
+        public:
42
+
43
+        // ====================  LIFECYCLE     =======================
44
+
45
+        /**
46
+         * @copybrief LemmaObject::New()
47
+         * @copydetails LemmaObject::New()
48
+         */
49
+        static TEMSurveyData* New();
50
+
51
+        /**
52
+         *  @return a deep copy of this, this is acomplished through Serialize
53
+         *          and DeSerialize methods.
54
+         */
55
+        TEMSurveyData* Clone();
56
+
57
+        /**
58
+         *  @copybrief   LemmaObject::Delete()
59
+         *  @copydetails LemmaObject::Delete()
60
+         */
61
+        void Delete();
62
+
63
+        // ====================  OPERATORS     =======================
64
+
65
+        /** Surveys can be added or subtracted from each other, throws a
66
+         *  pointer that will need to be managed (Deleted)
67
+         */
68
+        TEMSurveyData* operator+(const TEMSurveyData& Survey);
69
+
70
+        /** Surveys can be added or subtracted from each other, throws a
71
+         *  pointer that will need to be managed (Deleted).
72
+         */
73
+        TEMSurveyData* operator-(const TEMSurveyData& Survey);
74
+
75
+        /** Surveys can be added or subtracted from each other
76
+         */
77
+        void operator+=(const TEMSurveyData& Survey);
78
+
79
+        /** Surveys can be added or subtracted from each other
80
+         */
81
+        void operator-=(const TEMSurveyData& Survey);
82
+
83
+
84
+        /**  @param[in] idx the index to return
85
+         *   @return the SurveyLine with index idx
86
+         */
87
+        TEMSurveyLineData* operator( ) ( const int& idx ) const;
88
+
89
+        /**  @param[in] iline the line index to return
90
+         *   @param[in] irec the line index to return
91
+         *   @return the SurveyLine with index iline, irec
92
+         */
93
+        TEMSurveyLineRecordData* operator( ) ( const int& iline, const int& irec ) const;
94
+
95
+
96
+        // ====================  OPERATIONS    =======================
97
+
98
+        /** Sets the number of lines
99
+         */
100
+        void SetNumberOfLines( const int& nlines );
101
+
102
+        // ====================  ACCESS        =======================
103
+
104
+        /** @return the number of lines in the data
105
+         */
106
+        int GetNumberOfLines() const;
107
+
108
+        /**
109
+         *   @return pointer to line
110
+         */
111
+        TEMSurveyLineData* GetLine(const int& iline) const;
112
+
113
+        // ====================  INQUIRY       =======================
114
+
115
+#ifdef HAVE_YAMLCPP
116
+        /**
117
+         *  Uses YAML to serialize this object.
118
+         *  @return a YAML::Node
119
+         */
120
+        YAML::Node Serialize() const;
121
+
122
+        /**
123
+         *   Constructs an object from a YAML::Node.
124
+         */
125
+        static TEMSurveyData* DeSerialize(const YAML::Node& node);
126
+#endif
127
+
128
+        protected:
129
+
130
+        // ====================  LIFECYCLE     =======================
131
+
132
+        /** Default protected constructor, use New */
133
+        TEMSurveyData (const std::string& name);
134
+
135
+#ifdef HAVE_YAMLCPP
136
+        /** Protected DeDerializing constructor, use factory DeSerialize  method*/
137
+        TEMSurveyData (const YAML::Node& node);
138
+#endif
139
+
140
+        /** Default protected destructor, use Delete */
141
+        ~TEMSurveyData ();
142
+
143
+        /**
144
+         *  @copybrief   LemmaObject::Release()
145
+         *  @copydetails LemmaObject::Release()
146
+         */
147
+        void Release();
148
+
149
+        private:
150
+
151
+        // ====================  DATA MEMBERS  =========================
152
+
153
+        std::vector<TEMSurveyLineData*>  LineData;
154
+
155
+    }; // -----  end of class  TEMSurveyData  -----
156
+
157
+
158
+
159
+}		// -----  end of Lemma  name  -----
160
+
161
+#endif   // ----- #ifndef TEMSURVEYDATA_INC  -----

+ 117
- 0
LemmaCore/include/TEMSurveyLine.h View File

@@ -0,0 +1,117 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      10/10/2014 11:14:39 AM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#ifndef  TEMSURVEYLINE_INC
21
+#define  TEMSURVEYLINE_INC
22
+
23
+#include "LemmaObject.h"
24
+#include "TEMSurveyLineRecord.h"
25
+#include "TEMSurveyLineData.h"
26
+
27
+namespace Lemma {
28
+
29
+    /**
30
+      \brief    Represents a TEM survey line.
31
+      \details  This class is managed by TEMSurvey. You cannot create a TEMSurvey line directly
32
+                this should be done through a TEMSurvey.
33
+                @todo neeed to impliment a BaseClass besides LemmaObject without pure virtual Delete.
34
+     */
35
+    class TEMSurveyLine : public LemmaObject {
36
+
37
+        friend std::ostream &operator<<(std::ostream &stream,
38
+                const TEMSurveyLine &ob);
39
+
40
+        friend class TEMSurvey;
41
+
42
+        public:
43
+
44
+        // ====================  LIFECYCLE     =======================
45
+
46
+
47
+
48
+        // ====================  OPERATORS     =======================
49
+
50
+        // ====================  OPERATIONS    =======================
51
+
52
+        // ====================  ACCESS        =======================
53
+
54
+        /**
55
+            @return returns pointer to a specific record along the line
56
+         */
57
+        TEMSurveyLineRecord*  GetRecord(const unsigned int& irec);
58
+
59
+        /**
60
+            @param[in] nrec is the number of records along the line
61
+         */
62
+        void SetNumberOfRecords( const int& nrec );
63
+
64
+        // ====================  INQUIRY       =======================
65
+
66
+#ifdef HAVE_YAMLCPP
67
+        /**
68
+         *  Uses YAML to serialize this object.
69
+         *  @return a YAML::Node
70
+         */
71
+        YAML::Node Serialize() const;
72
+
73
+        /**
74
+         *   Constructs an object from a YAML::Node.
75
+         */
76
+        static TEMSurveyLine* DeSerialize(const YAML::Node& node);
77
+#endif
78
+
79
+        protected:
80
+
81
+        TEMSurveyLineData* ForwardModel(LayeredEarthEM* model, bool additiveNoise = false);
82
+
83
+        // ====================  LIFECYCLE     =======================
84
+
85
+        /** Default protected constructor, use New */
86
+        TEMSurveyLine (const std::string& name);
87
+
88
+#ifdef HAVE_YAMLCPP
89
+        /** Protected DeDerializing constructor, use factory DeSerialize  method*/
90
+        TEMSurveyLine (const YAML::Node& node);
91
+#endif
92
+
93
+        /** Default protected destructor, use Delete */
94
+        ~TEMSurveyLine ();
95
+
96
+        /**
97
+         *  @copybrief   LemmaObject::Release()
98
+         *  @copydetails LemmaObject::Release()
99
+         */
100
+        void Release();
101
+
102
+        private:
103
+
104
+        /**
105
+         *   Delete should not be called...
106
+         */
107
+        void Delete();
108
+
109
+        // ====================  DATA MEMBERS  =========================
110
+
111
+        std::vector<TEMSurveyLineRecord*>     Records;
112
+
113
+    }; // -----  end of class  TEMSurveyLine  -----
114
+
115
+}		// -----  end of Lemma  name  -----
116
+
117
+#endif   // ----- #ifndef TEMSURVEYLINE_INC  -----

+ 146
- 0
LemmaCore/include/TEMSurveyLineData.h View File

@@ -0,0 +1,146 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      03/03/2015 10:16:47
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2015, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2015, Trevor Irons
18
+ */
19
+
20
+#ifndef  TEMSURVEYLINEDATA_INC
21
+#define  TEMSURVEYLINEDATA_INC
22
+
23
+#include "LemmaObject.h"
24
+#include "TEMSurveyLineRecordData.h"
25
+
26
+namespace Lemma {
27
+
28
+/**
29
+  \brief   Holds Data for a TEM survey line
30
+  \details An entire flight line worth of data is stored here.
31
+ */
32
+class TEMSurveyLineData : public LemmaObject {
33
+
34
+    friend std::ostream &operator<<(std::ostream &stream,
35
+            const TEMSurveyLineData &ob);
36
+
37
+    //friend class TEMSurveyData;
38
+    friend class TEMSurveyLine;
39
+
40
+    public:
41
+
42
+    // ====================  LIFECYCLE     =======================
43
+
44
+    /**
45
+     * @copybrief LemmaObject::New()
46
+     * @copydetails LemmaObject::New()
47
+     */
48
+    static TEMSurveyLineData* New();
49
+
50
+    /**
51
+     *  @return a deep copy of this, this is acomplished through Serialize
52
+     *          and DeSerialize methods.
53
+     */
54
+    TEMSurveyLineData* Clone();
55
+
56
+    /**
57
+     *  @copybrief   LemmaObject::Delete()
58
+     *  @copydetails LemmaObject::Delete()
59
+     */
60
+    void Delete();
61
+
62
+    // ====================  OPERATORS     =======================
63
+
64
+    /** Survey lines can be added or subtracted from each other
65
+     */
66
+    TEMSurveyLineData* operator+(const TEMSurveyLineData& Survey);
67
+
68
+    /** Survey lines can be added or subtracted from each other
69
+     */
70
+    TEMSurveyLineData* operator-(const TEMSurveyLineData& Survey);
71
+
72
+    /** Survey lines can be added or subtracted from each other
73
+     */
74
+    void operator+=(const TEMSurveyLineData& Survey);
75
+
76
+    /** Survey lines can be added or subtracted from each other
77
+     */
78
+    void operator-=(const TEMSurveyLineData& Survey);
79
+
80
+    /**  @param[in] ir the index to return
81
+     *   @return the SurveyLineRecord with index ir
82
+     */
83
+    TEMSurveyLineRecordData* operator( ) ( const int& ir ) const ;
84
+
85
+    // ====================  OPERATIONS    =======================
86
+
87
+    // ====================  ACCESS        =======================
88
+
89
+    /**
90
+     *    @return pointer to specified record
91
+     */
92
+    TEMSurveyLineRecordData*  GetRecord(const int& ir) const ;
93
+
94
+    /**
95
+     * @return the number of records
96
+     */
97
+    int GetNumberOfRecords() const;
98
+
99
+    // ====================  INQUIRY       =======================
100
+
101
+#ifdef HAVE_YAMLCPP
102
+    /**
103
+     *  Uses YAML to serialize this object.
104
+     *  @return a YAML::Node
105
+     */
106
+    YAML::Node Serialize() const;
107
+
108
+    /**
109
+     *   Constructs an object from a YAML::Node.
110
+     */
111
+    static TEMSurveyLineData* DeSerialize(const YAML::Node& node);
112
+#endif
113
+
114
+    protected:
115
+
116
+    // ====================  LIFECYCLE     =======================
117
+
118
+    /** Default protected constructor, use New */
119
+    TEMSurveyLineData (const std::string& name);
120
+
121
+#ifdef HAVE_YAMLCPP
122
+    /** Protected DeDerializing constructor, use factory DeSerialize  method*/
123
+    TEMSurveyLineData (const YAML::Node& node);
124
+#endif
125
+
126
+    /** Default protected destructor, use Delete */
127
+    ~TEMSurveyLineData ();
128
+
129
+    /**
130
+     *  @copybrief   LemmaObject::Release()
131
+     *  @copydetails LemmaObject::Release()
132
+     */
133
+    void Release();
134
+
135
+    private:
136
+
137
+    // ====================  DATA MEMBERS  =========================
138
+
139
+    std::vector<TEMSurveyLineRecordData*>   RecordData;
140
+
141
+}; // -----  end of class  TEMSurveyLineData  -----
142
+
143
+}		// -----  end of Lemma  name  -----
144
+
145
+#endif   // ----- #ifndef TEMSURVEYLINEDATA_INC  -----
146
+

+ 140
- 0
LemmaCore/include/TEMSurveyLineRecord.h View File

@@ -0,0 +1,140 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      10/10/2014 12:15:03 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#ifndef  TEMSURVEYLINERECORD_INC
21
+#define  TEMSURVEYLINERECORD_INC
22
+
23
+#include "LemmaObject.h"
24
+#include "TEMReceiver.h"
25
+#include "TEMTransmitter.h"
26
+#include "TEMSurveyLineRecordData.h"
27
+#include "instrumenttem.h"
28
+
29
+namespace Lemma {
30
+
31
+    /**
32
+      \brief    Class holding everything necessary to create a TEM record.
33
+      \details  A TEM record represents the nexus of a transmitter with
34
+                receiver(s) and pulse moment(s). Therefore a record can contain
35
+                multiple sounding curves.
36
+     */
37
+    class TEMSurveyLineRecord : public LemmaObject {
38
+
39
+        friend std::ostream &operator<<(std::ostream &stream,
40
+                const TEMSurveyLineRecord &ob);
41
+
42
+        friend class TEMSurveyLine;
43
+
44
+        public:
45
+
46
+        // ====================  LIFECYCLE     =======================
47
+
48
+        // ====================  OPERATORS     =======================
49
+
50
+        // ====================  OPERATIONS    =======================
51
+
52
+        /**
53
+         *  Perfoms forward modelling given model.
54
+         *  @param[in] model is the earth model responsible for the response
55
+         *  @param[in] additiveNoise is whether or not to add noise to the response, defaults to false
56
+         *  @return the modelled data.
57
+         */
58
+        TEMSurveyLineRecordData* ForwardModel(LayeredEarthEM* model, bool additiveNoise=false);
59
+
60
+        /**
61
+         *  @param[in] nseq is the number of pulse sequences
62
+         */
63
+        void SetNumberOfPulseSequences( const int& nseq );
64
+
65
+        /**
66
+         *  @return the number of pulse sequences
67
+         */
68
+        int GetNumberOfPulseSequences();
69
+
70
+        /**
71
+         *  Sets the PulseSequence and Receiver pair used to model a *SINGLE* response curve.
72
+         *  @param[in] Seq is the Pulse Sequence
73
+         *  @param[in] Rx is the receiver for that pulse sequence
74
+         */
75
+        void SetTransmitterReceiverPair( const int& ii, TEMTransmitter* Seq, TEMReceiver* Rx );
76
+
77
+        // ====================  ACCESS        =======================
78
+
79
+        /**
80
+         *  @return a pointer to the specified receiver
81
+         */
82
+        TEMReceiver*   GetReceiver(const int& irec);
83
+
84
+        // ====================  INQUIRY       =======================
85
+
86
+#ifdef HAVE_YAMLCPP
87
+        /**
88
+         *  Uses YAML to serialize this object.
89
+         *  @return a YAML::Node
90
+         */
91
+        YAML::Node Serialize() const;
92
+
93
+        /**
94
+         *   Constructs an object from a YAML::Node.
95
+         */
96
+        static TEMSurveyLineRecord* DeSerialize(const YAML::Node& node);
97
+#endif
98
+
99
+        protected:
100
+
101
+
102
+
103
+        // ====================  LIFECYCLE     =======================
104
+
105
+        /** Default protected constructor, use New */
106
+        TEMSurveyLineRecord (const std::string& name);
107
+
108
+#ifdef HAVE_YAMLCPP
109
+        /** Protected DeDerializing constructor, use factory DeSerialize  method*/
110
+        TEMSurveyLineRecord (const YAML::Node& node);
111
+#endif
112
+
113
+        /** Default protected destructor, use Delete */
114
+        ~TEMSurveyLineRecord ();
115
+
116
+        /**
117
+         *  @copybrief   LemmaObject::Release()
118
+         *  @copydetails LemmaObject::Release()
119
+         */
120
+        void Release();
121
+
122
+        private:
123
+
124
+        /**
125
+         *   Delete is private, this class is managed through TEMSurvey
126
+         */
127
+        void Delete();
128
+
129
+        // ====================  DATA MEMBERS  =========================
130
+
131
+        int     numberOfPulseSequences;
132
+
133
+        std::vector<TEMTransmitter*>    Transmitters;
134
+        std::vector<TEMReceiver*>       Receivers;
135
+
136
+    }; // -----  end of class  TEMSurveyLineRecord  -----
137
+
138
+}		// -----  end of Lemma  name  -----
139
+
140
+#endif   // ----- #ifndef TEMSURVEYLINERECORD_INC  -----

+ 141
- 0
LemmaCore/include/TEMSurveyLineRecordData.h View File

@@ -0,0 +1,141 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      03/03/2015 10:29:01
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2015, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2015, Trevor Irons
18
+ */
19
+#ifndef  TEMSURVEYLINERECORDDATA_INC
20
+#define  TEMSURVEYLINERECORDDATA_INC
21
+
22
+#include "LemmaObject.h"
23
+
24
+namespace Lemma {
25
+
26
+    /**
27
+      \brief
28
+      \details
29
+     */
30
+    class TEMSurveyLineRecordData : public LemmaObject {
31
+
32
+        friend std::ostream &operator<<(std::ostream &stream,
33
+                const TEMSurveyLineRecordData &ob);
34
+
35
+        friend class TEMSurveyLineRecord;
36
+
37
+        public:
38
+
39
+        // ====================  LIFECYCLE     =======================
40
+
41
+        /**
42
+         * @copybrief LemmaObject::New()
43
+         * @copydetails LemmaObject::New()
44
+         */
45
+        static TEMSurveyLineRecordData* New();
46
+
47
+
48
+        /** Provides deep copy
49
+         */
50
+        TEMSurveyLineRecordData* Clone();
51
+
52
+        /**
53
+         *  @copybrief   LemmaObject::Delete()
54
+         *  @copydetails LemmaObject::Delete()
55
+         */
56
+        void Delete();
57
+
58
+        // ====================  OPERATORS     =======================
59
+
60
+        /**
61
+         * Records can be added
62
+         */
63
+        TEMSurveyLineRecordData* operator + (const TEMSurveyLineRecordData&);
64
+
65
+        /**
66
+         * Records can be subtracted
67
+         */
68
+        TEMSurveyLineRecordData* operator - (const TEMSurveyLineRecordData&);
69
+
70
+        /**
71
+         * Records can be added in place
72
+         */
73
+        void operator += (const TEMSurveyLineRecordData&);
74
+
75
+        /**
76
+         * Records can be subtracted in place
77
+         */
78
+        void operator -= (const TEMSurveyLineRecordData&);
79
+
80
+        // ====================  OPERATIONS    =======================
81
+
82
+        // ====================  ACCESS        =======================
83
+
84
+        /** @return a VectorXr of the merged data (all moments)
85
+         * @todo TODO this is actually a copy? is this intended?
86
+         */
87
+        VectorXr GetCombinedData();
88
+
89
+        /** @return a VectorXr of the combined gate centres alligned with
90
+         *          GetCombinedData();
91
+         */
92
+        VectorXr GetCombinedGateCentres();
93
+        // ====================  INQUIRY       =======================
94
+
95
+#ifdef HAVE_YAMLCPP
96
+        /**
97
+         *  Uses YAML to serialize this object.
98
+         *  @return a YAML::Node
99
+         */
100
+        YAML::Node Serialize() const;
101
+
102
+        /**
103
+         *   Constructs an object from a YAML::Node.
104
+         */
105
+        static TEMSurveyLineRecordData* DeSerialize(const YAML::Node& node);
106
+#endif
107
+
108
+        protected:
109
+
110
+        // ====================  LIFECYCLE     =======================
111
+
112
+        /** Default protected constructor, use New */
113
+        TEMSurveyLineRecordData (const std::string& name);
114
+
115
+#ifdef HAVE_YAMLCPP
116
+        /** Protected DeDerializing constructor, use factory DeSerialize  method*/
117
+        TEMSurveyLineRecordData (const YAML::Node& node);
118
+#endif
119
+
120
+        /** Default protected destructor, use Delete */
121
+        ~TEMSurveyLineRecordData ();
122
+
123
+        /**
124
+         *  @copybrief   LemmaObject::Release()
125
+         *  @copydetails LemmaObject::Release()
126
+         */
127
+        void Release();
128
+
129
+        private:
130
+
131
+        // ====================  DATA MEMBERS  =========================
132
+
133
+        std::vector<VectorXr>           DataSeries;
134
+
135
+        std::vector<VectorXr>           GateCentres;
136
+
137
+    }; // -----  end of class  TEMSurveyLineRecordData  -----
138
+
139
+}		// -----  end of Lemma  name  -----
140
+
141
+#endif   // ----- #ifndef TEMSURVEYLINERECORDDATA_INC  -----

+ 125
- 0
LemmaCore/include/TEMTransmitter.h View File

@@ -0,0 +1,125 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      09/29/2014 11:43:17 AM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#ifndef  TEMTRANSMITTER_INC
21
+#define  TEMTRANSMITTER_INC
22
+
23
+#include "PolygonalWireAntenna.h"
24
+
25
+#ifdef HAVE_YAMLCPP
26
+#include "yaml-cpp/yaml.h"
27
+#endif
28
+
29
+namespace Lemma {
30
+
31
+/**
32
+  \brief   Describes a TEM pulse sequence
33
+  \details Flexible class desribing a pulse sequence used by
34
+           a TEM instruement. Can be used by Airborne or Ground
35
+           instruments.
36
+ */
37
+class TEMTransmitter : public PolygonalWireAntenna {
38
+
39
+    friend std::ostream &operator<<(std::ostream &stream, const TEMTransmitter &ob);
40
+
41
+    public:
42
+
43
+    // ====================  LIFECYCLE     =======================
44
+
45
+    /**
46
+     * @copybrief LemmaObject::New()
47
+     * @copydetails LemmaObject::New()
48
+     */
49
+    static TEMTransmitter* New();
50
+
51
+    /**
52
+     *  Performs a deep copy of this and returns pointer
53
+     */
54
+    TEMTransmitter* Clone();
55
+
56
+    /**
57
+     *  @copybrief   LemmaObject::Delete()
58
+     *  @copydetails LemmaObject::Delete()
59
+     */
60
+    void Delete();
61
+
62
+    // ====================  OPERATORS     =======================
63
+
64
+    // ====================  OPERATIONS    =======================
65
+
66
+    // ====================  ACCESS        =======================
67
+
68
+    /** Sets the repetition frequency
69
+     */
70
+    void SetRepFrequency(const Real& fr, const FREQUENCYUNITS& units);
71
+
72
+    void SetWaveform( const VectorXr& times, const VectorXr& amps, const TIMEUNITS& units );
73
+
74
+    /**
75
+     *  @return the waveform times in seconds
76
+     */
77
+    VectorXr GetWfmTimes();
78
+
79
+    /** @return the waveform current in amps
80
+     */
81
+    VectorXr GetWfmAmps();
82
+
83
+    // ====================  INQUIRY       =======================
84
+
85
+#ifdef HAVE_YAMLCPP
86
+    YAML::Node Serialize() const;
87
+    static TEMTransmitter* DeSerialize(const YAML::Node& node);
88
+#endif
89
+
90
+    protected:
91
+
92
+    // ====================  LIFECYCLE     =======================
93
+
94
+    /** Default protected constructor, use New */
95
+    TEMTransmitter (const std::string& name);
96
+
97
+#ifdef HAVE_YAMLCPP
98
+    /** Default protected constructor, use New */
99
+    TEMTransmitter (const YAML::Node& node);
100
+#endif
101
+
102
+    /** Default protected destructor, use Delete */
103
+    ~TEMTransmitter ();
104
+
105
+    /**
106
+     *  @copybrief   LemmaObject::Release()
107
+     *  @copydetails LemmaObject::Release()
108
+     */
109
+    void Release();
110
+
111
+    private:
112
+
113
+    // ====================  DATA MEMBERS  =========================
114
+
115
+    Real                    repFreq;
116
+    FREQUENCYUNITS          repFreqUnits;
117
+    VectorXr                wfmTimes;
118
+    VectorXr                wfmAmps;
119
+
120
+}; // -----  end of class  TEMTransmitter  -----
121
+
122
+} // namespace Lemma
123
+
124
+#endif   // ----- #ifndef TEMTRANSMITTER_INC  -----
125
+

+ 88
- 0
LemmaCore/include/UngroundedElectricDipole.h View File

@@ -0,0 +1,88 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      01/29/2014 08:52:43 AM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+
21
+#ifndef  UNGROUNDEDELECTRICDIPOLE_INC
22
+#define  UNGROUNDEDELECTRICDIPOLE_INC
23
+
24
+#include "dipolesource.h"
25
+
26
+namespace Lemma {
27
+
28
+    /**
29
+      \brief  Ungrounded electric dipole
30
+      \details Used to model an idealised ungrounded electric dipole. Used primarily in integrating
31
+                around current sources.
32
+     */
33
+    class UngroundedElectricDipole : public DipoleSource {
34
+
35
+        friend std::ostream &operator<<(std::ostream &stream,
36
+                const UngroundedElectricDipole &ob);
37
+
38
+        public:
39
+
40
+        // ====================  LIFECYCLE     =======================
41
+
42
+        /**
43
+         * @copybrief LemmaObject::New()
44
+         * @copydetails LemmaObject::New()
45
+         */
46
+        static UngroundedElectricDipole* New();
47
+
48
+        /**
49
+         *  @copybrief   LemmaObject::Delete()
50
+         *  @copydetails LemmaObject::Delete()
51
+         */
52
+        void Delete();
53
+
54
+        // ====================  OPERATORS     =======================
55
+
56
+        // ====================  OPERATIONS    =======================
57
+
58
+        // ====================  ACCESS        =======================
59
+
60
+        // ====================  INQUIRY       =======================
61
+
62
+        protected:
63
+
64
+        // ====================  LIFECYCLE     =======================
65
+
66
+        /** Default protected constructor, use New */
67
+        UngroundedElectricDipole (const std::string& name);
68
+
69
+        /** Default protected destructor, use Delete */
70
+        ~UngroundedElectricDipole ();
71
+
72
+        /**
73
+         *  @copybrief   LemmaObject::Release()
74
+         *  @copydetails LemmaObject::Release()
75
+         */
76
+        void Release();
77
+
78
+        private:
79
+
80
+        // ====================  DATA MEMBERS  =========================
81
+
82
+    }; // -----  end of class  UngroundedElectricDipole  -----
83
+
84
+
85
+}		// -----  end of Lemma  name  -----
86
+
87
+#endif   // ----- #ifndef UNGROUNDEDELECTRICDIPOLE_INC  -----
88
+

+ 249
- 0
LemmaCore/include/WireAntenna.h View File

@@ -0,0 +1,249 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     12/16/2009
11
+  @version  $Id: WireAntenna.h 201 2015-01-03 00:07:47Z tirons $
12
+ **/
13
+
14
+#ifndef __WIREANTENNA_H
15
+#define __WIREANTENNA_H
16
+
17
+#include "LemmaObject.h"
18
+#include "dipolesource.h"
19
+
20
+#ifdef LEMMAUSEVTK
21
+#include "vtkActor.h"
22
+#endif
23
+
24
+namespace Lemma {
25
+
26
+
27
+    // ===================================================================
28
+    /**      Class:  WireAntenna
29
+      * \brief   Class representing a wire antennae.
30
+      * \details This is an abstract class.
31
+	  */
32
+    // ===================================================================
33
+    class WireAntenna : public LemmaObject {
34
+
35
+        friend std::ostream &operator<<(std::ostream &stream,
36
+            const WireAntenna &ob);
37
+
38
+        public:
39
+
40
+            // ====================  LIFECYCLE     =======================
41
+
42
+            /**
43
+             * Initialises antenna to contain no points, with no current
44
+             * and no frequency. NumberOfTurns set to 1
45
+             */
46
+            static WireAntenna* New();
47
+
48
+            /**
49
+             * Provides deep copy
50
+             */
51
+            virtual WireAntenna* Clone();
52
+
53
+            /**
54
+             * @copybrief LemmaObject::Delete()
55
+             * @copydetails LemmaObject::Delete()
56
+             */
57
+            void Delete();
58
+
59
+            // ====================  OPERATORS     =======================
60
+
61
+            // ====================  OPERATIONS    =======================
62
+
63
+            /**
64
+              * Approximates with evenly spaced electric dipoles around loop
65
+              * @param[in] delta is the spacing between moments
66
+			  */
67
+            virtual void ApproximateWithElectricDipoles(const Real &delta);
68
+
69
+            // ====================  ACCESS        =======================
70
+
71
+			/**
72
+              * Sets the number of turns in the loop, default is 1
73
+              * @param[in] nturns is the number of turns of the loop.
74
+			  */
75
+            void SetNumberOfTurns(const int &nturns);
76
+
77
+            /**
78
+              * Sets the number of points in the loop
79
+			  */
80
+            void SetNumberOfPoints(const int &np);
81
+
82
+			/**
83
+              * Sets a corner point of the loop. Counting starts at 0. It
84
+              * is not required to have the loop be closed right now, but
85
+              * its a good idea.
86
+			  */
87
+            void SetPoint(const int &p, const Vector3r &pos);
88
+
89
+            /**
90
+              * Sets a corner point of the loop. Counting starts at 0. It
91
+              * is not required to have the loop be closed right now, but
92
+              * its a good idea.
93
+			  */
94
+            void SetPoint(const int &p, const Real&x, const Real& y, const Real& z);
95
+
96
+            /** Sets the frequency of the current in the loop, default is 0
97
+			  * @param[in] ifreq is the frequency number to set
98
+              * @param[in] freq is the frequency (Hz) of the current
99
+			  */
100
+            void SetFrequency(const int& ifreq, const Real &freq);
101
+			/**
102
+              * Sets the number of frequencies.
103
+              * @param[in] nfreq is the number of frequencies that will be
104
+              * computed.
105
+			  */
106
+            void SetNumberOfFrequencies(const int& nfreq);
107
+
108
+			/**
109
+              * Sets the current in the loop, default is 0
110
+              * @param[in] amp is the current in the loop, in Amperes
111
+			  */
112
+            void SetCurrent(const Real &amp);
113
+
114
+            // ====================  INQUIRY       =======================
115
+
116
+            #ifdef HAVE_YAMLCPP
117
+            /**
118
+             *  Uses YAML to serialize this object.
119
+             *  @return a YAML::Node
120
+             */
121
+            YAML::Node Serialize() const;
122
+
123
+            /**
124
+             *   Constructs an object from a YAML::Node.
125
+             */
126
+            static WireAntenna* DeSerialize(const YAML::Node& node);
127
+            #endif
128
+
129
+			/**
130
+              * Returns the number of turns
131
+              * @return the number of turns of the loop.
132
+			  */
133
+            int GetNumberOfTurns( );
134
+
135
+            /**
136
+             * Returns all of the points
137
+             */
138
+            Vector3Xr GetPoints();
139
+
140
+            /**
141
+             * Returns all of the points in a general matrix, useful for python wrapper
142
+             */
143
+            MatrixXr GetPointsMat();
144
+
145
+			/**
146
+              * Returns the frequency in the loop.
147
+              * @return is the frequency in the loop in Hz
148
+			  */
149
+            Real GetFrequency(const int& ifreq);
150
+
151
+
152
+			/**
153
+              * Returns the current in the loop.
154
+              * @return is the Current
155
+			  */
156
+            Real GetCurrent( );
157
+
158
+
159
+			/**
160
+              * Returns pointer to a dipole source
161
+			  */
162
+            DipoleSource* GetDipoleSource(const int &dip);
163
+
164
+			/**
165
+              * returns number of dipoles used to approximate this
166
+              * loop
167
+			  */
168
+            int GetNumberOfDipoles();
169
+
170
+			/**
171
+              * @return the number of frequencies of this wire loop.
172
+			  */
173
+            int GetNumberOfFrequencies();
174
+
175
+            #ifdef LEMMAUSEVTK
176
+            /** Returns an actor that can be placed into a vtk scene easily
177
+              * Note that this function throws a pointer, it is the
178
+              * receivers job to manage this memory!
179
+			  */
180
+            vtkActor* GetVtkActor(const int &idip);
181
+            #endif
182
+
183
+            /** Returns true or false if loop is horizontally planar
184
+             */
185
+            bool IsHorizontallyPlanar();
186
+
187
+        protected:
188
+
189
+            // ====================  LIFECYCLE     =======================
190
+
191
+			/**
192
+              * Default protected constructor.
193
+			  */
194
+            WireAntenna (const std::string &name);
195
+
196
+#ifdef HAVE_YAMLCPP
197
+        /** Protected DeDerializing constructor, use factory DeSerialize  method*/
198
+            WireAntenna (const YAML::Node& node);
199
+#endif
200
+
201
+			/**
202
+              * Default protected destructor.
203
+			  */
204
+            ~WireAntenna ();
205
+
206
+            /**
207
+             * @copybrief LemmaObject::Release()
208
+             * @copydetails LemmaObject::Release()
209
+             */
210
+            void Release();
211
+
212
+            // ====================  DATA MEMBERS  =======================
213
+
214
+			/**
215
+              * Number of points that define the loop
216
+			  */
217
+            int NumberOfPoints;
218
+
219
+			/**
220
+              * Current in antennae (Amps)
221
+			  */
222
+            Real Current;
223
+
224
+			/**
225
+              * Number of turns
226
+			  */
227
+            int NumberOfTurns;
228
+
229
+			/**
230
+              * List of the dipoles
231
+			  */
232
+            std::vector<DipoleSource*>           Dipoles;
233
+
234
+			/**
235
+              * Points that define this loop
236
+			  */
237
+            Vector3Xr                            Points;
238
+
239
+			/**
240
+              * Frequencies of the loop.
241
+			  */
242
+            VectorXr                             Freqs;
243
+
244
+        private:
245
+
246
+    }; // -----  end of class  WireAntenna  -----
247
+
248
+}
249
+#endif // __WIREANTENNA_H

+ 24
- 0
LemmaCore/include/banner.h View File

@@ -0,0 +1,24 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API
2
+ */
3
+
4
+/* This Source Code Form is subject to the terms of the Mozilla Public
5
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
6
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7
+
8
+/**
9
+  @file
10
+  @author   M. Andy Kass
11
+  @date     05/03/2010
12
+  @version  $Id: banner.h 87 2013-09-05 22:44:05Z tirons $
13
+ **/
14
+
15
+#ifndef __BANNER_H
16
+#define __BANNER_H
17
+#include <iostream>
18
+#include <ostream>
19
+void banner(const std::string &name, const std::string &version,
20
+		const std::string &usage);
21
+#endif
22
+
23
+/* vim: set tabstop=4 expandtab: */
24
+/* vim: set filetype=cpp: */

+ 98
- 0
LemmaCore/include/bicgstab.h View File

@@ -0,0 +1,98 @@
1
+/*
2
+ modifed from http://www.netlib.org/templates/cpp//
3
+ Iterative template routine -- BiCGSTAB
4
+
5
+ BiCGSTAB solves the unsymmetric linear system Ax = b
6
+ using the Preconditioned BiConjugate Gradient Stabilized method
7
+
8
+ BiCGSTAB follows the algorithm described on p. 27 of the
9
+ SIAM Templates book.
10
+
11
+ The return value indicates convergence within max_iter (input)
12
+ iterations (0), or no convergence within max_iter iterations (1).
13
+
14
+ Upon successful return, output arguments have the following values:
15
+
16
+        x  --  approximate solution to Ax = b
17
+ max_iter  --  the number of iterations performed before the
18
+               tolerance was reached
19
+      tol  --  the residual after the final iteration
20
+*/
21
+
22
+#include <iostream>
23
+#include <fstream>
24
+#include "lemma.h"
25
+
26
+namespace Lemma {
27
+
28
+    template <typename Scalar>
29
+    VectorXr BiCGSTAB(const MatrixXr &A, const VectorXr &x0, const VectorXr &b,
30
+          const MatrixXr &M, int &max_iter, Scalar& tol) {
31
+        Scalar resid;
32
+        Scalar rho_1(0), rho_2(0), alpha(0), beta(0), omega(0);
33
+        VectorXr p, phat, s, shat, t, v;
34
+        VectorXr x = x0;
35
+        Scalar normb = b.norm();
36
+        VectorXr r = b - A * x;
37
+        VectorXr rtilde = r;
38
+
39
+        if (normb == 0.0)
40
+          normb = 1;
41
+
42
+        if ((resid = r.norm() / normb) <= tol) {
43
+          tol = resid;
44
+          max_iter = 0;
45
+          //return 0;
46
+          return x;
47
+        }
48
+
49
+        for (int i = 1; i <= max_iter; i++) {
50
+          rho_1 = rtilde.dot(r);
51
+          if (rho_1 == 0) {
52
+            tol = r.norm() / normb;
53
+            //return 2;
54
+            return x;
55
+          }
56
+          if (i == 1)
57
+            p = r;
58
+          else {
59
+            beta = (rho_1/rho_2) * (alpha/omega);
60
+            p = r + beta * (p - omega * v);
61
+          }
62
+          phat = M*p; //M.solve(p);
63
+          v = A * phat;
64
+          alpha = rho_1 / rtilde.dot(v);
65
+          s = r - alpha * v;
66
+          if ((resid = s.norm()/normb) < tol) {
67
+            x += alpha * phat;
68
+            tol = resid;
69
+            //return 0;
70
+            return x;
71
+          }
72
+          shat = M*s;//M.solve(s);
73
+          t = A * shat;
74
+          omega = t.dot(s) / t.dot(t);
75
+          x += alpha * phat + omega * shat;
76
+          r = s - omega * t;
77
+
78
+          rho_2 = rho_1;
79
+          if ((resid = r.norm() / normb) < tol) {
80
+            tol = resid;
81
+            max_iter = i;
82
+            //return 0;
83
+            return x;
84
+          }
85
+          if (omega == 0) {
86
+            tol = r.norm() / normb;
87
+            //return 3;
88
+            return x;
89
+          }
90
+        }
91
+
92
+        tol = resid;
93
+        return x;
94
+    }
95
+}
96
+
97
+/* vim: set tabstop=4 expandtab: */
98
+/* vim: set filetype=cpp: */

+ 437
- 0
LemmaCore/include/cg.h View File

@@ -0,0 +1,437 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @version  $Id: cg.h 87 2013-09-05 22:44:05Z tirons $
11
+ **/
12
+
13
+#ifndef  CG_INC
14
+#define  CG_INC
15
+
16
+
17
+#include <iostream>
18
+#include <fstream>
19
+#include "lemma.h"
20
+
21
+namespace Lemma {
22
+
23
+    /** Port of netlib.org http://www.netlib.org/templates/cpp//cg.h
24
+     *  Solves the symmetric postive definite system Ax=b.
25
+     *  No preconditioner is used.
26
+     *  Iterative template routine -- CG
27
+     *
28
+     *  CG solves the symmetric positive definite linear
29
+     *  system Ax=b using the Conjugate Gradient method.
30
+     *
31
+     *  CG follows the algorithm described on p. 15 in the
32
+     *  SIAM Templates book.
33
+     *
34
+     *  The return value indicates convergence within max_iter (input)
35
+     *  iterations (0), or no convergence within max_iter iterations (1).
36
+     *
37
+     *  Upon successful return, output arguments have the following values:
38
+     *
39
+     *         x  --  approximate solution to Ax = b
40
+     *  max_iter  --  the number of iterations performed before the
41
+     *                tolerance was reached
42
+     *       tol  --  the residual after the final iteration
43
+     *  @param[in] A is a Real matrix A to be solved.
44
+     *  @param[in] x0 is the starting model.
45
+     *  @param[in] b is the right hand side.
46
+     */
47
+    template < typename Scalar >
48
+    VectorXr CG(const MatrixXr &A, const VectorXr &x0, const VectorXr &b,
49
+        int &max_iter, Scalar &tol) {
50
+
51
+        VectorXr p, q;
52
+        Scalar alpha, beta, rho, rho_1(0);
53
+        VectorXr x = x0;
54
+        Scalar normb = b.norm( );
55
+        VectorXr r = b - A*x;
56
+
57
+        if (normb == 0.0) {
58
+            normb = 1;
59
+        }
60
+
61
+        Scalar resid = r.norm() / normb;
62
+        if (resid <= tol) {
63
+            tol = resid;
64
+            max_iter = 0;
65
+            return x;
66
+        }
67
+
68
+        for (int i = 1; i <= max_iter; i++) {
69
+
70
+            rho = r.transpose()*r;
71
+
72
+            if (i == 1) {
73
+                p = r;
74
+            }
75
+            else {
76
+                beta = rho / rho_1;
77
+                p = r + beta * p;
78
+            }
79
+
80
+            q = A*p;
81
+            alpha = rho / p.dot(q);
82
+
83
+            x += alpha * p;
84
+            r -= alpha * q;
85
+
86
+            if ((resid = r.norm() / normb) <= tol) {
87
+                tol = resid;
88
+                max_iter = i;
89
+                return x;
90
+            }
91
+            rho_1 = rho;
92
+        }
93
+        tol = resid;
94
+        std::cerr << "CG FAILED TO REACH CONVERGENCE\n";
95
+        return x;
96
+    }
97
+
98
+    // Specialised routine that appliex mod(Ax) so that b and x are in real, but
99
+    // A is complex.
100
+    template < typename Scalar >
101
+    VectorXr CG_ModulusAx(const MatrixXcr &A, const VectorXr &x0, const VectorXr &b,
102
+        int &max_iter, Scalar &tol) {
103
+
104
+        VectorXr p, q;
105
+        Scalar beta, rho, rho_1(0);
106
+        Scalar alpha;
107
+        VectorXr x = x0;
108
+        Scalar normb = b.norm( );
109
+        VectorXr r = b.array() - (A*x).array().abs();
110
+
111
+        if (normb == 0.0) {
112
+            normb = 1;
113
+        }
114
+
115
+        Scalar resid = r.norm() / normb;
116
+        if (resid <= tol) {
117
+            tol = resid;
118
+            max_iter = 0;
119
+            return x;
120
+        }
121
+
122
+        for (int i = 1; i <= max_iter; i++) {
123
+
124
+            rho = r.dot(r); //conjugate().transpose()*r;
125
+
126
+            if (i == 1) {
127
+                p = r;
128
+            }
129
+            else {
130
+                beta = rho / rho_1;
131
+                p = r + beta * p;
132
+            }
133
+
134
+            q = (A*p).array().abs();
135
+            alpha = rho / p.dot(q);
136
+
137
+            x += alpha * p;
138
+            r -= alpha * q;
139
+
140
+            if ((resid = r.norm() / normb) <= tol) {
141
+                tol = resid;
142
+                max_iter = i;
143
+                return x;
144
+            }
145
+            rho_1 = rho;
146
+        }
147
+
148
+        tol = resid;
149
+        std::cerr << "CG FAILED TO REACH CONVERGENCE\n";
150
+        return x;
151
+    }
152
+
153
+// Preconditioned version of above
154
+//*****************************************************************
155
+// Iterative template routine -- CG
156
+//
157
+// CG solves the symmetric positive definite linear
158
+// system Ax=b using the Conjugate Gradient method.
159
+//
160
+// CG follows the algorithm described on p. 15 in the
161
+// SIAM Templates book.
162
+//
163
+// The return value indicates convergence within max_iter (input)
164
+// iterations (0), or no convergence within max_iter iterations (1).
165
+//
166
+// Upon successful return, output arguments have the following values:
167
+//
168
+//        x  --  approximate solution to Ax = b
169
+// max_iter  --  the number of iterations performed before the
170
+//               tolerance was reached
171
+//      tol  --  the residual after the final iteration
172
+//
173
+//*****************************************************************
174
+
175
+//template < class Matrix, class Vector, class Preconditioner, class Real >
176
+//int
177
+//CG(const Matrix &A, Vector &x, const Vector &b,
178
+//   const Preconditioner &M, int &max_iter, Real &tol)
179
+//{
180
+    #include <limits>
181
+    template <typename Preconditioner>
182
+    VectorXr CG(const MatrixXr &A, const VectorXr &x0, const VectorXr &b,
183
+        const Preconditioner &M, int &max_iter, Real &tol) {
184
+        //const Eigen::SparseMatrix<Real> &M, int &max_iter, Real &tol) {
185
+
186
+        VectorXr p, z, q;
187
+        VectorXr x = x0;
188
+        Real alpha(0), beta(0), rho(0), rho_1(0);
189
+        Real normb;
190
+        VectorXr r;
191
+        #ifdef LEMMAUSEOMP
192
+        #pragma omp parallel sections
193
+        {
194
+        #endif
195
+            #ifdef LEMMAUSEOMP
196
+            #pragma omp section
197
+            #endif
198
+            {
199
+                normb = b.norm();
200
+            }
201
+            #ifdef LEMMAUSEOMP
202
+            #pragma omp section
203
+            #endif
204
+            {
205
+                r = b - A*x;
206
+            }
207
+        #ifdef LEMMAUSEOMP
208
+        }
209
+        #endif
210
+        if (normb <= std::numeric_limits<double>::epsilon() ) {
211
+            normb = 1;
212
+        }
213
+        Real resid = r.norm() / normb;
214
+        if (resid <= tol) {
215
+            tol = resid;
216
+            max_iter = 0;
217
+            return x;
218
+        }
219
+        // todo do 0th loop manually, gets rid of if statement
220
+        for (int i = 1; i <= max_iter; i++) {
221
+            z = M.solve(r);
222
+            //z = M*r;
223
+            rho = r.transpose()*z;
224
+            if (i == 1) {
225
+                p = z;
226
+            } else {
227
+                beta = rho / rho_1;
228
+                p = z + beta * p;
229
+            }
230
+            q = A*p;
231
+            alpha = rho / p.dot(q);
232
+            #ifdef LEMMAUSEOMP
233
+            #pragma omp parallel sections
234
+            {
235
+            #endif
236
+                #ifdef LEMMAUSEOMP
237
+                #pragma omp section
238
+                #endif
239
+                {
240
+                    x += alpha * p;
241
+                }
242
+                #ifdef LEMMAUSEOMP
243
+                #pragma omp section
244
+                #endif
245
+                {
246
+                    r -= alpha * q;
247
+                }
248
+            #ifdef LEMMAUSEOMP
249
+            }
250
+            #endif
251
+            if ((resid = r.norm() / normb) <= tol) {
252
+               tol = resid;
253
+               max_iter = i;
254
+               return x;
255
+            }
256
+            rho_1 = rho;
257
+        }
258
+        tol = resid;
259
+        std::cerr << "Preconditioned CG failed to converge\n";
260
+        return x;
261
+    }
262
+
263
+    template < typename Scalar >
264
+    VectorXr CGJ(const MatrixXr &A, const VectorXr &x0, const VectorXr &b,
265
+        const Eigen::SparseMatrix<Scalar> &M, int &max_iter, Scalar &tol) {
266
+
267
+        VectorXr p, z, q;
268
+        VectorXr x = x0;
269
+        Scalar alpha(0), beta(0), rho(0), rho_1(0);
270
+        Scalar normb;
271
+        VectorXr r;
272
+        #ifdef LEMMAUSEOMP
273
+        #pragma omp parallel sections
274
+        {
275
+        #endif
276
+            #ifdef LEMMAUSEOMP
277
+            #pragma omp section
278
+            #endif
279
+            {
280
+                normb = b.norm();
281
+            }
282
+            #ifdef LEMMAUSEOMP
283
+            #pragma omp section
284
+            #endif
285
+            {
286
+                r = b - A*x;
287
+            }
288
+        #ifdef LEMMAUSEOMP
289
+        }
290
+        #endif
291
+        if (normb <= std::numeric_limits<double>::epsilon() ) {
292
+            normb = 1;
293
+        }
294
+        Scalar resid = r.norm() / normb;
295
+        if (resid <= tol) {
296
+            tol = resid;
297
+            max_iter = 0;
298
+            return x;
299
+        }
300
+        // todo do 0th loop manually, gets rid of if statement
301
+        for (int i = 1; i <= max_iter; i++) {
302
+            //z = M.solve(r);
303
+            z = M*r;
304
+            rho = r.transpose()*z;
305
+            if (i == 1) {
306
+                p = z;
307
+            } else {
308
+                beta = rho / rho_1;
309
+                p = z + beta * p;
310
+            }
311
+            q = A*p;
312
+            alpha = rho / p.dot(q);
313
+            #ifdef LEMMAUSEOMP
314
+            #pragma omp parallel sections
315
+            {
316
+            #endif
317
+                #ifdef LEMMAUSEOMP
318
+                #pragma omp section
319
+                #endif
320
+                {
321
+                    x += alpha * p;
322
+                }
323
+                #ifdef LEMMAUSEOMP
324
+                #pragma omp section
325
+                #endif
326
+                {
327
+                    r -= alpha * q;
328
+                }
329
+            #ifdef LEMMAUSEOMP
330
+            }
331
+            #endif
332
+            if ((resid = r.norm() / normb) <= tol) {
333
+               tol = resid;
334
+               max_iter = i;
335
+               return x;
336
+            }
337
+            rho_1 = rho;
338
+        }
339
+        tol = resid;
340
+        std::cerr << "Preconditioned CG failed to converge\n";
341
+        return x;
342
+    }
343
+
344
+    ///////////////////////////////////////////////////////
345
+    // Log Barrier
346
+    /** Solves one iteration, using implicit multiplication of At*b, and ATA.
347
+     *  @param[in] G is the sensitivity matrix to be inverted.
348
+     *  @param[in] WdTWd is the data weighting matrix, usually sparse.
349
+     *  @param[in] WmTWm is the model weighting matrix, usually sparse.
350
+     *  @param[in] X1 is a vector of the inverse of the current model X. Used in
351
+     *  log barrier. Should be computed as X1 = VectorXr( 1. / (x.array() - minVal ))
352
+     *  @param[in] Y1 is a vector of the inverse of the current model X. Used in
353
+     *  log barrier. Should be computed as X1 = VectorXr( 1. / (maxVal - x.array() ))
354
+     *  @param[in] X2 is the analaogous inverse of X^2 diagonal matrix, stored
355
+     *  as a Vector.
356
+     *  @param[in] Y2 is the analaogous inverse of (maxVal-X)^2 diagonal matrix, stored
357
+     *  as a Vector.
358
+     *  @param[in] D2 is the datamisfit vector, formally (d_predicted - d_observed).
359
+     *  @param[in,out] Mk is the input / output solution vector. The input value is
360
+     *  an itital guess, and output is the solution.
361
+     *  @param[in] Mr is the reference model.
362
+     *  @param[in] BETA is the regularisation (Tikhonov parameter) to apply
363
+     *  @param[in] P is a preconditioner of G. The product Pb ~ x
364
+     *  @param[in,out] max_iter is the number of iterations.
365
+     *  @param[in,out] tol is the desired tolerance on input, and achieved on
366
+     *  output.
367
+     */
368
+    template < typename  Scalar >
369
+    int implicit_log_CG(const MatrixXr& G, const MatrixXr& WdTWd, const VectorXr& WmTWm,
370
+				const VectorXr& X1, const VectorXr& X2,
371
+				const VectorXr& Y1, const VectorXr& Y2,
372
+				const VectorXr& D2, VectorXr& Mk, const VectorXr& Mr,
373
+				const Scalar& BETA, const MatrixXr& P,
374
+                int& max_iter, Scalar& tol) {
375
+
376
+        // TODO add WdTWD to this!
377
+
378
+        Scalar resid;
379
+        VectorXr p, z, q;
380
+        Scalar alpha(0), beta(0), rho(0), rho_1(0);
381
+
382
+        // Calculate 'B'
383
+        VectorXr delM = Mk - Mr;
384
+        VectorXr B = (-G.transpose()*D2).array() - BETA*((WmTWm.asDiagonal()*delM).array())
385
+                     + X1.array() + Y1.array();
386
+
387
+        Scalar normb = B.norm();
388
+
389
+        // Implicit calc of A*x
390
+        VectorXr Y = BETA*(WmTWm.asDiagonal()*Mk).array() +
391
+                (X2.asDiagonal()*Mk).array() + (Y2.asDiagonal()*Mk).array();
392
+        VectorXr Z = G*Mk;
393
+        VectorXr U = G.transpose()*Z;
394
+
395
+        VectorXr r = B - (Y + U);
396
+
397
+        if (normb == 0.0) normb = 1;
398
+
399
+        if ((resid = r.norm() / normb) <= tol) {
400
+            tol = resid;
401
+            max_iter = 0;
402
+            return 0;
403
+        }
404
+
405
+        for (int i = 1; i <= max_iter; i++) {
406
+            //z = M.solve(r); // we can solve directly z = P*r
407
+            z = P*r;
408
+            rho = r.dot(z);
409
+            if (i == 1)  p = z;
410
+            else {
411
+                beta = rho / rho_1;
412
+                p = beta * p;
413
+ 	            p = p+z;
414
+            }
415
+            Y = BETA*(WmTWm.array()*p.array()) + X2.array()*p.array() + Y2.array()*p.array();
416
+            Z = G*p;
417
+            U = G.transpose()*Z;
418
+            q = Y+U;
419
+
420
+            alpha = rho / p.dot(q);
421
+
422
+            Mk = Mk + alpha * p;
423
+            r  = r - (alpha * q);
424
+
425
+            if ((resid = r.norm() / normb) <= tol) {
426
+                tol = resid;
427
+                max_iter = i;
428
+                return 0;
429
+            }
430
+            rho_1 = rho;
431
+        }
432
+        tol = resid;
433
+        return 1;
434
+    }
435
+} // end of namespace Lemma
436
+
437
+#endif   // ----- #ifndef CG_INC  -----

+ 101
- 0
LemmaCore/include/costransintegrationkernel.h View File

@@ -0,0 +1,101 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API
2
+ */
3
+
4
+/* This Source Code Form is subject to the terms of the Mozilla Public
5
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
6
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7
+
8
+/**
9
+  @file
10
+  @author   Trevor Irons
11
+  @date     02/08/2011
12
+  @version  $Id: costransintegrationkernel.h 87 2013-09-05 22:44:05Z tirons $
13
+ **/
14
+
15
+#ifndef  COSTRANSINTEGRATIONKERNEL_INC
16
+#define  COSTRANSINTEGRATIONKERNEL_INC
17
+
18
+#include "integrationkernel.h"
19
+
20
+namespace Lemma {
21
+
22
+    // ===================================================================
23
+    //  Class:  CosTransIntegrationKernel
24
+    /**
25
+      @class
26
+      \brief    Integration kernel for testing cosine transform.
27
+      \details  Evaluates cosine at the argument, using lagged convolution.
28
+                all of these kernels have exact solutions.
29
+     */
30
+    // ===================================================================
31
+    class CosTransIntegrationKernel : public IntegrationKernel<Real> {
32
+
33
+        public:
34
+
35
+            // ====================  LIFECYCLE     =======================
36
+
37
+            /** Returns a pointer to a new object of type CosTransIntegrationKernel.
38
+             * It allocates all necessary memory.
39
+             */
40
+            static CosTransIntegrationKernel* New();
41
+
42
+            /** Deletes this object. Delete also disconnects any
43
+             * attachments to this object.
44
+             */
45
+            void Delete();
46
+
47
+            // ====================  OPERATORS     =======================
48
+
49
+            Real Argument(const Real&x, const int& iRelated);
50
+
51
+            int GetNumRel();
52
+
53
+            /// Sets the value 'A' used in test cases
54
+            void SetA(const Real& A);
55
+
56
+            /** Sets the integral to evaluate (1, 2, 3)
57
+             */
58
+            void SetIntegral(const int& i);
59
+
60
+            /** Returns the analytical answer at A and B */
61
+            Real GetAnalytical(const Real& B);
62
+            // ====================  OPERATIONS    =======================
63
+
64
+            // ====================  ACCESS        =======================
65
+
66
+            // ====================  INQUIRY       =======================
67
+
68
+        protected:
69
+
70
+            // ====================  LIFECYCLE     =======================
71
+
72
+            /** Deletes this object. Delete also disconnects any
73
+             * attachments to this object.
74
+             */
75
+            void Release();
76
+
77
+            /// Default protected constructor.
78
+            CosTransIntegrationKernel (const std::string& name);
79
+
80
+            /// Default protected constructor.
81
+            ~CosTransIntegrationKernel ();
82
+
83
+            // ====================  DATA MEMBERS  =========================
84
+
85
+            /** Value used in test cases  */
86
+            Real A;
87
+
88
+            /** Test integral to evaluate */
89
+            int Integral;
90
+
91
+        private:
92
+
93
+    }; // -----  end of class  CosTransIntegrationKernel  -----
94
+
95
+
96
+}		// -----  end of Lemma  name  -----
97
+
98
+#endif   // ----- #ifndef COSTRANSINTEGRATIONKERNEL_INC  -----
99
+
100
+/* vim: set tabstop=4 expandtab: */
101
+/* vim: set filetype=cpp: */

+ 85
- 0
LemmaCore/include/data.h View File

@@ -0,0 +1,85 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     03/01/2010
11
+  @version  $Id: data.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  _DATA_H_INC
15
+#define  _DATA_H_INC
16
+
17
+#include "LemmaObject.h"
18
+
19
+namespace Lemma {
20
+
21
+    // ===================================================================
22
+    //        Class:  Data
23
+    /** \brief Abstract class for data from an instrument
24
+     *  \details Currently provides no functionality, but this will likely
25
+     *          change in the near future.
26
+     */
27
+    // ===================================================================
28
+    class Data : public LemmaObject {
29
+
30
+        friend std::ostream &operator<<(std::ostream &stream,
31
+                const Data &ob);
32
+
33
+        public:
34
+
35
+            // ====================  LIFECYCLE     =======================
36
+
37
+            /** Copies the *structure* of this class to a new object and
38
+             * returns a pointer to this object. Memory management is
39
+             * the responsibility of the receiver!. The data values are
40
+             * not copied.
41
+             */
42
+            virtual Data* Clone()=0;
43
+
44
+            // ====================  OPERATORS     =======================
45
+
46
+            // ====================  OPERATIONS    =======================
47
+
48
+            /** Clears all data arrays and containers
49
+             */
50
+            virtual void Zero()=0;
51
+
52
+            /** Data2 needs to be compatible with the calling class. Data2 will
53
+             * be cast into the calling class type. Most of the time this
54
+             * cast will not perform anything, as Data2 *is* the same type
55
+             * as the calling class.
56
+             */
57
+            virtual Real Norm(Data* Data2)=0;
58
+
59
+            // ====================  ACCESS        =======================
60
+
61
+            // ====================  INQUIRY       =======================
62
+
63
+
64
+        protected:
65
+
66
+            // ====================  LIFECYCLE     =======================
67
+
68
+            /** Default protected constructor. */
69
+            Data (const std::string &name);
70
+
71
+            /** Default protected constructor. */
72
+            ~Data ();
73
+
74
+            // ====================  DATA MEMBERS  =========================
75
+
76
+        private:
77
+
78
+    }; // -----  end of class  Data  -----
79
+
80
+}       // -----  end of Lemma  name  -----
81
+
82
+#endif   // ----- #ifndef _DATA_H_INC  -----
83
+
84
+/* vim: set tabstop=4 expandtab: */
85
+/* vim: set filetype=cpp: */

+ 181
- 0
LemmaCore/include/datafem.h View File

@@ -0,0 +1,181 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+
8
+/**
9
+  @file
10
+  @author   M. Andy Kass
11
+  @date     01/03/2013
12
+  @version  $Id$
13
+ **/
14
+
15
+#ifndef DATAFEM_H
16
+#define DATAFEM_H
17
+
18
+#include "data.h"
19
+
20
+namespace Lemma {
21
+
22
+// ===================================================================
23
+//        Class:  DataFEM
24
+/// \brief
25
+/// \details
26
+// ===================================================================
27
+	class DataFEM : public Data {
28
+
29
+		friend std::ostream &operator<<(std::ostream &stream,
30
+			const DataFEM &ob);
31
+
32
+	public:
33
+
34
+	// ====================  LIFECYCLE     =======================
35
+
36
+	static DataFEM* New();
37
+
38
+	DataFEM* Clone();
39
+
40
+	void Delete();
41
+
42
+	// ====================  OPERATORS     =======================
43
+
44
+
45
+	// ====================  OPERATIONS    =======================
46
+
47
+	void Zero();
48
+
49
+	Real Norm(Data* Data2);
50
+
51
+
52
+	// ====================  ACCESS        =======================
53
+
54
+	/// Set data dimensions
55
+	void SetSize(const int &nobs,const int &nfreq);
56
+
57
+	/// Input the data
58
+	void SetData(const MatrixXr &inputdata);
59
+
60
+	/// Input uncertainties
61
+	void SetUncertainties(const MatrixXr &uncertain);
62
+
63
+	/// Input the positions
64
+	void SetPositions(const Vector3Xr &positions);
65
+
66
+	/// Set the frequencies
67
+	void SetFreq(const VectorXr &freqs);
68
+
69
+	/// Set Tx Orientation
70
+	void SetTxOrientation(const Eigen::Matrix<ORIENTATION, Eigen::Dynamic, 1> &txorientation);
71
+
72
+	/// Set Rx Orientation
73
+	void SetRxOrientation(const Eigen::Matrix<ORIENTATION, Eigen::Dynamic, 1> &rxorientation);
74
+
75
+	/// Set the transmitter moments
76
+	void SetTxMom(const VectorXr &txmom);
77
+
78
+	/// Set Tx/Rx Separation
79
+	void SetTxRxSep(const Vector3Xr &txrxsep);
80
+
81
+	/// Set Scale Factor
82
+	void SetScaleFac(const VectorXr &scalefac);
83
+
84
+	// ====================  INQUIRY       =======================
85
+
86
+	/// Get number of frequencies used
87
+	int GetnFreq();
88
+
89
+	/// Get number of observation locations
90
+	int GetnObs();
91
+
92
+	/// Get the data cube
93
+	MatrixXr GetFEMDataCube();
94
+
95
+	/// Get the uncertainties
96
+	MatrixXr GetFEMUncertainCube();
97
+
98
+	/// Get a single data coefficient
99
+	Real GetDataCoeff(const int &x, const int &y);
100
+
101
+	/// Get the frequency array
102
+	VectorXr GetFreqs();
103
+
104
+	/// Get the position array
105
+	Vector3Xr GetXYZ();
106
+
107
+	/// Get the position for a single datum
108
+	VectorXr GetSingleXYZ(const int &x);
109
+
110
+	/// Get array of transmitter orientations
111
+	Eigen::Matrix<ORIENTATION, Eigen::Dynamic, 1> GetTxOrien();
112
+
113
+	/// Get array of receiver orientations
114
+	Eigen::Matrix<ORIENTATION, Eigen::Dynamic, 1> GetRxOrien();
115
+
116
+	/// Get array of Tx Moments
117
+	VectorXr GetTxMom();
118
+
119
+	/// Get Tx/Rx Separation
120
+	Vector3Xr GetTxRxSep();
121
+
122
+	/// Get Scale Factor
123
+	VectorXr GetScaleFac();
124
+
125
+	protected:
126
+
127
+	// ====================  LIFECYCLE     =======================
128
+
129
+		/// Default protected constructor.
130
+		DataFEM (const std::string &name);
131
+
132
+		/// Default protected constructor.
133
+		~DataFEM ();
134
+
135
+		void Release();
136
+
137
+	// ====================  DATA MEMBERS  =========================
138
+
139
+	/// Number of frequencies
140
+	int nFreq;
141
+
142
+	/// Number of observation locations
143
+	int nObs;
144
+
145
+	/// Data cube containing the inphase and quadrature
146
+	MatrixXr FEMDataCube;
147
+
148
+	/// Data cube containing the uncertainties
149
+	MatrixXr FEMUncertainCube;
150
+
151
+	/// Array of frequencies
152
+	VectorXr freq;
153
+
154
+	/// Position vector, with z as height above the ground surface (pos)
155
+	Vector3Xr xyz;
156
+
157
+	/// Array of Tx orientations (x,y,z) for each freq
158
+	Eigen::Matrix<ORIENTATION,Eigen::Dynamic,1> TxOrientation;
159
+
160
+	/// Array of Rx orientations (x,y,z) for each freq
161
+	Eigen::Matrix<ORIENTATION,Eigen::Dynamic,1> RxOrientation;
162
+
163
+	/// Transmitter moments, one for each frequency
164
+	VectorXr TxMom;
165
+
166
+	/// Tx/Rx Separation in local, right hand system with x aligned with flight
167
+	Vector3Xr TxRxSep;
168
+
169
+	/// Scale factor as described in EM1DFM manual
170
+	VectorXr ScaleFac;
171
+
172
+
173
+	private:
174
+
175
+}; // -----  end of class  DataFEM  -----
176
+} // end of namespace Lemma
177
+#endif
178
+
179
+/* vim: set tabstop=4 expandtab: */
180
+/* vim: set filetype=cpp: */
181
+

+ 67
- 0
LemmaCore/include/datareader.h View File

@@ -0,0 +1,67 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     03/01/2010
11
+  @version  $Id: datareader.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  DATAREADER_H_INC
15
+#define  DATAREADER_H_INC
16
+
17
+#include "LemmaObject.h"
18
+#include "data.h"
19
+
20
+namespace Lemma {
21
+
22
+// ===================================================================
23
+//        Class:  DataReader
24
+/// \brief  Abstract class whose derived members read data files and
25
+/// converts them to Data Classes
26
+/// \details
27
+// ===================================================================
28
+class DataReader : public LemmaObject {
29
+
30
+    friend std::ostream &operator<<(std::ostream &stream,
31
+            const DataReader &ob);
32
+
33
+    public:
34
+
35
+        // ====================  LIFECYCLE     =======================
36
+
37
+        // ====================  OPERATORS     =======================
38
+
39
+        // ====================  OPERATIONS    =======================
40
+
41
+        // ====================  ACCESS        =======================
42
+        virtual Data* GetData()=0;
43
+
44
+        // ====================  INQUIRY       =======================
45
+
46
+    protected:
47
+
48
+        // ====================  LIFECYCLE     =======================
49
+
50
+        /// Default protected constructor.
51
+        DataReader (const std::string &name);
52
+
53
+        /// Default protected constructor.
54
+        ~DataReader ();
55
+
56
+        // ====================  DATA MEMBERS  =========================
57
+
58
+    private:
59
+
60
+}; // -----  end of class  DataReader  -----
61
+
62
+}       // -----  end of Lemma  name  -----
63
+
64
+#endif   // ----- #ifndef DATAREADER_H_INC  -----
65
+
66
+/* vim: set tabstop=4 expandtab: */
67
+/* vim: set filetype=cpp: */

+ 67
- 0
LemmaCore/include/datareaderfem.h View File

@@ -0,0 +1,67 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     01/03/2013
11
+  @version  $Id$
12
+ **/
13
+
14
+#ifndef __DATAREADERFEM_H
15
+#define __DATAREADERFEM_H
16
+
17
+#include "datareader.h"
18
+#include "datafem.h"
19
+
20
+namespace Lemma {
21
+
22
+
23
+// ===================================================================
24
+//        Class:  DataReaderFem
25
+/// \brief
26
+/// \details
27
+// ===================================================================
28
+	class DataReaderFem : DataReader {
29
+
30
+	public:
31
+
32
+	// ====================  LIFECYCLE     =======================
33
+
34
+		static DataReaderFem* New();
35
+
36
+		void Delete();
37
+
38
+	// ====================  OPERATORS     =======================
39
+
40
+	// ====================  OPERATIONS    =======================
41
+
42
+	// ====================  ACCESS        =======================
43
+		Data* GetData();
44
+
45
+	// ====================  INQUIRY       =======================
46
+
47
+
48
+
49
+	protected:
50
+
51
+	// ====================  LIFECYCLE     =======================
52
+
53
+		/// Default protected constructor.
54
+		DataReaderFem (const std::string &name);
55
+
56
+		/// Default protected constructor.
57
+		~DataReaderFem ();
58
+
59
+		void Release();
60
+
61
+	// ====================  DATA MEMBERS  =========================
62
+
63
+	private:
64
+
65
+}; // -----  end of class  DataReaderFem  -----
66
+} // end of namespace Lemma
67
+#endif

+ 100
- 0
LemmaCore/include/datareaderfemubc.h View File

@@ -0,0 +1,100 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     01/03/2013
11
+  @version  $Id$
12
+ **/
13
+
14
+#ifndef __DATAREADERFEMUBC_H
15
+#define __DATAREADERFEMUBC_H
16
+
17
+#include "datareader.h"
18
+#include "datafem.h"
19
+
20
+namespace Lemma {
21
+
22
+
23
+// ===================================================================
24
+//        Class:  DataReaderFemUBC
25
+/// \brief  Reads UBC-format observation files
26
+/// \details This class reads UBC-format EM1DFM observation files and
27
+/// populates a DataFEM class.  Assumptions: the frequencies and coil
28
+/// geometries remain fixed throughout a survey.
29
+// ===================================================================
30
+	class DataReaderFemUBC : DataReader {
31
+
32
+		friend std::ostream &operator<<(std::ostream &stream,
33
+			const DataReaderFemUBC &ob);
34
+
35
+
36
+	public:
37
+
38
+	// ====================  LIFECYCLE     =======================
39
+
40
+		static DataReaderFemUBC* New();
41
+
42
+		void Delete();
43
+
44
+	// ====================  OPERATORS     =======================
45
+
46
+	// ====================  OPERATIONS    =======================
47
+
48
+		void ReadData(const std::string &datafile,int vbs = 0);
49
+
50
+	// ====================  ACCESS        =======================
51
+
52
+		///Attach the data object
53
+		void SetDataFEM(DataFEM* inputtemp);
54
+
55
+
56
+	// ====================  INQUIRY       =======================
57
+		/// Return the data object
58
+		DataFEM* GetData();
59
+
60
+	protected:
61
+
62
+	// ====================  LIFECYCLE     =======================
63
+
64
+		/// Default protected constructor.
65
+		DataReaderFemUBC (const std::string &name);
66
+
67
+		/// Default protected constructor.
68
+		~DataReaderFemUBC ();
69
+
70
+		void Release();
71
+
72
+		/// Load read data into data object
73
+		void SendData();
74
+
75
+	// ====================  DATA MEMBERS  =========================
76
+
77
+	DataFEM* InputData;
78
+
79
+	int nObs;
80
+	int nFreq;
81
+	MatrixXr DataMatrix;
82
+	MatrixXr Uncertainties;
83
+	Vector3Xr PositionVec;
84
+	VectorXr Freqs;
85
+	VectorXr TxMom;
86
+	Vector3Xr TxRxSep;
87
+	Eigen::Matrix<ORIENTATION,Eigen::Dynamic,1> TxOrientation;
88
+	Eigen::Matrix<ORIENTATION,Eigen::Dynamic,1> RxOrientation;
89
+	VectorXr ScaleFac;
90
+
91
+
92
+
93
+	private:
94
+
95
+}; // -----  end of class  DataReaderFemUBC  -----
96
+} // end of namespace Lemma
97
+#endif
98
+
99
+/* vim: set tabstop=4 expandtab: */
100
+/* vim: set filetype=cpp: */

+ 82
- 0
LemmaCore/include/datareadertem.h View File

@@ -0,0 +1,82 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     12/28/2011
11
+  @version  $Id: datareadertem.h 87 2013-09-05 22:44:05Z tirons $
12
+ **/
13
+
14
+#ifndef __DATAREADERTEM_H
15
+#define __DATAREADERTEM_H
16
+
17
+#include "datareader.h"
18
+#include "datatem.h"
19
+
20
+namespace Lemma {
21
+// ===================================================================
22
+//        Class:  DataReaderTem
23
+/// \brief
24
+/// \details
25
+// ===================================================================
26
+class DataReaderTem : DataReader {
27
+
28
+	public:
29
+
30
+		// ====================  LIFECYCLE     =======================
31
+
32
+		static DataReaderTem* New();
33
+
34
+		void Delete();
35
+
36
+		// ====================  OPERATORS     =======================
37
+
38
+		// ====================  OPERATIONS    =======================
39
+
40
+		/// Read in the data file
41
+		void ReadData(const std::string &datafile);
42
+
43
+		// ====================  ACCESS        =======================
44
+
45
+		/// Attach the data object
46
+		void SetDataTEM(DataTEM* inputtemp);
47
+
48
+		/// Output the data object
49
+		DataTEM* GetData();
50
+
51
+		/// Return number of gates
52
+		int GetnGates();
53
+
54
+		/// Return number of soundings
55
+		int GetnObs();
56
+
57
+		// ====================  INQUIRY       =======================
58
+
59
+
60
+
61
+	protected:
62
+
63
+		// ====================  LIFECYCLE     =======================
64
+
65
+		/// Default protected constructor.
66
+		DataReaderTem (const std::string &name);
67
+
68
+		/// Default protected constructor.
69
+		~DataReaderTem ();
70
+
71
+		void Release();
72
+
73
+		// ====================  DATA MEMBERS  =========================
74
+
75
+		/// Input data
76
+		DataTEM* InputData;
77
+
78
+	private:
79
+
80
+}; // -----  end of class  Datareadertem  -----
81
+} // end of namespace Lemma
82
+#endif // __DATAREADERTEM_H

+ 131
- 0
LemmaCore/include/datatem.h View File

@@ -0,0 +1,131 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     03/23/2010
11
+  @version  $Id: datatem.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  DATATEM_INC
15
+#define  DATATEM_INC
16
+
17
+#include "data.h"
18
+
19
+namespace Lemma {
20
+
21
+    // ===================================================================
22
+    //        Class:  DataTEM
23
+    /// \brief  Class for TEM data.
24
+    /// \details  A lot to do here. Just a placeholder.
25
+    // ===================================================================
26
+    class DataTEM : public Data {
27
+
28
+        friend std::ostream &operator<<(std::ostream &stream,
29
+            const DataTEM &ob);
30
+
31
+        public:
32
+
33
+            // ====================  LIFECYCLE     =======================
34
+
35
+            /** Returns pointer to new object
36
+             */
37
+            static DataTEM* New();
38
+
39
+            /** @copybrief Data::Clone()
40
+             *  @copydetails Data::Clone()
41
+             */
42
+            DataTEM* Clone();
43
+
44
+            /**
45
+             * @copybrief LemmaObject::Delete()
46
+             * @copydetails LemmaObject::Delete()
47
+             */
48
+            void Delete();
49
+
50
+            // ====================  OPERATORS     =======================
51
+
52
+            // ====================  OPERATIONS    =======================
53
+
54
+            void Zero();
55
+
56
+            /** Data2 needs to be compatible with DataTEM, that is
57
+             *  to say that it needs to be able to be cast into the
58
+             *  form of DataTEM. It also needs to be aligned with
59
+             *  the calling class.
60
+             */
61
+            Real Norm(Data* Data2);
62
+
63
+            // ====================  ACCESS        =======================
64
+
65
+			/// Set data dimensions
66
+			void SetSize(const int &nObs,const int &nGates);
67
+
68
+			/// Input the data
69
+			void SetData(const MatrixXr &inputdata);
70
+
71
+			/// Input the positions
72
+			void SetPositions(const Vector3Xr &positions);
73
+
74
+			/// Return number of time gates
75
+			int GetnGates();
76
+
77
+			/// Return number of soundings
78
+			int GetnObs();
79
+
80
+			/// Return data matrix
81
+			MatrixXr GetData();
82
+
83
+			/// Return single data coefficient
84
+			Real GetDataCoeff(const int &x,const int &y);
85
+
86
+			/// Return time
87
+			VectorXr GetTimes();
88
+
89
+			/// Return positions
90
+			Vector3Xr GetPositions();
91
+
92
+            // ====================  INQUIRY       =======================
93
+
94
+        protected:
95
+
96
+            // ====================  LIFECYCLE     =======================
97
+
98
+            /// Default protected constructor.
99
+            DataTEM (const std::string &name);
100
+
101
+            /// Default protected constructor.
102
+            ~DataTEM ();
103
+
104
+            /**
105
+             * @copybrief LemmaObject::Release()
106
+             * @copydetails LemmaObject::Release()
107
+             */
108
+            void Release();
109
+
110
+            // ====================  DATA MEMBERS  =========================
111
+
112
+			MatrixXr TEMDataCube;
113
+
114
+			VectorXr times;
115
+
116
+			Vector3Xr locations;
117
+
118
+			int nGates;
119
+
120
+			int nObs;
121
+
122
+    private:
123
+
124
+    }; // -----  end of class  DataTEM  -----
125
+
126
+}       // -----  end of Lemma  name  -----
127
+
128
+#endif   // ----- #ifndef DATATEM_INC  -----
129
+
130
+/* vim: set tabstop=4 expandtab: */
131
+/* vim: set filetype=cpp: */

+ 83
- 0
LemmaCore/include/digitalfiltercostrans.h View File

@@ -0,0 +1,83 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     02/07/2011
11
+  @version  $Id: digitalfiltercostrans.h 87 2013-09-05 22:44:05Z tirons $
12
+ **/
13
+
14
+#ifndef __DIGITALFILTERCOSTRANS_H
15
+#define __DIGITALFILTERCOSTRANS_H
16
+
17
+#include "digitalfilterintegrator.h"
18
+
19
+namespace Lemma {
20
+
21
+	// ===================================================================
22
+	//        Class:  DigitalFilterCosTrans
23
+	/** \brief Cosine Transform via digital filters
24
+	    \details Based on Andersons' Hankel transform, this calculates
25
+	 			the cosine transform of a discrete function
26
+				using a digital filter approach.  Filter weights are
27
+				hard-coded.
28
+				Calculates transform of the form:
29
+				\f[ \int_0^\infty f(x) \cos (x\omega)~dx
30
+				\f]
31
+    */
32
+
33
+	// ===================================================================
34
+	class DigitalFilterCosTrans : public DigitalFilterIntegrator<Real> {
35
+
36
+		friend std::ostream &operator<<(std::ostream &stream, const
37
+			DigitalFilterCosTrans &ob);
38
+
39
+		public:
40
+
41
+			// ====================  LIFECYCLE     =======================
42
+
43
+			static DigitalFilterCosTrans* New();
44
+
45
+			void Delete();
46
+
47
+			// ====================  OPERATORS     =======================
48
+
49
+			// ====================  OPERATIONS    =======================
50
+
51
+			// ====================  ACCESS        =======================
52
+
53
+			// ====================  INQUIRY       =======================
54
+
55
+		protected:
56
+
57
+			// ====================  LIFECYCLE     =======================
58
+
59
+			/// Default protected constructor.
60
+			DigitalFilterCosTrans (const std::string& name);
61
+
62
+			/// Default protected constructor.
63
+			~DigitalFilterCosTrans ();
64
+
65
+			void Release();
66
+
67
+			/// Set all the filter weights
68
+			void SetFilterWeights();
69
+
70
+			// ====================  DATA MEMBERS  =========================
71
+
72
+			//Eigen::Matrix<Real, 787, 1> FilterWeights;
73
+
74
+		private:
75
+
76
+    }; // -----  end of class  DigitalFilterCosTrans  -----
77
+
78
+} //end of namespace Lemma
79
+
80
+#endif // __DIGITALFILTERCOSTRANS_H
81
+
82
+/* vim: set tabstop=4 expandtab: */
83
+/* vim: set filetype=cpp: */

+ 542
- 0
LemmaCore/include/digitalfilterintegrator.h View File

@@ -0,0 +1,542 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     02/07/2011
11
+  @version  $Id: digitalfilterintegrator.h 124 2014-02-07 04:26:26Z tirons $
12
+ **/
13
+
14
+#ifndef  DIGITALFILTERINTEGRATOR_INC
15
+#define  DIGITALFILTERINTEGRATOR_INC
16
+
17
+#include "integrator.h"
18
+#include "integrationkernel.h"
19
+
20
+namespace Lemma {
21
+
22
+    // ===================================================================
23
+    //  Class:  DigitalFilterIntegrator
24
+    /**
25
+      @class
26
+      \brief   Reimplimentation of Walt Anderson's digital filtering
27
+               algorithms which are public domain.
28
+      \details Walt Anderson wrote several routines for digital filtering
29
+               that reused a lot of code. The original fortran codes are
30
+               available at:
31
+        ftp://ftpext.usgs.gov/pub/cr/co/denver/musette/pub/anderson/
32
+               This is an abstract class. Concrete classes must define the
33
+               a function to make arguments.
34
+               Template specilizations are found in the implimentation file
35
+               digitalfilterintegrator.cpp. This was necessary to support
36
+               the design paradigm of Lemma.
37
+     */
38
+    // ===================================================================
39
+    template <typename Scalar>
40
+    class DigitalFilterIntegrator : public Integrator {
41
+
42
+        /** Prints out basic info about the class, Complex implimentation */
43
+
44
+        template <typename Scalar2>
45
+        friend std::ostream &operator<<(std::ostream &stream,
46
+                        const DigitalFilterIntegrator<Scalar2> &ob);
47
+
48
+        public:
49
+
50
+            // ====================  LIFECYCLE     =======================
51
+
52
+            // ====================  OPERATORS     =======================
53
+
54
+            // ====================  OPERATIONS    =======================
55
+
56
+            /** Sets the number of desired convolutions. From Anderson, where
57
+                this value is called NB:
58
+                NUMBER OF LAGGED CONVOLUTIONS DESIRED (NB.GE.1).  USE
59
+                NB=1 IF B=BMIN=BMAX (I.E.,NO LAGGING DESIRED).  USE
60
+                NB>1 IF B IS LAGGED IN (BMIN,BMAX), WHERE
61
+                BMIN=BMAX*DEXP(-.1D0*(NB-1)) DOES NOT UNDERFLOW THE DEXP
62
+                RANGE.  THE B-LAGGED SPACING IS .1D0 IN LOG-SPACE. FOR
63
+                CONVENIENCE IN SPLINE INTERPOLATION LATER, EACH B IN
64
+                (BMIN,BMAX) IS RETURNED IN ARRAY ARG(I),I=1,NB, WHERE
65
+                ARG(I+1)/ARG(I)=DEXP(.1D0) FOR ALL I.  IF BMAX>BMIN>0 IS
66
+                GIVEN, THEN AN EFFECTIVE VALUE OF NB IS DETERMINED AS
67
+                NB=DINT(10.*DLOG(BMAX/BMIN))+I, WHERE I>1 IS RECOMMENDED,
68
+                PARTICULARLY IF USING SUBSEQUENT SPLINE INTERPOLATION FOR
69
+                A DIFFERENT B-SPACING THAN USED IN THE DIGITAL FILTER. IF
70
+                SPLINE INTERPOLATION IS TO BE USED LATER, IT IS GENERALLY
71
+                BEST TO USE DLOG(ARG(I)) INSTEAD OF ARG(I) -VS- DANS(I),
72
+                FOR I=1,NB.
73
+            */
74
+            void SetNumConv(const int& i);
75
+
76
+            /** Evaluates related integrals */
77
+            void ComputeRelated(const Real& rho,
78
+                IntegrationKernel<Scalar>* Kernel);
79
+
80
+            /** Evaluates the integral
81
+            @param[in]tol  REQUESTED TRUNCATION TOLERANCE AT BOTH FILTER TAILS
82
+              FOR ADAPTIVE CONVOLUTION FOR ALL NB TRANSFORMS.  THE
83
+              TRUNCATION CRITERION IS ESTABLISHED DURING CONVOLUTION IN
84
+              A FIXED ABSCISSA RANGE (USING WEIGHTS 426-461) OF THE
85
+              COSINE FILTER AS THE MAXIMUM ABSOLUTE CONVOLVED PRODUCT
86
+              TIMES TOL.  THE CONVOLUTION SUMMATION IS TERMINATED
87
+              ON EITHER SIDE OF THE FIXED RANGE WHENEVER THE ABSOLUTE
88
+              PRODUCT .LE. THE TRUNCATION CRITERION.  IN GENERAL, A
89
+              DECREASING TOLERANCE WILL PRODUCE HIGHER ACCURACY SINCE
90
+              MORE FILTER WEIGHTS ARE USED (UNLESS EXPONENT UNDERFLOW
91
+              OCCURS IN THE TRANSFORM INPUT FUNCTION EVALUATION).
92
+              ONE MAY SET TOL=0.D0 TO OBTAIN MAXIMUM ACCURACY FOR ALL
93
+              NB DOUBLE-PRECISION COSINE TRANSFORMS IN DANS(NB).
94
+              HOWEVER, THE ACTUAL RELATIVE ERRORS CANNOT BE EXPECTED TO
95
+              BE SMALLER THAN ABOUT .1D-12 REGARDLESS OF THE TOLERANCE
96
+              VALUE USED, SINCE DOUBLE-PRECISION FILTER WEIGHTS AND A
97
+              DOUBLE-PRECISION FUNCTION ARE USED. IN ANY EVENT,
98
+              ONE SHOULD ALWAYS CHOOSE TOL<<DESIRED RELATIVE ERROR.
99
+           ** ACCURACY WARNING **  SOME HIGHLY OSCILLATORY FUNCTIONS
100
+              FUN(G) AND (OR) LIMITING CASES OF B NEAR MACHINE-ZERO
101
+              (OR INFINITY) SHOULD BE AVOIDED, OTHERWISE UNSATISFACTORY
102
+              RESULTS (E.G., RELATIVE & ABSOLUTE ERRORS>>TOL) MAY OCCUR.
103
+              @param[in] ntol  NUMBER OF CONSECUTIVE TIMES THE TRUNCATION CRITERION (TOL)
104
+              IS TO BE MET AT EITHER FILTER TAIL BEFORE FILTER
105
+              TRUNCATION OCCURS.  NTOL=1 SHOULD BE USED FOR INPUT
106
+              FUNCTIONS THAT DO NOT HAVE MANY ZEROS IN (0,INFINITY). FOR
107
+              OSCILLATORY FUNCTIONS WITH MANY ZEROS, NTOL>1 MAY BE USED
108
+              TO INSURE A PREMATURE CUTOFF DOES NOT OCCUR FOR TRUNCATION
109
+              (SEE USE OF ITOL,NTOL,TOL IN THE CODE BELOW).
110
+            @param[in] rho integration argument argument
111
+            */
112
+            void Compute(const Real& rho, const int& ntol, const Real& tol);
113
+
114
+            /** Attaches the integration kernel */
115
+            void AttachKernel(IntegrationKernel<Scalar> *Kernel);
116
+
117
+            /** Detaches the integration kernel */
118
+            void DetachKernel( );
119
+
120
+            // ====================  ACCESS        =======================
121
+
122
+            /** Returns the Vector of Abscissa arguments
123
+             */
124
+            VectorXr  GetAbscissaArguments();
125
+
126
+            Eigen::Matrix<Scalar, Eigen::Dynamic, Eigen::Dynamic > GetAnswer();
127
+
128
+            /** Returns the number of evaluations of kernel */
129
+            int GetNumFun();
130
+            // ====================  INQUIRY       =======================
131
+
132
+        protected:
133
+
134
+            // ====================  LIFECYCLE     =======================
135
+
136
+            /** Default protected constructor. */
137
+            DigitalFilterIntegrator (const std::string& name);
138
+
139
+            /** Default protected constructor. */
140
+            ~DigitalFilterIntegrator ();
141
+
142
+            // ====================  DATA MEMBERS  =========================
143
+
144
+            /** A rewrite of Anderson's Pseudo-subroutine. */
145
+            void StoreRetreive(const int& idx, const int& lag, const Real& y,
146
+                        Scalar& Zsum, const int& jrel, Scalar& C);
147
+
148
+            // ====================  OPERATIONS    ==============================
149
+            /** Sets the filter weights as prescribed by Anderson. This is called
150
+                automatically when the SetBesselOrder(int ) is called. This is
151
+                a protected function and cannot be called directly.
152
+             */
153
+            virtual void SetFilterWeights()=0;
154
+
155
+            /** Computes the absolute maximum of the scalar */
156
+            Scalar AbsMax(const Scalar& C, const Scalar& Cmax);
157
+
158
+            // ====================  DATA MEMBERS  ==============================
159
+
160
+            /** The hankel transform wavenumber embedded in the integral */
161
+            Real Lambda;
162
+
163
+            /** Number of times kernel was evaluated */
164
+            int NumFun;
165
+
166
+            /** Number of lagged convolutions
167
+                must be greater or equal to 1
168
+                It is set automatically in the @see Compute function so
169
+                that  \f$ \rho \exp\left( -.1*(\mathtt{NumConv} -1) \right) \f$
170
+                does not underflow the exponent range
171
+             */
172
+            int NumConv;
173
+
174
+            /** Number of related kernels */
175
+            int NumRel;
176
+
177
+            /** Used as base for filter abscissa generation */
178
+            Real ABSCISSA;
179
+
180
+            /** Also used in abscissa generation \f$ ABSE = \exp{.1} \f$ */
181
+            const Real ABSE;
182
+
183
+            /** Also used in abscissa generation \f$ ABSER = 1 / \exp{.1} \f$ */
184
+            const Real ABSER;
185
+
186
+            /** Counter for calculated */
187
+            int icount;
188
+
189
+            /** Index of special case low side convolution filter weights */
190
+            int ilow;
191
+
192
+            /** Index of special case right side convolution filter weights */
193
+            int ihi;
194
+
195
+            /** Kernel Calculator */
196
+            IntegrationKernel<Scalar> *IntKernel;
197
+
198
+            /** Holds answer, dimensions are NumConv, and NumberRelated. */
199
+            Eigen::Matrix<Scalar, Eigen::Dynamic, Eigen::Dynamic> Ans;
200
+
201
+            /** Filter weight coefficients.
202
+             */
203
+            VectorXr  FilterWeights;
204
+
205
+            /** Stored abscissa arguments
206
+             */
207
+            VectorXr  Arg;
208
+
209
+            /** Work from Anderson
210
+             */
211
+            Eigen::Matrix<Scalar, Eigen::Dynamic, Eigen::Dynamic> Work;
212
+
213
+            /// Key used internally
214
+            Eigen::Matrix<int, Eigen::Dynamic, 1> Key;
215
+
216
+        private:
217
+
218
+    }; // -----  end of class  DigitalFilterIntegrator  -----
219
+
220
+
221
+    /////////////////////////////////////////
222
+    /////////////////////////////////////////
223
+    //      Templated implimentation       //
224
+    /////////////////////////////////////////
225
+    /////////////////////////////////////////
226
+
227
+    template <typename Scalar>
228
+    std::ostream &operator<<(std::ostream &stream,
229
+			const DigitalFilterIntegrator<Scalar> &ob) {
230
+		stream << *(Integrator*)(&ob);
231
+		return stream;
232
+	}
233
+
234
+    // ====================  LIFECYCLE     =======================
235
+
236
+    template <typename Scalar>
237
+    DigitalFilterIntegrator<Scalar>::
238
+            DigitalFilterIntegrator(const std::string& name) :
239
+        Integrator(name), Lambda(0), NumFun(0), NumConv(0), NumRel(0),
240
+        ABSCISSA(0),
241
+        ABSE(1.10517091807564762),   //   exp(.1)
242
+        ABSER(0.904837418035959573), // 1/exp(.1)
243
+        ilow(0), ihi(0), IntKernel(NULL) {
244
+    }
245
+
246
+    template <typename Scalar>
247
+    DigitalFilterIntegrator<Scalar>::~DigitalFilterIntegrator( ) {
248
+    }
249
+
250
+    template <typename Scalar>
251
+    Eigen::Matrix<Scalar, Eigen::Dynamic, Eigen::Dynamic >
252
+        DigitalFilterIntegrator<Scalar>::GetAnswer() {
253
+        return Ans;
254
+    }
255
+
256
+    // ====================  OPERATIONS    =======================
257
+
258
+    template <typename Scalar>
259
+    void DigitalFilterIntegrator<Scalar>::SetNumConv(const int& i) {
260
+        this->NumConv = i;
261
+    }
262
+
263
+    template <typename Scalar>
264
+    void DigitalFilterIntegrator<Scalar>::
265
+            AttachKernel(IntegrationKernel<Scalar> *ck) {
266
+		if (this->IntKernel == ck) return;
267
+        if (this->IntKernel != NULL) {
268
+			this->IntKernel->DetachFrom(this);
269
+		}
270
+		ck->AttachTo(this);
271
+		this->IntKernel = ck;
272
+	}
273
+
274
+
275
+    template <typename Scalar>
276
+	void DigitalFilterIntegrator<Scalar>::DetachKernel( ) {
277
+		if (this->IntKernel != NULL) {
278
+			this->IntKernel->DetachFrom(this);
279
+		}
280
+		this->IntKernel = NULL;
281
+	}
282
+
283
+//     template < >
284
+//     inline Complex DigitalFilterIntegrator<Complex>::AbsMax(const Complex& C,
285
+//         const Complex& Cmax) {
286
+// 		return Complex(std::max(std::abs(real(C)), std::real(Cmax)),
287
+// 					   std::max(std::abs(imag(C)), std::imag(Cmax)) );
288
+//     }
289
+//     template < >
290
+//     Real DigitalFilterIntegrator<Real>::AbsMax(const Real& C,
291
+//         const Real& Cmax) {
292
+//         return std::max(C, Cmax);
293
+//     }
294
+
295
+    template <typename Scalar>
296
+    VectorXr  DigitalFilterIntegrator<Scalar>::GetAbscissaArguments() {
297
+        return this->Arg;
298
+    }
299
+
300
+//     ///////////////////////////////////////////
301
+// 	// Computes the transform
302
+//
303
+//     template < >
304
+//     void DigitalFilterIntegrator<Real>::Compute(const Real& rho,
305
+//         const int& ntol, const Real& tol) {
306
+//
307
+// 		Real y1 = this->ABSCISSA/rho;
308
+// 		this->Key.setZero();
309
+//
310
+// 		// Check to make sure everything is set
311
+// 		if (rho<=0) {
312
+// 			throw std::runtime_error("In DigitalFilterIntegrator Argument rho < 0.");
313
+// 		}
314
+//
315
+// 		if (this->NumConv<1) {
316
+// 			throw std::runtime_error("In DigitalFilterIntegrator NumConv is less than 1.");
317
+// 		}
318
+//
319
+// 		if (this->IntKernel == NULL) {
320
+// 			throw std::runtime_error("In DigitalFilterIntegrator Unset Kernel Calculator");
321
+// 		}
322
+//
323
+// 		Arg = VectorXr::Zero(this->NumConv);
324
+// 		Real y = std::pow(rho*ABSER, this->NumConv-1);
325
+//
326
+// 		if (y <= 0) {
327
+// 			std::cerr << "Exponent Underflow Error";
328
+// 			throw std::underflow_error("Exponent underflow");
329
+// 		}
330
+//
331
+// 		this->Work.resize(Eigen::NoChange, this->IntKernel->GetNumRel());
332
+//
333
+//         // Main Loop
334
+// 		int itol = 0;
335
+// 		int none = 0;
336
+// 		this->NumFun = 0;
337
+// 		int idx = 0;
338
+// 		int istore = 0;
339
+// 		Real Sum(0.);
340
+// 		Real Cmax(0.);
341
+// 		Real C(0.);
342
+// 		Ans.resize(this->NumConv, this->IntKernel->GetNumRel());
343
+// 		Ans.setZero();
344
+//  		// 1010 Loop
345
+//  		for (int ilag=0; ilag < this->NumConv; ++ilag) {
346
+//   			istore = this->NumConv - 1 - ilag;
347
+//   			if (ilag > 0) y1 *= ABSE;
348
+//   			Arg(istore) = ABSCISSA/y1;
349
+//
350
+//  			// 1000 Loop
351
+//  			for (int irel=0; irel < this->IntKernel->GetNumRel(); ++irel) {
352
+// 				//this->SetBesselOrder(this->Ckernel->GetBesselOrder(irel));
353
+//   				none = 0;
354
+//   				itol = ntol;
355
+//   				Sum = Real(0);
356
+//   				Cmax = Real(0);
357
+//   				y = y1;
358
+// 				// Begin right side convolution at weight 298
359
+// 				// counting from 0
360
+//   				idx = ilow;
361
+//   				y *= ABSE;
362
+// 				// Code Block 20 in Anderson
363
+// 				do {
364
+//  					this->StoreRetreive(idx, ilag, y, Sum, irel, C);
365
+//                     Cmax = AbsMax(C, Cmax);
366
+// 					++idx;
367
+// 					y *= ABSE;
368
+// 				} while (idx <= ihi);
369
+// 				//if (real(Cmax) == 0 && imag(Cmax) == 0) none = 1;
370
+// 				if (Cmax == Real(0)) none = 1;
371
+// 				Cmax *= tol;
372
+// 				// Code Block 30 in Anderson
373
+// 				do {
374
+//  					this->StoreRetreive(idx, ilag, y, Sum, irel, C);
375
+// 					if (std::abs(C) <= Cmax) {
376
+// 						--itol;
377
+// 						if (itol < 0 || idx > FilterWeights.size()-1) break;
378
+// 					} else {
379
+// 						itol = ntol;
380
+// 					}
381
+// 					++idx;
382
+// 					y *= ABSE;
383
+// 				} while (idx < FilterWeights.size());
384
+// 				itol = ntol;
385
+// 				y = y1;
386
+// 				// Code Block 60 in Anderson
387
+// 				idx = ilow-1;
388
+// 				do {
389
+//  					this->StoreRetreive(idx, ilag, y, Sum, irel, C);
390
+// 					if (std::abs(C) <= Cmax &&  none == 0) {
391
+// 						--itol;
392
+// 						if (itol < 0 || idx < 0) break;
393
+// 					} else {
394
+// 						itol = ntol;
395
+// 					}
396
+// 					--idx;
397
+// 					y *= ABSER;
398
+// 				} while (idx>=0);
399
+//  				Ans(istore, irel) = Sum/Arg(istore);
400
+//   			}  // End of 1000 loop
401
+//   		}      // End of 1010 loop
402
+// 	}
403
+//
404
+//
405
+//     template < >
406
+// 	void DigitalFilterIntegrator<Complex>::Compute(const Real &rho,
407
+//             const int& ntol, const Real &tol) {
408
+//
409
+// 		Real y1 = this->ABSCISSA/rho;
410
+//
411
+// 		this->Key.setZero();
412
+//
413
+// 		// Check to make sure everything is set
414
+// 		if (rho<=0) {
415
+// 			throw std::runtime_error("In DigitalFilterIntegrator Argument rho < 0.");
416
+// 		}
417
+//
418
+// 		if (this->NumConv<1) {
419
+// 			throw std::runtime_error("In DigitalFilterIntegrator NumConv is less than 1.");
420
+// 		}
421
+//
422
+// 		if (this->IntKernel == NULL) {
423
+// 			throw std::runtime_error("In DigitalFilterIntegrator Unset Kernel Calculator");
424
+// 		}
425
+//
426
+// 		Arg = VectorXr::Zero(this->NumConv);
427
+// 		Real y = std::pow(rho*ABSER, this->NumConv-1);
428
+//
429
+// 		if (y <= 0) {
430
+// 			std::cerr << "Exponent Underflow Error";
431
+// 			throw std::underflow_error("Exponent underflow");
432
+// 		}
433
+//
434
+// 		this->Work.resize(Eigen::NoChange, this->IntKernel->GetNumRel());
435
+//
436
+//         // Main Loop
437
+// 		int itol = 0;
438
+// 		int none = 0;
439
+// 		this->NumFun = 0;
440
+// 		int idx = 0;
441
+// 		int istore = 0;
442
+// 		Complex Zsum(0.);
443
+// 		Complex Cmax(0.);
444
+// 		Complex C(0.);
445
+// 		Ans.resize(this->NumConv, this->IntKernel->GetNumRel());
446
+// 		Ans.setZero();
447
+//  		// 1010 Loop
448
+//  		for (int ilag=0; ilag < this->NumConv; ++ilag) {
449
+//   			istore = this->NumConv - 1 - ilag;
450
+//   			if (ilag > 0) y1 *= ABSE;
451
+//   			Arg(istore) = ABSCISSA/y1;
452
+//  			// 1000 Loop
453
+//  			for (int irel=0; irel < this->IntKernel->GetNumRel(); ++irel) {
454
+// 				//this->SetBesselOrder(this->Ckernel->GetBesselOrder(irel));
455
+//   				none = 0;
456
+//   				itol = ntol;
457
+//   				Zsum = Complex(0);
458
+//   				Cmax = Complex(0);
459
+//   				y = y1;
460
+// 				// Begin right side convolution at weight 298
461
+// 				// counting from 0
462
+//   				idx = ilow;
463
+//   				y *= ABSE;
464
+// 				// Code Block 20 in Anderson
465
+// 				do {
466
+//  					this->StoreRetreive(idx, ilag, y, Zsum, irel, C);
467
+//                     Cmax = AbsMax(C, Cmax);
468
+// 					++idx;
469
+// 					y *= ABSE;
470
+// 				} while (idx <= ihi);
471
+// 				//if (real(Cmax) == 0 && imag(Cmax) == 0) none = 1;
472
+// 				if (Cmax == Complex(0)) none = 1;
473
+// 				Cmax *= tol;
474
+// 				// Code Block 30 in Anderson
475
+// 				do {
476
+//  					this->StoreRetreive(idx, ilag, y, Zsum, irel, C);
477
+// 					if ( std::abs(real(C)) <= real(Cmax) &&
478
+// 						 std::abs(imag(C)) <= imag(Cmax) ) {
479
+// 						--itol;
480
+// 						if (itol < 0 || idx > FilterWeights.size()-1) break;
481
+// 					} else {
482
+// 						itol = ntol;
483
+// 					}
484
+// 					++idx;
485
+// 					y *= ABSE;
486
+// 				} while (idx < FilterWeights.size());
487
+// 				itol = ntol;
488
+// 				y = y1;
489
+// 				// Code Block 60 in Anderson
490
+// 				idx = ilow-1;
491
+// 				do {
492
+//  					this->StoreRetreive(idx, ilag, y, Zsum, irel, C);
493
+// 					if ( std::abs(real(C)) <= real(Cmax) &&
494
+// 						 std::abs(imag(C)) <= imag(Cmax) &&
495
+// 						 none == 0 ) {
496
+// 						--itol;
497
+// 						if (itol < 0 || idx < 0) break;
498
+// 					} else {
499
+// 						itol = ntol;
500
+// 					}
501
+// 					--idx;
502
+// 					y *= ABSER;
503
+// 				} while (idx>=0);
504
+//  				Ans(istore, irel) = Zsum/Arg(istore);
505
+//   			}  // End of 1000 loop
506
+//   		}      // End of 1010 loop
507
+// 	}
508
+
509
+    template <typename Scalar>
510
+    int DigitalFilterIntegrator<Scalar>::GetNumFun() {
511
+        return NumFun;
512
+    }
513
+
514
+    // generic rewrite of store-retreive 'pseudo-subroutine'
515
+    template <typename Scalar>
516
+    void DigitalFilterIntegrator<Scalar>::StoreRetreive(const int &idx,
517
+            const int& lag, const Real& y, Scalar& Sum,
518
+            const int& jrel, Scalar& C) {
519
+
520
+		int look = idx+lag;
521
+ 		int	iq = look/FilterWeights.size();
522
+ 		int	ir = look%FilterWeights.size();
523
+		int iroll = iq*(FilterWeights.size()-1);
524
+
525
+		if(this->Key(ir) <= iroll) {
526
+			this->Key(ir) = iroll + ir;
527
+			this->Lambda = y;
528
+ 			++this->NumFun;
529
+ 			for (int ir2=0; ir2<IntKernel->GetNumRel(); ++ir2) {
530
+ 			    this->Work(ir, ir2) = this->IntKernel->Argument(this->Lambda, ir2);
531
+ 			}
532
+		}
533
+
534
+		C = this->Work(ir, jrel) * this->FilterWeights(idx);
535
+		Sum += C;
536
+		return;
537
+
538
+	}
539
+
540
+}		// -----  end of Lemma  name  -----
541
+
542
+#endif   // ----- #ifndef DIGITALFILTERINTEGRATOR_INC  -----

+ 81
- 0
LemmaCore/include/digitalfiltersintrans.h View File

@@ -0,0 +1,81 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     02/18/2011
11
+  @version  $Id: digitalfiltersintrans.h 87 2013-09-05 22:44:05Z tirons $
12
+ **/
13
+
14
+#ifndef __DIGITALFILTERSINTRANS_H
15
+#define __DIGITALFILTERSINTRANS_H
16
+
17
+#include "digitalfilterintegrator.h"
18
+
19
+namespace Lemma {
20
+
21
+	// ===================================================================
22
+	//        Class:  DigitalFilterSinTrans
23
+	/** \brief Sine Transform via digital filters
24
+	    \details Based on Andersons' Hankel transform, this calculates
25
+	 			the sine transform of a discrete function
26
+				using a digital filter approach.  Filter weights are
27
+				hard-coded.
28
+				Calculates transform of the form:
29
+				\f[ \int_0^\infty f(x) \sin (x\omega)~dx
30
+				\f]
31
+    */
32
+
33
+	// ===================================================================
34
+	class DigitalFilterSinTrans : public DigitalFilterIntegrator<Real> {
35
+
36
+		friend std::ostream &operator<<(std::ostream &stream, const
37
+			DigitalFilterSinTrans &ob);
38
+
39
+		public:
40
+
41
+			// ====================  LIFECYCLE     =======================
42
+
43
+			static DigitalFilterSinTrans* New();
44
+
45
+			void Delete();
46
+
47
+			// ====================  OPERATORS     =======================
48
+
49
+			// ====================  OPERATIONS    =======================
50
+
51
+			// ====================  ACCESS        =======================
52
+
53
+			// ====================  INQUIRY       =======================
54
+
55
+		protected:
56
+
57
+			// ====================  LIFECYCLE     =======================
58
+
59
+			/// Default protected constructor.
60
+			DigitalFilterSinTrans (const std::string& name);
61
+
62
+			/// Default protected constructor.
63
+			~DigitalFilterSinTrans ();
64
+
65
+			void Release();
66
+
67
+			/// Set all the filter weights
68
+			void SetFilterWeights();
69
+
70
+			// ====================  DATA MEMBERS  =========================
71
+
72
+			//Eigen::Matrix<Real, 787, 1> FilterWeights;
73
+
74
+		private:
75
+
76
+    }; // -----  end of class  DigitalFilterSinTrans  -----
77
+
78
+} //end of namespace Lemma
79
+
80
+#endif // __DIGITALFILTERSINTRANS_H
81
+

+ 335
- 0
LemmaCore/include/dipolesource.h View File

@@ -0,0 +1,335 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     12/02/2009
11
+  @version  $Id: dipolesource.h 203 2015-01-09 21:19:04Z tirons $
12
+ **/
13
+
14
+#ifndef __DIPOLESOURCE_H
15
+#define __DIPOLESOURCE_H
16
+
17
+#include "LemmaObject.h"
18
+#include "layeredearthem.h"
19
+//#include "kernelem1dmanager.h"
20
+
21
+
22
+#ifdef LEMMAUSEVTK
23
+#include "vtkActor.h"
24
+#include "vtkLineSource.h"
25
+#include "vtkSphereSource.h"
26
+#include "vtkPolyDataMapper.h"
27
+#include "vtkTubeFilter.h"
28
+#include "vtkRegularPolygonSource.h"
29
+#include "vtkProperty.h"
30
+#endif
31
+
32
+namespace Lemma {
33
+
34
+    class KernelEM1DManager;
35
+    class ReceiverPoints;
36
+    class HankelTransform;
37
+
38
+    // ==========================================================================
39
+    //        Class:  DipoleSource
40
+    /// \brief    Dipole sources form the backbone of Lemma.
41
+    /// \details  More complex sources are constructed from a superposition of
42
+    ///           dipoles.
43
+    // ==========================================================================
44
+    class DipoleSource : public LemmaObject {
45
+
46
+        public:
47
+
48
+            // ====================    FRIENDS     ======================
49
+
50
+            friend std::ostream &operator<<(std::ostream &stream,
51
+                        const DipoleSource &ob);
52
+
53
+
54
+            // ====================  LIFECYCLE     ======================
55
+
56
+            /**
57
+             *  Returns pointer to new DipoleSource. Location is
58
+             *  initialized to (0,0,0) type and polarization are
59
+             *  initialized  to nonworking values that will throw
60
+             *  exceptions if used.
61
+             */
62
+            static DipoleSource* New();
63
+
64
+
65
+            /** Returns a deep copy of the dipole. Used to make thread safe methods. Does not
66
+                copy attachments.
67
+             */
68
+            DipoleSource* Clone();
69
+
70
+            /**
71
+             * @copybrief LemmaObject::Delete()
72
+             * @copydetails LemmaObject::Delete()
73
+             */
74
+            void Delete();
75
+
76
+            // ====================  OPERATORS     ======================
77
+
78
+            // ====================  OPERATIONS    ======================
79
+
80
+            /** Determines if kernels have been loaded already, and if so if they can be reused
81
+             */
82
+            void SetKernels(const int& ifreq,  const FIELDCALCULATIONS&  Fields, ReceiverPoints* Receivers, const int& irec,
83
+                    LayeredEarthEM* Earth );
84
+
85
+            /** resets the kernels if they cannot be reused */
86
+            virtual void ReSetKernels(const int& ifreq,  const FIELDCALCULATIONS&  Fields, ReceiverPoints* Receivers, const int& irec,
87
+                    LayeredEarthEM* Earth );
88
+
89
+            /** Updates the receiver fields */
90
+            virtual void UpdateFields(const int& ifreq, HankelTransform* Hankel, const Real& wavef);
91
+
92
+            // ====================  ACCESS        ======================
93
+
94
+            /** Sets the position.
95
+             * @param [in] posin
96
+             */
97
+            void SetLocation(const Vector3r &posin);
98
+
99
+            /** Sets the location using three Real coordinate arguments.
100
+             *  @param[in] xp is the x coordinate of the dipole
101
+             *  @param[in] yp is the y coordinate of the dipole
102
+             *  @param[in] zp is the z coordinate of the dipole
103
+             */
104
+            void SetLocation(const Real &xp, const Real &yp, const Real &zp);
105
+
106
+            /** Sets the dipole direction (polarisation). This method
107
+             * replaced SetPolarisation(DipoleSourcePolarisation) and allows for general dipole
108
+             * directionality.
109
+             * @param[in] dir is the direction of the dipole. This will be normalised.
110
+             */
111
+            void SetPolarisation(const Vector3r &dir);
112
+
113
+            /** Sets the polarisation of the dipole. Conveneince method that calls
114
+             *  SetPolarisation(const Vector3r &dir), constructing the normalized Vector | <x, y, z> |
115
+             */
116
+            void SetPolarisation(const Real& x, const Real& y, const Real& z );
117
+
118
+            /// Sets the dipole polarisation
119
+            /// @param[in] pol is the enumerated polarisation
120
+            void SetPolarisation(const DipoleSourcePolarisation &pol);
121
+
122
+            /// Sets the dipole source type
123
+            /// @param[in] stype is one of the enerated values taking either
124
+            /// ELECTRICDIPOLE or MAGNETICDIPOLE
125
+            void SetType(const DipoleSourceType &stype);
126
+
127
+            /// Sets the dipole moment
128
+            void SetMoment(const Real &moment);
129
+
130
+            /// Sets the dipole phse
131
+            void SetPhase(const Real &phase);
132
+
133
+            /// Sets the polarity
134
+            void SetPolarity(const DipoleSourcePolarity& pol);
135
+
136
+            /// Sets number of frequencies
137
+            void SetNumberOfFrequencies(const int &nfreq);
138
+
139
+            /// Sets a specific frequency.
140
+            /// @param[in] ifreq is the frequency bin number
141
+            /// @param[in] freq is the frequency to set, in Hz
142
+            void SetFrequency(const int &ifreq, const Real &freq);
143
+
144
+            /// Sets the frequencies of the dipole.
145
+            /// @param[in] freqs is a vector of the frequencies. Also sets
146
+            /// number of frequencies
147
+            void SetFrequencies(const VectorXr& freqs);
148
+
149
+
150
+            // ====================  INQUIRY       ======================
151
+
152
+            /**  Accessor to polarisation vector.
153
+                 @return returns the unit polarisation vector.
154
+             */
155
+            Vector3r GetPolarisation();
156
+
157
+            /// Returns Vector3r position of the dipole
158
+            Vector3r GetLocation();
159
+
160
+            /// Returns a specific coordinate of the dipole
161
+            /// @param coordinate 0=x, 1=y, 2=z
162
+            Real  GetLocation(const int &coordinate);
163
+
164
+            /// Returns enumerated of DipoleSourceType
165
+            DipoleSourceType GetDipoleSourceType();
166
+
167
+            /// Returns the dipole type
168
+            DipoleSourceType GetType();
169
+
170
+            /// Returns pointer to KernelEM1DManager
171
+            KernelEM1DManager*  GetKernelManager();
172
+
173
+            // Returns enumerated DipoleSourcePolarization
174
+            //DipoleSourcePolarisation GetDipoleSourcePolarisation();
175
+
176
+            /// Returns the dipole moment
177
+            Real GetMoment();
178
+
179
+            /// Returns the angular frequency of the dipole
180
+            Real GetAngularFrequency(const int &ifreq);
181
+
182
+            /// Returns the frequency of the dipole (Hz)
183
+            Real GetFrequency(const int &ifreq);
184
+
185
+            /// Returns the frequency of the dipole (Hz)
186
+            VectorXr GetFrequencies( );
187
+
188
+            /// Returns the phase offset of the dipole
189
+            Real GetPhase();
190
+
191
+            /// Returns the number of frequencies
192
+            int GetNumberOfFrequencies();
193
+
194
+            #ifdef LEMMAUSEVTK
195
+            /// Returns an actor that can be placed into a vtk scene easily
196
+            /// Note that this function throws a pointer, it is the receivers
197
+            /// job to manage this memory!
198
+            vtkActor* GetVtkActor();
199
+            #endif
200
+
201
+        protected:
202
+
203
+            // ====================  LIFECYCLE     ======================
204
+
205
+            /// Default protected constructor.
206
+            DipoleSource (const std::string &name);
207
+
208
+            /// Default protected constructor.
209
+            ~DipoleSource ();
210
+
211
+            /**
212
+             * @copybrief LemmaObject::Release()
213
+             * @copydetails LemmaObject::Release()
214
+             */
215
+            void Release();
216
+
217
+            // ====================  DATA MEMBERS  ======================
218
+
219
+            /// Defines the type of source (magnetic or electric)
220
+            DipoleSourceType             Type;
221
+
222
+            // Polarization of the dipole, (x, y or z)
223
+            //DipoleSourcePolarisation     Polarisation;
224
+
225
+            // Dipole polarity
226
+            //DipoleSourcePolarity         Polarity;
227
+
228
+            /// Which receiver index should Kernels be configured for
229
+            int                          irec;
230
+            int                          lays;
231
+            int                          layr;
232
+
233
+            /// Phase offset of the dipole, referenced from 0
234
+            Real                         Phase;
235
+
236
+            /// Dipole Moment
237
+            Real                         Moment;
238
+
239
+            Real                         xxp;
240
+            Real                         yyp;
241
+            Real                         rho;
242
+            Real                         sp;
243
+            Real                         cp;
244
+            Real                         scp;
245
+            Real                         sps;
246
+            Real                         cps;
247
+            Real                         c2p;
248
+            Real                         kernelFreq;
249
+
250
+            FIELDCALCULATIONS            FieldsToCalculate;
251
+
252
+            VectorXcr                    f;
253
+            VectorXi                     ik;
254
+
255
+            /// Central location of the dipole
256
+            Vector3r                     Location;
257
+
258
+            /// Unit vector defining directionality of the dipole
259
+            Vector3r                     Phat;
260
+
261
+            /// Freqencies of the source, in Hz
262
+            VectorXr                     Freqs;
263
+
264
+            /// Storage of the EM1D kernels used by this dipole
265
+            KernelEM1DManager*          KernelManager;
266
+
267
+            /// Receiver points, keep track if these have changed
268
+            ReceiverPoints*             Receivers;
269
+
270
+            /// Layered Earth used by Kernels
271
+            LayeredEarthEM*             Earth;
272
+
273
+    }; // -----  end of class  DipoleSource  -----
274
+
275
+    /** If no dipole source has been specified, throw this error.
276
+    */
277
+    class NullDipoleSource : public std::runtime_error {
278
+        public:
279
+        /** Thrown when a DipoleSource pointer is NULL
280
+         */
281
+        NullDipoleSource ( );
282
+    };
283
+
284
+    /** Error class for assignment of a dipole source that did not connect properly.
285
+     */
286
+    class NonValidDipoleTypeAssignment  : public std::runtime_error {
287
+        public:
288
+            NonValidDipoleTypeAssignment(  );
289
+    };
290
+
291
+    /** Error class for a non-valid dipole type. Generally thrown if this was not
292
+     * set properly.
293
+     */
294
+    class NonValidDipoleType  : public std::runtime_error {
295
+        public:
296
+            /** Throws error. This is a deprecated function. Call the method with
297
+             *  the pointer address instead.
298
+             */
299
+            NonValidDipoleType( );
300
+            /** Throws error with information on the class throwing the error.
301
+            */
302
+            NonValidDipoleType( LemmaObject *ptr );
303
+    };
304
+
305
+    /** Error class for non valid dipole polarisation
306
+     */
307
+    class NonValidDipolePolarisation  : public std::runtime_error {
308
+        public:
309
+            NonValidDipolePolarisation( );
310
+    };
311
+
312
+    /** Error class for non valid dipole polarity
313
+     */
314
+    class NonValidDipolePolarity  : public std::runtime_error {
315
+        public:
316
+            NonValidDipolePolarity( );
317
+    };
318
+
319
+    /** Error class for non valid dipole polarisation
320
+     */
321
+    class NonValidDipolePolarisationAssignment  : public std::runtime_error {
322
+        public:
323
+            NonValidDipolePolarisationAssignment( );
324
+    };
325
+
326
+    /** Error class for non valid location coordinate.
327
+     */
328
+    class NonValidLocationCoordinate  : public std::runtime_error {
329
+        public:
330
+            NonValidLocationCoordinate( );
331
+    };
332
+
333
+}
334
+
335
+#endif // __DIPOLESOURCE_H

+ 142
- 0
LemmaCore/include/earthmodel.h View File

@@ -0,0 +1,142 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     03/23/2010
11
+  @version  $Id: earthmodel.h 198 2014-12-27 06:14:05Z tirons $
12
+ **/
13
+
14
+#ifndef  EARTHMODEL_INC
15
+#define  EARTHMODEL_INC
16
+
17
+#include "LemmaObject.h"
18
+
19
+namespace Lemma {
20
+
21
+    // ===================================================================
22
+    //        Class:  EarthModel
23
+    /// \brief abstract class for Earth models
24
+    /// \details
25
+    // ===================================================================
26
+    class EarthModel : public LemmaObject {
27
+
28
+        // ====================    FRIENDS     ===========================
29
+        friend std::ostream &operator<<(std::ostream &stream,
30
+                        const EarthModel &ob);
31
+
32
+        public:
33
+
34
+            // ====================  LIFECYCLE     =======================
35
+            #ifdef HAVE_YAMLCPP
36
+            /** YAML Serializing method
37
+             */
38
+            YAML::Node Serialize() const;
39
+            //static LayeredEarth* DeSerialize(const YAML::Node& node);
40
+            #endif
41
+
42
+            // ====================  OPERATORS     =======================
43
+
44
+            // ====================  OPERATIONS    =======================
45
+
46
+            // ====================  ACCESS        =======================
47
+
48
+            /** Sets the earth's magnetic field, in Tesla
49
+                @param[in] bfield contains the x,y, and z components of
50
+                the field. EarthModel::Inc, EarthModel::Dec, and
51
+                EarthModel::BMag are computed:
52
+                \f{eqnarray*}{ \mathrm{Inc} = &
53
+                \cos^{-1}( \mathbf{B} \cdot \hat{\mathbf{z}} / B )
54
+                \\ \mathrm{Dec} =& \cos^{-1}
55
+                         (\mathbf{B} \cdot \hat{\mathbf{x}} / B )
56
+                   \\           \mathrm{Mag} =& \Vert \mathbf{B} \Vert  \f}
57
+               @param[in] unit specifies the units of bfield.
58
+              */
59
+            void SetMagneticFieldComponents(const Vector3r &bfield,
60
+                            const MAGUNITS &unit);
61
+
62
+            /// Sets the magnetic field using inclination, declination,
63
+            /// and magnitude, units of Tesla
64
+            /// @param[in] inc is the field's inclination
65
+            /// @param[in] dec is the field's declination
66
+            /// @param[in] Mag is the field's magnitude
67
+            /// @param[in] unit specifies the the units used.
68
+            /// The components are set according to
69
+            /// \f{eqnarray*} { B_x =& B \cos(inc (\pi/180)) \cos(dec (\pi/180))
70
+            ///            \\   B_y =& B \cos(inc (\pi/180)) \sin(dec (\pi/180))
71
+            ///            \\   B_z =& B \sin(inc (\pi/180))
72
+            /// \f}
73
+            void SetMagneticFieldIncDecMag(const Real& inc, const Real&dec,
74
+                            const Real& Mag, const MAGUNITS &unit);
75
+
76
+            // ====================  INQUIRY       =======================
77
+
78
+            /// Gets the magnetic field of the earth, in T
79
+            Vector3r GetMagneticField( );
80
+
81
+            /// Gets the magnetic field of the earth, in T
82
+            Vector3r GetMagneticFieldInGauss(  );
83
+
84
+            /// Gets the magnetic field unit vector of the earth
85
+            Vector3r GetMagneticFieldUnitVector( );
86
+
87
+            /// Returns the magnitude of the magnetic field \f$ \Vert
88
+            /// \mathbf{B}_0 \Vert \f$
89
+            Real GetMagneticFieldMagnitude();
90
+
91
+            /// Returns the magnitude of the magnetic field \f$ \Vert
92
+            /// \mathbf{B}_0 \Vert \f$ in Gauss units
93
+            Real GetMagneticFieldMagnitudeInGauss( );
94
+
95
+        protected:
96
+
97
+            // ====================  LIFECYCLE     =======================
98
+
99
+            /// Default protected constructor.
100
+            EarthModel (const std::string& name);
101
+
102
+            #ifdef HAVE_YAMLCPP
103
+            /** Deserialize constructor */
104
+            EarthModel (const YAML::Node& node);
105
+            #endif
106
+
107
+            /// Default protected constructor.
108
+            ~EarthModel ();
109
+
110
+            // ====================  DATA MEMBERS  =========================
111
+
112
+            /// Magnetic field, in units of nT
113
+            Vector3r          BField;
114
+
115
+            /// Magnetic field unit vector \f$  \hat{\mathbf{B}_0} \f$
116
+            Vector3r          BFieldUnit;
117
+
118
+            /// Inclination of the magnetic field
119
+            Real              BInc;
120
+
121
+            /// Declination of the magnetic field
122
+            Real              BDec;
123
+
124
+            /// Declination of the magnetic field
125
+            Real              BMag;
126
+
127
+    }; // -----  end of class  EarthModel  -----
128
+
129
+    //////////////////////////////////////////////////////////////
130
+    // Error Classes
131
+
132
+    /** If the Earth class is NULL valued, throw this
133
+     */
134
+    class NullEarth : public std::runtime_error {
135
+            /** Thrown when an Earth pointer is NULL
136
+             */
137
+            public: NullEarth ();
138
+    };
139
+
140
+}       // -----  end of Lemma  name  -----
141
+
142
+#endif   // ----- #ifndef EARTHMODEL_INC  -----

+ 232
- 0
LemmaCore/include/emearth1d.h View File

@@ -0,0 +1,232 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     12/02/2009
11
+  @version  $Id: emearth1d.h 266 2015-04-01 03:24:00Z tirons $
12
+ **/
13
+
14
+#ifndef __EMEARTH1D_H
15
+#define __EMEARTH1D_H
16
+
17
+#include "dipolesource.h"
18
+#include "layeredearthem.h"
19
+#include "receiverpoints.h"
20
+#include "WireAntenna.h"
21
+#include "PolygonalWireAntenna.h"
22
+#include "kernelem1dspec.h"
23
+#include "kernelem1dmanager.h"
24
+#include "hankeltransformgaussianquadrature.h"
25
+#include "hankeltransformhankel2.h"
26
+#include "FHTKey.h"
27
+#include "FHTKey51.h"
28
+#include "FHTKey101.h"
29
+#include "QWEKey.h"
30
+#include "CubicSplineInterpolator.h"
31
+
32
+#ifdef HAVEBOOSTPROGRESS
33
+#include "boost/progress.hpp"
34
+#endif
35
+
36
+namespace Lemma {
37
+
38
+    // =======================================================================
39
+    //        Class:  EmEarth1D
40
+    /// \brief  Implimentation of 1D EM solution.
41
+    /// \details  We've done a lot of different things.
42
+    // =======================================================================
43
+    class EMEarth1D : public LemmaObject {
44
+
45
+		friend std::ostream &operator<<(std::ostream &stream,
46
+			const EMEarth1D &ob);
47
+
48
+        public:
49
+
50
+            //friend class KernelEm1D;
51
+
52
+            // ====================  LIFECYCLE     ===========================
53
+
54
+            /**
55
+             *  Returns pointer to new EMEarth1D. Location is
56
+             *  initialized to (0,0,0) type and polarization are
57
+             *  initialized  to nonworking values that will throw
58
+             *  exceptions if used.
59
+             */
60
+            static EMEarth1D* New();
61
+
62
+            /**
63
+             * @copybrief LemmaObject::Delete()
64
+             * @copydetails LemmaObject::Delete()
65
+             */
66
+            void Delete();
67
+
68
+            /** stream debugging info to std::out
69
+             */
70
+            void Query();
71
+
72
+            #ifdef HAVE_YAMLCPP
73
+            /** YAML Serializing method
74
+             */
75
+            YAML::Node Serialize() const;
76
+
77
+            //static EMEarth1D* DeSerialize(const YAML::Node& node);
78
+            #endif
79
+
80
+            // ====================  OPERATORS     ===========================
81
+
82
+            // ====================  OPERATIONS    ===========================
83
+
84
+            /// Calculates the field(s) due to an ungrounded dipole source
85
+            /// Calls FORTRAN library em1d (em1dnew.for)
86
+#ifdef COMPILE_FORTRAN
87
+            void MakeCalc();
88
+#endif
89
+
90
+            /** C++ wrapper for em1dnew.for, serial */
91
+            void MakeCalc3();
92
+
93
+            /** Calculates the field(s) due to a wire antennae */
94
+            void CalculateWireAntennaFields(bool progressbar=false);
95
+
96
+            // ====================  ACCESS        ===========================
97
+
98
+            /** Attaches an antennae */
99
+            void AttachWireAntenna(WireAntenna *antennae);
100
+
101
+            /** Attaches a dipole for calculation */
102
+            void AttachDipoleSource(DipoleSource *dipole);
103
+
104
+            /** Attaches a layered earth model for calculation */
105
+            void AttachLayeredEarthEM(LayeredEarthEM *Earth);
106
+
107
+            /** Attaches a set of receiver points for calculation */
108
+            void AttachReceiverPoints(ReceiverPoints *Receivers);
109
+
110
+            /** Sets the fields that are calcultated, E,H or BOTH */
111
+            void SetFieldsToCalculate(const FIELDCALCULATIONS &calc);
112
+
113
+            /** Sets the method to use to evaluate the Hankel integral,
114
+             */
115
+            void SetHankelTransformMethod(const HANKELTRANSFORMTYPE &type);
116
+
117
+            // ====================  INQUIRY       ===========================
118
+
119
+        protected:
120
+
121
+            // ====================  LIFECYCLE     ===========================
122
+
123
+            /** Default protected constructor. */
124
+            EMEarth1D (const std::string& name);
125
+
126
+            #ifdef HAVE_YAMLCPP
127
+            /** Default protected constructor. */
128
+			EMEarth1D (const YAML::Node& node);
129
+            #endif
130
+
131
+            /** Default protected constructor. */
132
+            ~EMEarth1D ();
133
+
134
+            /**
135
+             * @copybrief LemmaObject::Release()
136
+             * @copydetails LemmaObject::Release()
137
+             */
138
+            void Release();
139
+
140
+            // ====================  OPERATIONS    ===========================
141
+
142
+            /** Used internally, this is the innermost loop of the MakeCalc3,
143
+             *  and CalculateWireAntennaField routines.
144
+             */
145
+            void SolveSingleTxRxPair(const int &irec,
146
+                    HankelTransform *Hankel,
147
+                    const Real &wavef, const int &ifreq,
148
+                    DipoleSource *tDipole);
149
+
150
+            /** Used internally, this is the innermost loop of the MakeCalc3,
151
+             *  and CalculateWireAntennaField routines.
152
+             */
153
+            void SolveLaggedTxRxPair(const int &irec, Hankel2* Hankel,
154
+                    const Real &wavef, const int &ifreq,
155
+                    PolygonalWireAntenna* antenna);
156
+
157
+            /** Removes all connections */
158
+            void DetachAll();
159
+
160
+            // ====================  DATA MEMBERS  ===========================
161
+
162
+            /** Computes field due to dipole */
163
+            DipoleSource*        Dipole;
164
+
165
+            /** Earth model (Cole-cole) */
166
+            LayeredEarthEM*      Earth;
167
+
168
+            /** Receiver points */
169
+            ReceiverPoints*      Receivers;
170
+
171
+            /** Wire antennae tx */
172
+            WireAntenna*         Antenna;
173
+
174
+            /** What fields are wanted */
175
+            FIELDCALCULATIONS    FieldsToCalculate;
176
+
177
+            /** The type of Hankel transform to use, default to digital
178
+             *  filtering
179
+             */
180
+            HANKELTRANSFORMTYPE  HankelType;
181
+
182
+            /** Counter for number of caclulations made
183
+             */
184
+            int icalcinner;
185
+
186
+            /** Counter for number of caclulations made
187
+             */
188
+            int icalc;
189
+
190
+    }; // -----  end of class  EMEarth1D  -----
191
+
192
+    /////////////////////////////////////////
193
+    // Exception classes
194
+
195
+    /** If a Receivers Class is NULL valued, throw this.
196
+     */
197
+    class NullReceivers : public std::runtime_error {
198
+            /** Thrown when Receivers pointer is NULL
199
+             */
200
+            public: NullReceivers();
201
+    };
202
+
203
+    /** If an Antenna is NULL valued, throw this error.
204
+     */
205
+    class NullAntenna : public std::runtime_error {
206
+            /** Thrown when an antenna pointer is NULL
207
+             */
208
+            public: NullAntenna();
209
+    };
210
+
211
+    /** If an Instrument is NULL valued, throw this error.
212
+     */
213
+    class NullInstrument : public std::runtime_error {
214
+            /** thrown when an instrument pointer is NULL.
215
+             *  @param[in] ptr is a pointer to the class throwing the exception.
216
+             */
217
+            public: NullInstrument(LemmaObject* ptr);
218
+    };
219
+
220
+    /** If a dipole source is specified, but a method calling a wire antenna is
221
+     * called, throw this.
222
+     */
223
+    class DipoleSourceSpecifiedForWireAntennaCalc : public std::runtime_error {
224
+            /** Thrown when a dipole source is specified when a wire antenna is
225
+             * expected
226
+             */
227
+            public: DipoleSourceSpecifiedForWireAntennaCalc();
228
+    };
229
+
230
+} // Namespace Lemma
231
+
232
+#endif // __EMEARTH1D_H

+ 78
- 0
LemmaCore/include/emearth3d.h View File

@@ -0,0 +1,78 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     10/28/2010
11
+  @version  $Id: emearth3d.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+
15
+#ifndef  EMEARTH3D_INC
16
+#define  EMEARTH3D_INC
17
+
18
+#include "LemmaObject.h"
19
+
20
+namespace Lemma {
21
+
22
+
23
+    // ===================================================================
24
+    //  Class:  EMEarth3D
25
+    /**
26
+      @class
27
+      \brief   Impliments a 3D EM solution to a general conductivity
28
+               structure.
29
+      \details Calculations are made on a rectilinear grid. General 3D
30
+               conductivity is supported, but not magnetic permeability.
31
+     */
32
+    // ===================================================================
33
+    class EMEarth3D : public LemmaObject {
34
+
35
+        public:
36
+
37
+            // ====================  LIFECYCLE     =======================
38
+
39
+            /** Returns a pointer to a new object of type EMEarth3D.
40
+             * It allocates all necessary memory.
41
+             */
42
+            static EMEarth3D* New();
43
+
44
+            /** Deletes this object. Delete also disconnects any
45
+             * attachments to this object.
46
+             */
47
+            void Delete();
48
+
49
+            // ====================  OPERATORS     =======================
50
+
51
+            // ====================  OPERATIONS    =======================
52
+
53
+            // ====================  ACCESS        =======================
54
+
55
+            // ====================  INQUIRY       =======================
56
+
57
+        protected:
58
+
59
+            // ====================  LIFECYCLE     =======================
60
+
61
+            /// Default protected constructor.
62
+            EMEarth3D (const std::string& name);
63
+
64
+            /// Default protected constructor.
65
+            ~EMEarth3D ();
66
+
67
+            /// Frees all memory
68
+            void Release();
69
+
70
+            // ====================  DATA MEMBERS  =========================
71
+
72
+        private:
73
+
74
+    }; // -----  end of class  EMEarth3D  -----
75
+
76
+}		// -----  end of Lemma  name  -----
77
+
78
+#endif   // ----- #ifndef EMEARTH3D_INC  -----

+ 62
- 0
LemmaCore/include/filter.h View File

@@ -0,0 +1,62 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     07/20/2010
11
+  @version  $Id: filter.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#include "LemmaObject.h"
15
+
16
+namespace Lemma {
17
+
18
+
19
+    // ===================================================================
20
+    //  Class:  Filter
21
+    /**
22
+      @class  Filter
23
+      \brief  Abstract class for filtering.
24
+      \details Derived classes include fourier domain and time domain filters.
25
+     */
26
+    // ===================================================================
27
+
28
+    class Filter : public LemmaObject {
29
+
30
+        public:
31
+
32
+            // ====================  LIFECYCLE     =======================
33
+
34
+            // ====================  OPERATORS     =======================
35
+
36
+            // ====================  OPERATIONS    =======================
37
+
38
+            // ====================  ACCESS        =======================
39
+
40
+            // ====================  INQUIRY       =======================
41
+
42
+        protected:
43
+
44
+            // ====================  LIFECYCLE     =======================
45
+
46
+            /// Default protected constructor.
47
+            Filter (const std::string& name);
48
+
49
+            /// Default protected constructor.
50
+            ~Filter ();
51
+
52
+            // ====================  DATA MEMBERS  =========================
53
+
54
+        private:
55
+
56
+    }; // -----  end of class  Filter  -----
57
+
58
+
59
+}		// -----  end of Lemma  name  -----
60
+
61
+/* vim: set tabstop=4 expandtab: */
62
+/* vim: set filetype=cpp: */

+ 139
- 0
LemmaCore/include/gaussianquadrature.h View File

@@ -0,0 +1,139 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     10/07/2010
11
+  @version  $Id: gaussianquadrature.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef __gaussianquadrature_h
15
+#define __gaussianquadrature_h
16
+
17
+#include "LemmaObject.h"
18
+
19
+namespace Lemma {
20
+
21
+
22
+	// ===================================================================
23
+	//        Class:  gaussianquadrature
24
+	/// \brief Numerical integration via Legendre-Gauss Quadrature.
25
+	/// \details Returns integration result, weights, and abscissae.  This
26
+	/// script computes the Legendre-Gauss nodes and weights on an interval
27
+	/// [a,b] with truncation order N.  This class is heavily derived from
28
+	/// lgwt.m by Greg von Winckel (2/25/2004).
29
+	// ===================================================================
30
+	class gaussianquadrature {
31
+
32
+		public:
33
+
34
+			friend std::ostream &operator<<(std::ostream &stream,
35
+						const gaussianquadrature &ob);
36
+
37
+			// ====================  LIFECYCLE     =======================
38
+
39
+			static gaussianquadrature* New();
40
+
41
+			void Delete();
42
+
43
+			// ====================  OPERATORS     =======================
44
+
45
+			// ====================  OPERATIONS    =======================
46
+			/// Perform Gaussian Quadrature Integration
47
+			void Integrate();
48
+
49
+			/// Calculate abscissae and weights
50
+			void CalcAW();
51
+
52
+			// ====================  ACCESS        =======================
53
+			/// Set number of points and limits
54
+			void SetFreqs(const int& nfreq, const Real& a, const Real& b);
55
+
56
+			/// Eigen Vector of function values to be integrated over
57
+			void SetFunc(const VectorXr& fx);
58
+
59
+			// ====================  INQUIRY       =======================
60
+			/// Returns Eigen Vector of Abscissae
61
+			VectorXr GetAbscissae();
62
+
63
+			/// Returns Eigen Vector of Weights
64
+			VectorXr GetWeights();
65
+
66
+			/// Returns integration result
67
+			Real GetResult();
68
+
69
+
70
+		protected:
71
+
72
+			// ====================  LIFECYCLE     =======================
73
+
74
+			/// Default protected constructor.
75
+			gaussianquadrature ();
76
+
77
+			/// Default protected constructor.
78
+			~gaussianquadrature ();
79
+
80
+
81
+
82
+			// ====================  DATA MEMBERS  =========================
83
+			/// Interval
84
+			Real dx;
85
+
86
+			/// Machine precision
87
+			Real machineeps;
88
+
89
+			/// Bookkeeping variable
90
+			int N;
91
+
92
+			/// Bookkeeping variable
93
+			int N1;
94
+
95
+			/// Bookkeeping variable
96
+			int N2;
97
+
98
+			/// Lower bound
99
+			Real a;
100
+
101
+			/// Upper bound
102
+			Real b;
103
+
104
+			/// Placeholder vector
105
+			VectorXr ytemp;
106
+
107
+			/// Abscissae
108
+			VectorXr xu;
109
+
110
+			/// Intermediate Abscissae vector
111
+			VectorXr y;
112
+
113
+			/// Intermediate Abscissae vector
114
+			VectorXr y0;
115
+
116
+			/// Legendre-Gauss Vandermonde Matrix
117
+			MatrixXr L;
118
+
119
+			/// Derivative of LGVM
120
+			VectorXr Lp;
121
+
122
+			/// Intermediate Matrix
123
+			VectorXr Ltemp;
124
+
125
+			/// Weights Vector
126
+			VectorXr wgq;
127
+
128
+			///Function to integrate
129
+			VectorXr funcx;
130
+
131
+			/// Integration result
132
+			Real intres;
133
+
134
+		private:
135
+
136
+	}; // -----  end of class  gaussianquadrature  -----
137
+} // end of namespace Lemma
138
+#endif // __gaussianquadrature_h
139
+

+ 64
- 0
LemmaCore/include/grid.h View File

@@ -0,0 +1,64 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     10/25/2009
11
+  @version  $Id: grid.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef __GRID_H
15
+#define __GRID_H
16
+
17
+#include "LemmaObject.h"
18
+
19
+namespace Lemma {
20
+
21
+// ===============================================================================
22
+//        Class:  Grid
23
+/// \brief Abstract base class for grids.
24
+/// \details Grids define values in space, they may either be an integral part
25
+/// of models, or simply the output of a forward modelling procedure.
26
+// ===============================================================================
27
+
28
+class Grid : public LemmaObject {
29
+
30
+    friend std::ostream &operator<<(std::ostream &stream,
31
+            const Grid &ob);
32
+
33
+    public:
34
+
35
+        // ====================  LIFECYCLE     ===================================
36
+
37
+        // ====================  OPERATORS     ===================================
38
+
39
+        // ====================  OPERATIONS    ===================================
40
+
41
+        // ====================  ACCESS        ===================================
42
+
43
+        // ====================  INQUIRY       ===================================
44
+
45
+    protected:
46
+
47
+        // ====================  LIFECYCLE     ===================================
48
+
49
+        /// Default protected constructor.
50
+        Grid (const std::string &name);
51
+
52
+        /// Default protected constructor.
53
+        ~Grid ();
54
+
55
+        // ====================  DATA MEMBERS  ===================================
56
+
57
+    private:
58
+
59
+}; // -----  end of class  Grid  -----
60
+
61
+} // namespace Lemma
62
+
63
+#endif // __GRID_H
64
+

+ 90
- 0
LemmaCore/include/hankeltransform.h View File

@@ -0,0 +1,90 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     01/28/2010
11
+  @version  $Id: hankeltransform.h 270 2015-08-24 15:45:41Z tirons $
12
+ **/
13
+
14
+#ifndef __hankeltransform_h
15
+#define __hankeltransform_h
16
+
17
+#include "LemmaObject.h"
18
+#include "kernelem1dbase.h"
19
+#include "kernelem1dspec.h"
20
+#include "kernelem1dmanager.h"
21
+
22
+namespace Lemma {
23
+
24
+        // ===================================================================
25
+        //        Class:  HankelTransform
26
+        /// \brief  Pure abstract class for hankel transforms
27
+        /// \details
28
+        // ===================================================================
29
+        class HankelTransform : public LemmaObject {
30
+
31
+            public:
32
+
33
+                /// Prints out basic info about the class
34
+                friend std::ostream &operator<<(std::ostream &stream,
35
+                        const HankelTransform &ob);
36
+
37
+                // ====================  LIFECYCLE     =======================
38
+
39
+                //static HankelTransform* New();
40
+
41
+                //void Delete();
42
+
43
+                // ====================  OPERATORS     =======================
44
+
45
+                // ====================  OPERATIONS    =======================
46
+
47
+                /// @todo this is actually a deprecated function. Only Chave
48
+                ///   uses this.
49
+                /// Performs numerical integration using Gaussian quadrature
50
+                /// ikk:   type of kernel depending on source and receiver couple
51
+                /// imode: a switch for TE(0) and TM(1) mode
52
+                /// itype: order of Bessel function
53
+                /// rho is argument to integral
54
+                /// wavef is the propogation constant of free space
55
+                /// = omega * sqrt( EP*AMU )  amu = 4 pi e-7  ep = 8.85e-12
56
+                virtual Complex Zgauss(const int &ikk, const EMMODE &imode,
57
+                            const int &itype, const Real &rho,
58
+                            const Real &wavef, KernelEm1DBase *Kernel)=0;
59
+
60
+                /// Computes related kernels, if applicable, otherwise this is
61
+                /// just a dummy function.
62
+                virtual void ComputeRelated(const Real& rho, KernelEm1DBase* Kernel);
63
+
64
+                virtual void ComputeRelated(const Real& rho, std::vector< KernelEm1DBase* > KernelVec);
65
+
66
+                virtual void ComputeRelated(const Real& rho, KernelEM1DManager* KernelManager);
67
+
68
+                // ====================  ACCESS        =======================
69
+
70
+                // ====================  INQUIRY       =======================
71
+
72
+                // ====================  DATA MEMBERS  =======================
73
+
74
+            protected:
75
+
76
+                // ====================  LIFECYCLE     =======================
77
+
78
+                /// Default protected constructor.
79
+                HankelTransform (const std::string &name);
80
+
81
+                /// Default protected constructor.
82
+                ~HankelTransform ();
83
+
84
+            private:
85
+
86
+    }; // -----  end of class  HankelTransform  -----
87
+
88
+}
89
+
90
+#endif // __hankeltransform_h

+ 349
- 0
LemmaCore/include/hankeltransformgaussianquadrature.h View File

@@ -0,0 +1,349 @@
1
+/* This Source Code Form is subject to the terms of the Mozilla Public
2
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
3
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4
+
5
+/**
6
+  @file
7
+  @author   Trevor Irons
8
+  @date     01/02/2010
9
+  @version  $Id: hankeltransformgaussianquadrature.h 199 2014-12-29 19:25:20Z tirons $
10
+ **/
11
+
12
+#ifndef  _HANKELTRANSFORMGAUSSIANQUADRATURE_h_INC
13
+#define  _HANKELTRANSFORMGAUSSIANQUADRATURE_h_INC
14
+
15
+#include "hankeltransform.h"
16
+#include "kernelem1dbase.h"
17
+
18
+#ifdef HAVEBOOSTCYLBESSEL
19
+#include "boost/math/special_functions.hpp"
20
+#endif
21
+
22
+namespace Lemma {
23
+
24
+
25
+	// =======================================================================
26
+	//        Class:  HankelTransformGaussianQuadrature
27
+	/// \brief  Calculates hankel transform using gaussian quadrature.
28
+	/// \details  Accurate but slow, this is a port of Alan Chave's public domain
29
+    /// fortran code
30
+	// =======================================================================
31
+	class HankelTransformGaussianQuadrature : public HankelTransform {
32
+
33
+		friend std::ostream &operator<<(std::ostream &stream,
34
+				const HankelTransformGaussianQuadrature &ob);
35
+
36
+		public:
37
+
38
+			// ====================  LIFECYCLE     ===========================
39
+
40
+            /**
41
+             *  Returns pointer to new HankelTransformGaussianQuadrature.
42
+             *  Location is
43
+             *  initialized to (0,0,0) type and polarization are
44
+             *  initialized  to nonworking values that will throw
45
+             *  exceptions if used.
46
+             */
47
+			static HankelTransformGaussianQuadrature* New();
48
+
49
+            /**
50
+             * @copybrief LemmaObject::Delete()
51
+             * @copydetails LemmaObject::Delete()
52
+             */
53
+            void Delete();
54
+
55
+			// ====================  OPERATORS     ===========================
56
+
57
+			// ====================  OPERATIONS    ===========================
58
+
59
+			/// Performs numerical integration using Gaussian quadrature
60
+			/// ikk:   type of kernel depending on source and receiver couple
61
+			/// imode: a switch for TE(0) and TM(1) mode
62
+			/// itype: order of Bessel function
63
+			/// rho is argument to integral
64
+			/// wavef is the propogation constant of free space
65
+			/// = omega * sqrt( EP*AMU )  amu = 4 pi e-7  ep = 8.85e-12
66
+            //template <EMMODE T>
67
+			Complex Zgauss(const int &ikk, const EMMODE &imode,
68
+							const int &itype, const Real &rho,
69
+							const Real &wavef, KernelEm1DBase *Kernel);
70
+
71
+			// ====================  ACCESS        ============================
72
+
73
+			// ====================  INQUIRY       ============================
74
+
75
+			// ====================  DATA MEMBERS  ============================
76
+
77
+		protected:
78
+
79
+			// ====================  LIFECYCLE     ============================
80
+
81
+			/// Default protected constructor.
82
+			HankelTransformGaussianQuadrature (const std::string &name);
83
+
84
+            /// Default protected constructor.
85
+			~HankelTransformGaussianQuadrature ();
86
+
87
+            /**
88
+             * @copybrief LemmaObject::Release()
89
+             * @copydetails LemmaObject::Release()
90
+             */
91
+            void Release();
92
+
93
+			// ====================  OPERATIONS    ============================
94
+
95
+			/// Modified by Yoonho Song to branch cut, June, 1996
96
+			/// Separate Gaussian quarature integral by two interval
97
+			/// first:  integal from 0 to wavenumber of free space
98
+			/// second: integral from wavenunmber of free space to infinity
99
+			///         for large arguments, it uses continued fraction also
100
+			/// It is recommended to use nl = 1 to 6, nu =7
101
+			/// PERFORMS AUTOMATIC CALCULATION OF BESSEL TRANSFORM TO SPECIFIED
102
+			/// RELATIVportisheadE AND ABSOLUTE ERROR
103
+			///
104
+			/// ARGUMENT LIST:
105
+			///
106
+			/// BESR,BESI-REAL AND IMAGINARY PARTS RETURNED BY BESAUX
107
+			/// iorder-ORDER OF THE BESSEL FUNCTION
108
+			/// NL-LOWER LIMIT FOR GAUSS ORDER TO START COMPUTATION
109
+			/// NU-UPPER LIMIT FOR GAUSS ORDER
110
+			/// NU,NL=1,...7 SELECTS 3,7,15,31,63,127,AND 255 POINT GAUSS
111
+			/// QUADRATURE BETWEEN THE ZERO CROSSINGS OF THE BESSEL FUNCTION
112
+			/// R-ARGUMENT OF THE BESSEL FUNCTION
113
+			/// RERR,AERR-RELATIVE AND ABSOLUTE ERROR FOR TERMINATION
114
+			/// BESAUX TERMINATES WHEN INCREASING THE GAUSS ORDER DOES NOT
115
+			/// CHANGE THE RESULT BY MORE THAN RERR OR WHEN THE ABSOLUTE ERROR
116
+			/// IS LESS THAN AERR OR WHEN A GAUSS ORDER OF NU IS REACHED.
117
+			/// NPCS-NUMBER OF PIECES INTO WHICH EACH PARTIAL INTEGRAND
118
+			/// IS DIVIDED,
119
+			/// ORDINARILY SET TO ONE. FOR VERY SMALL VALUES OF R WHERE
120
+			/// THE KERNEL FUNCTION IS APPRECIABLE ONLY OVER THE FIRST FEW
121
+			/// LOOPS OF THE BESSEL FUNCTION, NPCS MAY BE INCREASED TO ACHIEVE
122
+			/// REASONABLE ACCURACY.
123
+			/// NEW  IF NEW=1, THE INTEGRANDS ARE COMPUTED AND SAVED AT EACH
124
+			/// GAUSS
125
+			/// ORDER. IF NEW=2, PREVIOUSLY COMPUTED INTEGRANDS ARE USED. NOTE
126
+			/// THAT ORDER,R, AND NPCS MUST NOT BE CHANGED WHEN SETTING NEW=2.
127
+			/// IERR-ERROR PARAMETER
128
+			/// IERR=0--NORMAL RETURN
129
+			/// IERR=1--RESULT NOT ACCURATE TO RERR DUE TO TOO LOW A GAUSS
130
+			///  ORDER OR CONVERGENCE NOT ACHIEVED IN BESTRX
131
+            //template <EMMODE T>
132
+			void Besautn(Real &besr, Real &besi, const int &iorder,
133
+							const int &nl, const int &nu, const Real &rho,
134
+							const Real &rerr, const Real &aerr,
135
+							const int &npcs, int &inew, const Real &aorb,
136
+							KernelEm1DBase *Kernel);
137
+
138
+			/// COMPUTES BESSEL TRANSFORM OF SPECIFIED ORDER DEFINED AS
139
+			/// INTEGRAL(FUNCT(X)*J-SUB-ORDER(X*R)*DX) FROM X=0 TO INFINITY
140
+			/// COMPUTATION IS ACHIEVED BY INTEGRATION BETWEEN THE ASYMPTOTIC
141
+			/// ZERO CROSSINGS OF THE BESSEL FUNCTION USING GAUSS QUADRATURE.
142
+			/// THE RESULTING SERIES OF PARTIAL INTEGRANDS IS SUMMED BY
143
+			/// CALCULATING THE PADE APPROXIMANTS TO SPEED UP CONVERGENCE.
144
+			/// ARGUMENT LIST:
145
+			/// BESR,BESI  REAL AND IMAGINARY PARTS RETURNED BY BESTRN
146
+			/// iorder  ORDER OF THE BESSEL FUNCTIONC  NG  NUMBER OF GAUSS
147
+			/// POINTS TO USE IN THE QUADRATURE ROUTINE.
148
+			/// NG=1 THROUGH 7 SELECTS 3,7,15,31,63,126,AND 255 TERMS.
149
+			///   R     ARGUMENT OF THE BESSEL FUNCTION
150
+			///   RERR,AERR  SPECIFIED RELATIVE AND ABSOLUTE ERROR FOR THE
151
+			///           CALCULATION.  THE INTEGRATION
152
+			///  TERMINATES WHEN AN ADDITIONAL TERM DOES NOT CHANGE THE
153
+			///  RESULT BY MORE THAN RERR*RESULT+AERR
154
+			///  NPCS  NUMBER OF PIECES INTO WHICH EACH PARTIAL I
155
+			///        NTEGRAND IS DIVIDED,
156
+			///        ORDINARILY SET TO ONE. FOR VERY SMALL VALUES OF RANGE
157
+			///        WHERE THE KERNEL FUNCTION IS APPRECIABLE ONLY OVER THE
158
+			///        FIRST FEW LOOPS OF THE BESSEL FUNCTION, NPCS MAY BE
159
+			///        INCREASED TO ACHIEVE REASONABLE ACCURACY. NOTE THAT
160
+			///        NPCS AFFECTS ONLY THE PADE
161
+			///        SUM PORTION OF THE INTEGRATION, OVER X(NSUM) TO INFINITY.
162
+			/// XSUM  VECTOR OF VALUES OF THE KERNEL ARGUMENT OF FUNCT FOR WHICH
163
+			/// EXPLICIT CALCULATION OF THE INTEGRAL IS DESIRED, SO THAT THE
164
+			/// INTEGRAL OVER 0 TO XSUM(NSUM) IS ADDED TO THE INTEGRAL OVER
165
+			/// XSUM(NSUM) TO INFINITY WITH THE PADE METHOD INVOKED ONLY FOR
166
+			/// THE LATTER. THIS ALLOWS THE PADE SUMMATION METHOD TO BE
167
+			/// OVERRIDDEN AND SOME TYPES OF SINGULARITIES TO BE HANDLED.
168
+			/// NSUM  NUMBER OF VALUES IN XSUM, MAY BE ZERO.
169
+			/// NEW   DETERMINES METHOD OF KERNEL CALCULATION
170
+			/// NEW=0 MEANS  CALCULATE BUT DO NOT SAVE INTEGRANDS
171
+			/// NEW=1 MEANS CALCULATE KERNEL BY CALLING FUNCT-SAVE KERNEL
172
+			///       TIMES BESSEL FUNCTION
173
+			/// NEW=2 MEANS USE SAVED KERNELS TIMES BESSEL FUNCTIONS IN
174
+			///       COMMON /BESINT/. NOTE THAT ORDER,R,NPCS,XSUM, AND
175
+			///       NSUM MAY NOT BE CHANGED WHEN SETTING NEW=2.
176
+			/// IERR  ERROR PARAMETER
177
+			///       0 NORMAL RETURN-INTEGRAL CONVERGED
178
+			///       1 MEANS NO CONVERGENCE AFTER NSTOP TERMS IN THE PADE SUM
179
+			///
180
+			/// SUBROUTINES REQUIRED:
181
+			/// BESQUD,PADECF,CF,ZEROJ,DOT,JBESS
182
+			///  A.CHAVE IGPP/UCSD
183
+			/// NTERM IS MAXIMUM NUMBER OF BESSEL FUNCTION LOOPS STORED IF
184
+			/// NEW.NE.0
185
+			/// NSTOP IS MAXIMUM Number of Pade terms
186
+            //template <EMMODE T>
187
+ 			void Bestrn( Real &BESR, Real &BESI, const int &iorder,
188
+ 					const int &NG, const Real &R,
189
+ 					const Real &RERR, const Real &AERR, const int &npcs,
190
+ 					VectorXi &XSUM, int &NSUM, int &NEW,
191
+ 					int &IERR, int &NCNTRL, const Real &AORB,
192
+					KernelEm1DBase *Kernel);
193
+
194
+			/// CALCULATES THE INTEGRAL OF F(X)*J-SUB-N(X*R) OVER THE
195
+			/// INTERVAL A TO B AT A SPECIFIED GAUSS ORDER THE RESULT IS
196
+			/// OBTAINED USING A SEQUENCE OF 1, 3, 7, 15, 31, 63, 127, AND 255
197
+			/// POINT INTERLACING GAUSS FORMULAE SO THAT NO INTEGRAND
198
+			/// EVALUATIONS ARE WASTED. THE KERNEL FUNCTIONS MAY BE
199
+			/// SAVED SO THAT BESSEL TRANSFORMS OF SIMILAR KERNELS ARE COMPUTED
200
+			/// WITHOUT NEW EVALUATION OF THE KERNEL.  DETAILS ON THE FORMULAE
201
+			/// ARE GIVEN IN 'THE OPTIMUM ADDITION OF POINTS TO QUADRATURE
202
+			/// FORMULAE' BY T.N.L. PATTERSON, MATHS.COMP. 22,847-856 (1968).
203
+			/// GAUSS WEIGHTS TAKEN FROM COMM. A.C.M. 16,694-699 (1973)
204
+			/// ARGUMENT LIST:
205
+			/// A      LOWER LIMIT OF INTEGRATION
206
+			/// B      UPPER LIMIT OF INTEGRATION
207
+			/// BESR,BESI RETURNED INTEGRAL VALUE REAL AND IMAGINARY PARTS
208
+			/// NG NUMBER OF POINTS IN THE GAUSS FORMULA.  NG=1,...7
209
+			///        SELECTS 3,7,15,31,63,127,AND 255 POINT QUADRATURE.
210
+			///  NEW SELECTS METHOD OF KERNEL EVALUATION
211
+			///    NEW=0 CALCULATES KERNELS BY CALLING F - NOTHING SAVED
212
+			///    NEW=1 CALCULATES KERNELS BY CALLING F AND SAVES KERNEL TIMES
213
+			///           BESSEL FUNCTION IN COMMON /BESINT/
214
+			///    NEW=2 USES SAVED KERNEL TIMES BESSEL FUNCTIONS IN
215
+			///           COMMON /BESINT/
216
+			/// iorder ORDER OF THE BESSEL FUNCTION
217
+			/// R    ARGUMENT OF THE BESSEL FUNCTION
218
+			/// F     F(X) IS THE EXTERNAL INTEGRAND SUBROUTINE
219
+			/// A.CHAVE IGPP/UCSDC
220
+			/// MAXIMUM NUMBER OF BESSEL FUNCTION LOOPS THAT CAN BE SAVED
221
+            //template <EMMODE T>
222
+			void Besqud(const Real &A, const Real &B, Real &BESR, Real &BESI,
223
+							const int &NG, const int &NEW, const int &iorder,
224
+							const Real &R, KernelEm1DBase *Kernel);
225
+
226
+			/// COMPUTES SUM(S(I)),I=1,...N BY COMPUTATION OF PADE APPROXIMANT
227
+			/// USING CONTINUED FRACTION EXPANSION.  FUNCTION IS DESIGNED TO BE
228
+			/// CALLED SEQUENTIALLY AS N IS INCREMENTED FROM 1 TO ITS FINAL
229
+			/// VALUE.  THE NTH CONTINUED FRACTION COEFFICIENT IS CALCULATED AND
230
+			/// STORED AND THE NTH CONVERGENT RETURNED.  IT IS UP TO THE USER TO
231
+			/// STOP THE CALCULATION WHEN THE DESIRED ACCURACY IS ACHIEVED.
232
+			/// ALGORITHM FROM HANGGI ET AL., Z.NATURFORSCH. 33A,402-417 (1977)
233
+			/// IN THEIR NOTATION, VECTORS CFCOR,CFCOI ARE LOWER CASE D,
234
+			/// VECTORS DR, DI ARE UPPER CASE D, VECTORS XR,XI ARE X, AND
235
+			/// VECTORS SR,SI ARE S
236
+			/// A.CHAVE IGPP/UCSD
237
+			void Padecf(Real &SUMR, Real &SUMI, const int &N);
238
+
239
+			/// EVALUATES A COMPLEX CONTINUED FRACTION BY RECURSIVE DIVISION
240
+			/// STARTING AT THE BOTTOM, AS USED BY PADECF
241
+			/// RESR,RESI ARE REAL AND IMAGINARY PARTS RETURNED
242
+			/// CFCOR,CFCOI ARE REAL AND IMAGINARY VECTORS OF CONTINUED FRACTION
243
+			/// COEFFICIENTS
244
+			void CF(        Real& RESR, Real &RESI,
245
+							Eigen::Matrix<Real, 100, 1> &CFCOR,
246
+							Eigen::Matrix<Real, 100, 1> &CFCOI,
247
+							const int &N);
248
+
249
+
250
+			/// COMPUTES ZERO OF BESSEL FUNCTION OF THE FIRST KIND FROM
251
+			/// MCMAHON'S ASYMPTOTIC EXPANSION
252
+			/// NZERO-NUMBER OF THE ZERO
253
+			/// iorder-ORDER OF THE BESSEL FUNCTION (0 OR 1)
254
+			Real ZeroJ(const int &ZERO, const int &IORDER);
255
+
256
+			/// COMPUTES BESSEL FUNCTION OF ORDER "ORDER" AND ARGUMENT X BY
257
+			/// CALLING NBS ROUTINES J0X AND J1X (REAL*8 BUT APPROXIMATELY
258
+			/// REAL*4 ACCURACY).
259
+			/// FOR MORE ACCURACY JBESS COULD BE CHANGED TO CALL, FOR EXAMPLE,
260
+			/// THE IMSL ROUTINES MMBSJ0,MMBSJ1 << SEE C// BELOW >>
261
+			Real Jbess(const Real &X, const int &IORDER);
262
+
263
+			/// COMPUTES DOT PRODUCT OF TWO D.P. VECTORS WITH NONUNIT
264
+			/// INCREMENTING ALLOWED. REPLACEMENT FOR BLAS SUBROUTINE SDOT.
265
+			/// Currently does no checking, kind of stupid.
266
+			/// The fortran version will wrap around if (inc*N) > X1.size()
267
+			/// but not in a nice way.
268
+			Real _dot(const int&N,
269
+				const Eigen::Matrix<Real, Eigen::Dynamic, Eigen::Dynamic> &X1,
270
+							const int &INC1,
271
+				const Eigen::Matrix<Real, Eigen::Dynamic, Eigen::Dynamic> &X2,
272
+				const int &INC2);
273
+
274
+			// ====================  DATA MEMBERS  ============================
275
+
276
+            static const Real PI2;
277
+			static const Real X01P;
278
+			static const Real XMAX;
279
+			static const Real XSMALL;
280
+			static const Real J0_X01;
281
+			static const Real J0_X02;
282
+			static const Real J0_X11;
283
+			static const Real J0_X12;
284
+			static const Real FUDGE;
285
+			static const Real FUDGEX;
286
+			static const Real TWOPI1;
287
+			static const Real TWOPI2;
288
+			static const Real RTPI2;
289
+			static const Real XMIN;
290
+			static const Real J1_X01;
291
+			static const Real J1_X02;
292
+			static const Real J1_X11;
293
+			static const Real J1_X12;
294
+
295
+			/// Highest gauss order used, Was NG
296
+			int HighestGaussOrder;
297
+
298
+			/// Total number of partial integrals on last call, was NI
299
+			int NumberPartialIntegrals;
300
+
301
+			/// Total number of function calls, was NF
302
+			int NumberFunctionEvals;
303
+
304
+			int          np;
305
+			int          nps;
306
+
307
+            /////////////////////////////////////////////////////////////
308
+			// Eigen members
309
+
310
+            // Shared constant values
311
+			static const VectorXr  WT;
312
+			static const VectorXr  WA;
313
+
314
+			Eigen::Matrix<int,  100, 1>    Nk;
315
+			//Eigen::Matrix<Real, 255, 100>  karg;
316
+			//Eigen::Matrix<Real, 510, 100>  kern;
317
+			Eigen::Matrix<Real, Eigen::Dynamic, Eigen::Dynamic>  karg;
318
+			Eigen::Matrix<Real, Eigen::Dynamic, Eigen::Dynamic>  kern;
319
+
320
+			// Was Besval COMMON block
321
+			Eigen::Matrix<Real, 100, 1> Xr;
322
+			Eigen::Matrix<Real, 100, 1> Xi;
323
+			Eigen::Matrix<Real, 100, 1> Dr;
324
+			Eigen::Matrix<Real, 100, 1> Di;
325
+			Eigen::Matrix<Real, 100, 1> Sr;
326
+			Eigen::Matrix<Real, 100, 1> Si;
327
+			Eigen::Matrix<Real, 100, 1> Cfcor;
328
+			Eigen::Matrix<Real, 100, 1> Cfcoi;
329
+
330
+		private:
331
+
332
+	}; // -----  end of class  HankelTransformGaussianQuadrature  -----
333
+
334
+    //////////////////////////////////////////////////////////////
335
+    // Exception Classes
336
+
337
+    /** If the lower integration limit is greater than the upper limit, throw this
338
+     * error.
339
+     */
340
+    class LowerGaussLimitGreaterThanUpperGaussLimit :
341
+        public std::runtime_error {
342
+        /** Thrown when the LowerGaussLimit is greater than the upper limit.
343
+         */
344
+        public: LowerGaussLimitGreaterThanUpperGaussLimit();
345
+    };
346
+
347
+}	   // -----  end of Lemma  name  -----
348
+
349
+#endif   // ----- #ifndef _HANKELTRANSFORMGAUSSIANQUADRATURE_h_INC  -----

+ 246
- 0
LemmaCore/include/hankeltransformhankel2.h View File

@@ -0,0 +1,246 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     06/26/2009
11
+  @version  $Id: hankeltransformhankel2.h 201 2015-01-03 00:07:47Z tirons $
12
+ **/
13
+
14
+#ifndef __HANKEL2_H
15
+#define __HANKEL2_H
16
+
17
+#include "hankeltransform.h"
18
+#include "kernelem1dbase.h"
19
+#include "kernelem1dspec.h"
20
+#include "CubicSplineInterpolator.h"
21
+
22
+namespace Lemma {
23
+
24
+// ==========================================================================
25
+//        Class:  Hankel2
26
+/** \brief   Computes the Hankel transform of orders 0 and 1 using lagged
27
+             and related convolutions.
28
+    \details A rewrite of work by Anderson who wrote a FORTRAN program
29
+             that he released while working at the USGS.
30
+             The  transform evaluates an integral of the form:
31
+             \f[ \int_0^\infty K(\lambda) J_I (\lambda r) ~ d \lambda
32
+             \f]
33
+             Where \f$ K(\lambda) \f$ is some kernel function. The value
34
+             \f$ J_I \f$ is the Bessel function of order
35
+             \f$I, I \in \{0,1\} \f$
36
+             The kernel function is unique for each source and is computed
37
+             in the class CalculateKernel. The value \f$r\f$ is the radial
38
+             distance away from the centre of the grid \f$ r=\sqrt{x^2 + y^2} \f$
39
+             The Hankel transform is useful as it allows a double fourier
40
+             transform to be written as a single integral:
41
+             \f[ \mathop {\int \!\!\! \int}_{\!\!\!\!\!-\infty}^{\,\,\infty}
42
+             F(k_x^2 + k_y^2)
43
+                 e^{\imath (k_x x + k_y y)} dk_x \, dk_y = 2 \pi
44
+                 \int_0^\infty K(\lambda) J_I (\lambda r) ~ d \lambda
45
+             \f]
46
+             This can only be done where there is radial symmetry. Hence
47
+             its application to 1D solutions here.
48
+ */
49
+// ==========================================================================
50
+
51
+class Hankel2 : public HankelTransform {
52
+
53
+    friend std::ostream &operator<<(std::ostream &stream, const Hankel2 &ob);
54
+
55
+    public:
56
+
57
+        // ====================  LIFECYCLE     ==============================
58
+        /**
59
+         *  Returns pointer to new Hankel2. Location is
60
+         *  initialized to (0,0,0) type and polarization are
61
+         *  initialized  to nonworking values that will throw
62
+         *  exceptions if used.
63
+         */
64
+        static Hankel2 *New();
65
+
66
+        /**
67
+         * @copybrief LemmaObject::Delete()
68
+         * @copydetails LemmaObject::Delete()
69
+         */
70
+        void Delete();
71
+
72
+        // ====================  OPERATORS     ==============================
73
+
74
+        // ====================  OPERATIONS    ==============================
75
+
76
+        /// Sets the number of convolutions
77
+        void SetNumConv(const int &i);
78
+
79
+        /// Computes the hankel transform with arguments
80
+        /// @param rho [input] rho is the hankel transform argument
81
+        /// @param ntol [input] ntol is
82
+        /// @param tol [input] tol is
83
+        void Compute(const Real &rho, const int& ntol, const Real &tol);
84
+
85
+        /// Computes the related
86
+        void ComputeRelated(const Real &rho, KernelEm1DBase* Kernel);
87
+
88
+        /// Computes the related
89
+        void ComputeRelated(const Real &rho,  std::vector< KernelEm1DBase* > KernelVec);
90
+
91
+        /// Computes the related
92
+        void ComputeRelated(const Real &rho,  KernelEM1DManager* Manager);
93
+
94
+        /// Computes the related and lagged convolutions
95
+        void ComputeLaggedRelated(const Real &rho, const int& nlag,  KernelEM1DManager* Manager);
96
+
97
+        // ====================  ACCESS        ==============================
98
+
99
+        /// Returns the answer
100
+        Eigen::Matrix<Complex, Eigen::Dynamic, Eigen::Dynamic>  GetAnswer();
101
+
102
+        /// Returns the arguments for lagged convolutions
103
+        VectorXr GetArg() {return Arg;};
104
+
105
+        /// Returns the value of Abscissa stepping
106
+        Real GetABSER( ) { return ABSER; };
107
+
108
+        /// Sets the lagged kernel index so that the proper value is returned
109
+        void SetLaggedArg(const Real& rho);
110
+
111
+
112
+        // ====================  INQUIRY       ==============================
113
+
114
+        /// Calculates Hankel Transform using filtering.
115
+        /// ikk:   type of kernel depending on source and receiver couple
116
+        /// imode: a switch for TE(0) and TM(1) mode
117
+        /// itype: order of Bessel function
118
+        /// rho is argument to integral
119
+        /// wavef is the propogation constant of free space
120
+        /// = omega * sqrt( EP*AMU )  amu = 4 pi e-7  ep = 8.85e-12
121
+        Complex Zgauss(const int &ikk, const EMMODE &imode,
122
+                        const int &itype, const Real &rho,
123
+                        const Real &wavef, KernelEm1DBase *Kernel);
124
+
125
+    protected:
126
+
127
+        // ====================  LIFECYCLE     ==============================
128
+
129
+        /** A rewrite of Anderson's Pseudo-subroutine. */
130
+        inline void StoreRetreive(const int &idx, const int &lag,
131
+                        Complex &Zsum, const int &irel, Complex &C, const Real& rho0) {
132
+
133
+            int look = idx+lag;
134
+    		int	iq = look/801;
135
+    		int	ir = look%801;
136
+    		int iroll = iq*800;
137
+
138
+    		if(this->Key[ir] <= iroll) {
139
+			    this->Key[ir] = iroll + ir;
140
+ 	    		++this->NumFun;
141
+                Manager->ComputeReflectionCoeffs(this->Lambda, idx, rho0);
142
+ 			    for (unsigned int ir2=0; ir2<this->kernelVec.size(); ++ir2) {
143
+ 			        this->Zwork(ir, ir2) = this->kernelVec[ir2]->RelBesselArg(this->Lambda);
144
+ 			    }
145
+		    }
146
+
147
+		    C = this->Zwork(ir, irel) * this->FilterWeights(this->BesselOrder, idx);
148
+		    Zsum += C;
149
+		    return;
150
+	    }
151
+
152
+        /// Default protected constructor
153
+        Hankel2(const std::string& name);
154
+
155
+        /// Default protected destructor
156
+        ~Hankel2();
157
+
158
+        /**
159
+         * @copybrief LemmaObject::Release()
160
+         * @copydetails LemmaObject::Release()
161
+         */
162
+        void Release();
163
+
164
+        // ====================  OPERATIONS    ==============================
165
+
166
+        void DeleteSplines();
167
+
168
+        // ====================  DATA MEMBERS  ==============================
169
+
170
+        /// The hankel transform wavenumber embedded in the integral
171
+        Real Lambda;
172
+
173
+        /// Number of times a kernel was evaluated
174
+        int NumFun;
175
+
176
+        /// Number of lagged convolutions
177
+        /// must be greater or equal to 1
178
+        /// It is set automatically in the @see Compute function so
179
+        /// that  \f$ \rho \exp\left( -.1*(\mathtt{NumConv} -1) \right) \f$
180
+        /// does not underflow the exponent range
181
+        int NumConv;
182
+
183
+        /// Number of related kernels
184
+        int NumRel;
185
+
186
+        /** Bessel transform order to use */
187
+        int BesselOrder;
188
+
189
+        /** Lag argument */
190
+        int iLag;
191
+
192
+        /* Should results be cached? Useful for repeated calculations of few receiver points */
193
+        // turned out to have only marginal benefits in best case, and awful consequences in many
194
+        //bool cacheResults;
195
+
196
+        /** Related Kernel Manager */
197
+        KernelEM1DManager*          Manager;
198
+
199
+        /// Used as base for filter abscissa generation
200
+        static const Real ABSCISSA;
201
+
202
+        /// Also used in abscissa generation \f$ ABSE = \exp{.1} \f$
203
+        static const Real ABSE;
204
+
205
+        /// Also used in abscissa generation \f$ ABSER = 1 / \exp{.1} \f$
206
+        static const Real ABSER;
207
+
208
+        /// Counter for calculated
209
+        int icount;
210
+
211
+        /// Kernel Calculator
212
+        std::vector <KernelEm1DBase*> kernelVec;
213
+
214
+        /// Spines for lagged convolutions (real part)
215
+        std::vector <CubicSplineInterpolator*> splineVecReal;
216
+
217
+        /// Spines for lagged convolutions (imaginary part)
218
+        std::vector <CubicSplineInterpolator*> splineVecImag;
219
+
220
+        /// Key used internally
221
+        Eigen::Matrix<int, 801, 1> Key;
222
+        //int  Key[801];
223
+        //Eigen::Matrix<int, Eigen::Dynamic, 1> Key;
224
+
225
+        /// Filter weight coefficients. Set for either \f$J_0\f$ or \f$J_1\f$
226
+        /// internally by protected function SetFilterWeights.
227
+        /// Fixed sized will yield better performance. (not necessarily)
228
+        //Eigen::Matrix<Real, 801, 1> FilterWeights;
229
+        static const Eigen::Matrix<Real, 2, 801> FilterWeights;
230
+        //static const Eigen::Matrix<Real, Eigen::Dynamic, Eigen::Dynamic> FilterWeights;
231
+
232
+        /// Zwork from Anderson
233
+        Eigen::Matrix<Complex, 801, Eigen::Dynamic> Zwork;
234
+        //Eigen::Matrix<Complex, Eigen::Dynamic, Eigen::Dynamic> Zwork;
235
+
236
+        /// Holds answer, dimensions are NumConv, and NumberRelated.
237
+        Eigen::Matrix<Complex, Eigen::Dynamic, Eigen::Dynamic> Zans;
238
+
239
+        /// Holds the arguments for lagged convolutions
240
+        VectorXr Arg;
241
+
242
+}; // -----  end of class  HankelTransform  -----
243
+
244
+}
245
+
246
+#endif // __HANKEL2_h

+ 277
- 0
LemmaCore/include/helper.h View File

@@ -0,0 +1,277 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      10/02/2014 02:49:55 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#pragma once
21
+
22
+#ifndef  HELPER_INC
23
+#define  HELPER_INC
24
+
25
+#include "lemma.h"
26
+
27
+#ifdef HAVE_YAMLCPP
28
+#include "yaml-cpp/yaml.h"
29
+#endif
30
+
31
+namespace Lemma {
32
+
33
+    template <class T>
34
+    inline std::string to_string (const T& t) {
35
+        std::stringstream ss;
36
+        ss << t;
37
+        return ss.str();
38
+    }
39
+
40
+
41
+    // handy little way to convert enums, saves repeated code useful for YAML serializing
42
+    std::string enum2String(const FREQUENCYUNITS& Units);
43
+    std::string enum2String(const TIMEUNITS& Units);
44
+    std::string enum2String(const MAGUNITS& Units);
45
+    std::string enum2String(const TEMPUNITS& Units);
46
+    std::string enum2String(const FEMCOILORIENTATION& Units);
47
+    std::string enum2String(const ORIENTATION& Units);
48
+    std::string enum2String(const FIELDCOMPONENT& Comp);
49
+    std::string enum2String(const HANKELTRANSFORMTYPE& Htype);
50
+    std::string enum2String(const FIELDCALCULATIONS& Htype);
51
+
52
+    // other way around is a template, where template argument lets us know
53
+    // which specialisation to use.
54
+    template <typename T>
55
+    T string2Enum( const std::string& str );
56
+
57
+    // Handy little class that indents a stream.
58
+    // Based on solution provided here, todo may need to add to some managing class which keeps
59
+    // track of nesting levels? But perhaps not. A Lemma class will contain pointers to other Lemma
60
+    // classes. But those are not specifically listed out.
61
+    // http://stackoverflow.com/questions/9599807/how-to-add-indention-to-the-stream-operator
62
+    class IndentingOStreambuf : public std::streambuf {
63
+        std::streambuf*     myDest;
64
+        bool                myIsAtStartOfLine;
65
+        std::string         myIndent;
66
+        std::ostream*       myOwner;
67
+    protected:
68
+        virtual int         overflow( int ch )
69
+        {
70
+            if ( myIsAtStartOfLine && ch != '\n' ) {
71
+                myDest->sputn( myIndent.data(), myIndent.size() );
72
+            }
73
+            myIsAtStartOfLine = ch == '\n';
74
+            return myDest->sputc( ch );
75
+        }
76
+    public:
77
+        explicit            IndentingOStreambuf(
78
+                                std::streambuf* dest, int indent = 4 )
79
+            : myDest( dest )
80
+            , myIsAtStartOfLine( true )
81
+            , myIndent( indent, ' ' )
82
+            , myOwner( NULL )
83
+        {
84
+        }
85
+        explicit            IndentingOStreambuf(
86
+                                std::ostream& dest, int indent = 4 )
87
+            : myDest( dest.rdbuf() )
88
+            , myIsAtStartOfLine( true )
89
+            , myIndent( indent, ' ' )
90
+            , myOwner( &dest )
91
+        {
92
+            myOwner->rdbuf( this );
93
+        }
94
+        virtual             ~IndentingOStreambuf()
95
+        {
96
+            if ( myOwner != NULL ) {
97
+                myOwner->rdbuf( myDest );
98
+            }
99
+        }
100
+    };
101
+
102
+
103
+} // end namespace Lemma
104
+
105
+#ifdef HAVE_YAMLCPP
106
+
107
+///////////////////////////////////////////////////////
108
+// YAML Serializing helper functions. Can we move this into helper.h
109
+namespace YAML {
110
+
111
+template<>
112
+struct convert<Lemma::Complex> {
113
+  static Node encode(const Lemma::Complex& rhs) {
114
+    Node node;
115
+    node["real"] = rhs.real();
116
+    node["imag"] = rhs.imag();
117
+
118
+    // No labels
119
+    //node.push_back(rhs.real());
120
+    //node.push_back(rhs.imag());
121
+
122
+    node.SetTag( "Complex" ); // too verbose?
123
+    return node;
124
+  }
125
+
126
+  static bool decode(const Node& node, Lemma::Complex& rhs) {
127
+    // Disabled due to overly verbose output. Just believe...
128
+    if( node.Tag() != "Complex" ) {
129
+        return false;
130
+    }
131
+    rhs = Lemma::Complex( node["real"].as<Lemma::Real>(), node["imag"].as<Lemma::Real>()  );
132
+    // no label style
133
+    //rhs = Lemma::Complex( node[0].as<Lemma::Real>(), node[1].as<Lemma::Real>()  );
134
+    return true;
135
+  }
136
+
137
+};
138
+
139
+template<>
140
+struct convert<Lemma::Vector3Xr> {
141
+  static Node encode(const Lemma::Vector3Xr& rhs) {
142
+    Node node;
143
+    node["size"] = rhs.cols();
144
+    //node["rows"] = rhs.rows(); // == 3
145
+    for (int ic=0; ic<rhs.cols(); ++ic) {
146
+        node[ic].push_back( rhs(0, ic) );
147
+        node[ic].push_back( rhs(1, ic) );
148
+        node[ic].push_back( rhs(2, ic) );
149
+    }
150
+    node.SetTag( "Vector3Xr" );
151
+    return node;
152
+  }
153
+
154
+  static bool decode(const Node& node, Lemma::Vector3Xr& rhs) {
155
+    if( node.Tag() != "Vector3Xr" ) {
156
+        return false;
157
+    }
158
+    rhs.resize( Eigen::NoChange, node["size"].as<int>() );
159
+    for (unsigned int ic=0; ic<node.size(); ++ic) {
160
+        int ir=0;
161
+        for(YAML::const_iterator it=node[ic].begin();it!=node[ic].end();++it) {
162
+            rhs(ir, ic) = it->as<Lemma::Real>();
163
+            ++ir;
164
+        }
165
+    }
166
+    return true;
167
+  }
168
+};
169
+
170
+template<>
171
+struct convert<Lemma::VectorXr> {
172
+  static Node encode(const Lemma::VectorXr& rhs) {
173
+    Node node;
174
+    node["size"] = rhs.size();
175
+    for (int ic=0; ic<rhs.size(); ++ic) {
176
+        node["data"].push_back( rhs(ic) );
177
+    }
178
+    node.SetTag( "VectorXr" );
179
+    return node;
180
+  }
181
+
182
+  static bool decode(const Node& node, Lemma::VectorXr& rhs) {
183
+    if( node.Tag() != "VectorXr" ) {
184
+        return false;
185
+    }
186
+    rhs.resize( node["size"].as<int>() );
187
+    int ir=0;
188
+    for(YAML::const_iterator it=node["data"].begin(); it!=node["data"].end(); ++it) {
189
+        rhs(ir) = it->as<Lemma::Real>();
190
+        ++ir;
191
+    }
192
+    return true;
193
+  }
194
+};
195
+
196
+template<>
197
+struct convert<Lemma::VectorXcr> {
198
+  static Node encode(const Lemma::VectorXcr& rhs) {
199
+    Node node;
200
+    node["size"] = rhs.size();
201
+    for (int ic=0; ic<rhs.size(); ++ic) {
202
+        node["data"].push_back( rhs(ic) );
203
+    }
204
+    node.SetTag( "VectorXcr" );
205
+    return node;
206
+  }
207
+
208
+  static bool decode(const Node& node, Lemma::VectorXcr& rhs) {
209
+    if( node.Tag() != "VectorXcr" ) {
210
+        return false;
211
+    }
212
+    rhs.resize( node["size"].as<int>() );
213
+    int ir=0;
214
+    for(YAML::const_iterator it=node["data"].begin(); it!=node["data"].end(); ++it) {
215
+        rhs(ir) = it->as<Lemma::Complex>();
216
+        ++ir;
217
+    }
218
+    return true;
219
+  }
220
+};
221
+
222
+
223
+template<>
224
+struct convert<Lemma::VectorXi> {
225
+  static Node encode(const Lemma::VectorXi& rhs) {
226
+    Node node;
227
+    node["size"] = rhs.size();
228
+    for (int ic=0; ic<rhs.size(); ++ic) {
229
+        node["data"].push_back( rhs(ic) );
230
+    }
231
+    node.SetTag( "VectorXi" );
232
+    return node;
233
+  }
234
+
235
+  static bool decode(const Node& node, Lemma::VectorXi& rhs) {
236
+    if( node.Tag() != "VectorXi" ) {
237
+        return false;
238
+    }
239
+    rhs.resize( node["size"].as<int>() );
240
+    int ir=0;
241
+    for(YAML::const_iterator it=node["data"].begin(); it!=node["data"].end(); ++it) {
242
+        rhs(ir) = it->as<int>();
243
+        ++ir;
244
+    }
245
+    return true;
246
+  }
247
+};
248
+
249
+template<>
250
+struct convert<Lemma::Vector3r> {
251
+  static Node encode(const Lemma::Vector3r& rhs) {
252
+    Node node;
253
+    for (int ic=0; ic<rhs.size(); ++ic) {
254
+        node[0].push_back( rhs(ic) );
255
+    }
256
+    node.SetTag( "Vector3r" );
257
+    return node;
258
+  }
259
+
260
+  static bool decode(const Node& node, Lemma::Vector3r& rhs) {
261
+    if( node.Tag() != "Vector3r" ) {
262
+        return false;
263
+    }
264
+    int ir=0;
265
+    for(YAML::const_iterator it=node[0].begin(); it!=node[0].end(); ++it) {
266
+        rhs(ir) = it->as<Lemma::Real>();
267
+        ++ir;
268
+    }
269
+    return true;
270
+  }
271
+};
272
+
273
+}
274
+#endif //HAVE_YAMLCPP
275
+
276
+#endif   // ----- #ifndef HELPER_INC  -----
277
+

+ 62
- 0
LemmaCore/include/instrument.h View File

@@ -0,0 +1,62 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     02/05/2010
11
+  @version  $Id: instrument.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef __INSTRUMENT_H
15
+#define __INSTRUMENT_H
16
+
17
+#include "LemmaObject.h"
18
+
19
+namespace Lemma {
20
+
21
+	// =======================================================================
22
+	//        Class:  Instrument
23
+	/// \brief    Abstract class for instruments
24
+	/// \details
25
+	// =======================================================================
26
+	class Instrument : public LemmaObject {
27
+
28
+		friend std::ostream &operator<<(std::ostream &stream,
29
+			const Instrument &ob);
30
+
31
+		public:
32
+
33
+			// ====================  LIFECYCLE     ===========================
34
+
35
+			// ====================  OPERATORS     ===========================
36
+
37
+			// ====================  OPERATIONS    ===========================
38
+            //virtual void ForwardModelOnOctreeMesh()=0;
39
+
40
+			// ====================  ACCESS        ===========================
41
+
42
+			// ====================  INQUIRY       ===========================
43
+
44
+			// ====================  DATA MEMBERS  ===========================
45
+
46
+		protected:
47
+
48
+			// ====================  LIFECYCLE     ===========================
49
+
50
+			/// Default protected constructor.
51
+			Instrument (const std::string &name);
52
+
53
+			/// Default protected constructor.
54
+			~Instrument ();
55
+
56
+		private:
57
+
58
+	}; // -----  end of class  Instrument  -----
59
+
60
+}		// -----  end of Lemma  name  -----
61
+
62
+#endif // __INSTRUMENT_H

+ 144
- 0
LemmaCore/include/instrumentfem.h View File

@@ -0,0 +1,144 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     01/14/2013
11
+  @version  $Id$
12
+ **/
13
+
14
+#ifndef __INSTRUMENTFEM_H
15
+#define __INSTRUMENTFEM_H
16
+
17
+#include "instrument.h"
18
+#include "emearth1d.h"
19
+#include "WireAntenna.h"
20
+#include "PolygonalWireAntenna.h"
21
+#include "receiverpoints.h"
22
+#include "dipolesource.h"
23
+#include "layeredearthem.h"
24
+#include "datafem.h"
25
+
26
+namespace Lemma {
27
+
28
+// ===================================================================
29
+//        Class:  InstrumentFem
30
+/// \brief
31
+/// \details
32
+// ===================================================================
33
+	class InstrumentFem : public Instrument {
34
+		friend std::ostream &operator<<(std::ostream &stream,
35
+			const InstrumentFem &ob);
36
+
37
+
38
+	public:
39
+
40
+	// ====================  LIFECYCLE     =======================
41
+
42
+		static InstrumentFem* New();
43
+
44
+		void Delete();
45
+
46
+	// ====================  OPERATORS     =======================
47
+
48
+	// ====================  OPERATIONS    =======================
49
+
50
+		/// Make the forward model calculation
51
+		void MakeCalculation();
52
+
53
+		/// Forward model from a vector of inputs
54
+		void ForwardModelProfile();
55
+
56
+	// ====================  ACCESS        =======================
57
+	//
58
+		/// Set layered earth model
59
+		void EMEarthModel(LayeredEarthEM* Earth);
60
+
61
+		/// Set dipole source
62
+		void SetDipoleSource(DipoleSource* dipolesource);
63
+
64
+		/// Set Field Points
65
+		void SetReceiverPoints(ReceiverPoints* receiver);
66
+
67
+		/// Copy parameters from data object
68
+		void AlignWithData(DataFEM* inpdata);
69
+
70
+		/// Set a data object for output
71
+		void SetOutputData(DataFEM* outputdata);
72
+
73
+
74
+
75
+	// ====================  INQUIRY       =======================
76
+
77
+
78
+	protected:
79
+
80
+	// ====================  LIFECYCLE     =======================
81
+
82
+		/// Default protected constructor.
83
+		InstrumentFem (const std::string &name);
84
+
85
+		/// Default protected constructor.
86
+		~InstrumentFem ();
87
+
88
+		void Release();
89
+
90
+	// ====================  DATA MEMBERS  =========================
91
+
92
+	LayeredEarthEM* EarthModel;
93
+
94
+	DipoleSource* Dipole;
95
+
96
+	ReceiverPoints* Receiver;
97
+
98
+	DataFEM* InputData;
99
+
100
+	DataFEM* OutputData;
101
+
102
+	/// Vector of dipole sources - may be superceded by boost
103
+	std::vector<DipoleSource*> Transmitters;
104
+
105
+	/// Vector of receivers - may be superceded by boost
106
+	/// not necessary--one set of receivers for all dipoles,
107
+	/// except the number of frequencies is built into the receiver
108
+	std::vector<ReceiverPoints*> Receivers;
109
+
110
+	/// Vector of Earth Models - may be superceded by boost
111
+	//std::vector<LayeredEarthEM*> EarthModels;
112
+
113
+	/// Number of frequencies
114
+	int nFreq;
115
+
116
+	/// Number of observation locations
117
+	int nObs;
118
+
119
+	/// Array of frequencies
120
+	VectorXr freq;
121
+
122
+	/// Position vector, with z as height above the ground surface (pos)
123
+	Vector3Xr xyz;
124
+
125
+	/// Array of Tx orientations (x,y,z) for each freq
126
+	Eigen::Matrix<ORIENTATION,Eigen::Dynamic,1> TxOrientation;
127
+
128
+	/// Array of Rx orientations (x,y,z) for each freq
129
+	Eigen::Matrix<ORIENTATION,Eigen::Dynamic,1> RxOrientation;
130
+
131
+	/// Transmitter moments, one for each frequency
132
+	VectorXr TxMom;
133
+
134
+	/// Tx/Rx Separation in local, right hand system with x aligned with flight
135
+	Vector3Xr TxRxSep;
136
+
137
+	/// Scale factor as described in EM1DFM manual
138
+	VectorXr ScaleFac;
139
+
140
+	private:
141
+
142
+}; // -----  end of class  InstrumentFem  -----
143
+} // end of namespace Lemma
144
+#endif

+ 213
- 0
LemmaCore/include/instrumenttem.h View File

@@ -0,0 +1,213 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     02/10/2011
11
+  @version  $Id: instrumenttem.h 201 2015-01-03 00:07:47Z tirons $
12
+ **/
13
+
14
+#ifndef __INSTRUMENTTEM_H
15
+#define __INSTRUMENTTEM_H
16
+
17
+#include "instrument.h"
18
+#include "emearth1d.h"
19
+#include "WireAntenna.h"
20
+#include "PolygonalWireAntenna.h"
21
+#include "receiverpoints.h"
22
+#include "dipolesource.h"
23
+#include "layeredearthem.h"
24
+#include "digitalfiltercostrans.h"
25
+#include "digitalfiltersintrans.h"
26
+#include "temintegrationkernel.h"
27
+#include "CubicSplineInterpolator.h"
28
+
29
+namespace Lemma {
30
+
31
+enum ReceiverType { INDUCTIVE, MAGNETOMETER, ELECTRIC };
32
+
33
+// ===================================================================
34
+//        Class:  InstrumentTem
35
+/// \brief  TEM Instrument Class
36
+/// \details Provides utility to forward model TEM data in Lemma.
37
+// ===================================================================
38
+class InstrumentTem : public Instrument {
39
+
40
+	friend std::ostream &operator<<(std::ostream &stream,
41
+		const InstrumentTem &ob);
42
+
43
+	public:
44
+
45
+	// ====================  LIFECYCLE     =======================
46
+
47
+		static InstrumentTem* New();
48
+
49
+		void Delete();
50
+
51
+	// ====================  OPERATORS     =======================
52
+
53
+	// ====================  OPERATIONS    =======================
54
+
55
+		/// Perform the forward model calculation
56
+		void MakeDirectCalculation( const HANKELTRANSFORMTYPE& hType );
57
+
58
+        /** Perform the forward model calculation, use lagged convolutions to
59
+         *  speed up the calculations
60
+         */
61
+		void MakeLaggedCalculation( const HANKELTRANSFORMTYPE& hType );
62
+
63
+	// ====================  ACCESS        =======================
64
+
65
+		/** Sets pulse parameters as a linearly segmented graph, so
66
+         *  for example a triangle wave needs three points in Amps and
67
+         *  times, a trapazoidal needs for. The pulse is assumed (defaults) to be
68
+         *  bipolar, only the positive polarity should be specified.
69
+         *  @param[in] Amp is the waveform current in Amps
70
+         *  @param[in] times are the abscissa values of the waveform
71
+         *  @param[in] bipolar specifies whether or not the pulse is bipolar
72
+         */
73
+		void SetPulse( const VectorXr& Amp, const VectorXr& times, bool bipolar=true );
74
+
75
+		/// Sets layered earth model
76
+		void EMEarthModel(LayeredEarthEM* Earth);
77
+
78
+		/// Sets transmitter parameters
79
+		void SetTransmitLoop(WireAntenna *antennae);
80
+
81
+		/// Sets dipole source parameters
82
+		void SetDipoleSource(DipoleSource* dipolesource);
83
+
84
+		/// Sets receiver points and parameters
85
+		void SetReceiver(ReceiverPoints* Receivers);
86
+
87
+        /** Sets the type of receiver/measurement
88
+         */
89
+        void SetReceiverType( const ReceiverType& rtype  );
90
+
91
+		/// Return calculated data
92
+		MatrixXr GetMeasurements();
93
+
94
+		/**
95
+            Set time gates, assumes gates widths are delta (instantaneous)
96
+            @param[in] times gate centres units are in seconds
97
+         */
98
+
99
+		void SetTimes(const VectorXr &times);
100
+
101
+        /** Sets time gates centres and widths, both in seconds. The window is assumed to be
102
+         *  a simple boxcar. Simpson's rule is used to integrate the response
103
+         * @param[in] times gate centres units are in seconds
104
+         * @param[in] widths gate widths units are in seconds
105
+         */
106
+        void SetTimeGates(const VectorXr &centres, const VectorXr& widths);
107
+
108
+		/// Get number of times
109
+		int GetNumberOfTimes();
110
+
111
+        /** Sets reference time for time gate to pulse time offset.
112
+         */
113
+        void SetReferenceTime(const Real& RefTime);
114
+
115
+		/// Attach EMEarth1D
116
+		//void AttachEMEarth1D(EMEarth1D *EMEarth);
117
+
118
+	// ====================  INQUIRY       =======================
119
+
120
+
121
+
122
+	protected:
123
+
124
+	// ====================  LIFECYCLE     =======================
125
+
126
+		/// Default protected constructor.
127
+		InstrumentTem (const std::string &name);
128
+
129
+		/// Default protected constructor.
130
+		~InstrumentTem ();
131
+
132
+		void Release();
133
+
134
+    // ====================  OPERATIONS    =======================
135
+
136
+        /**
137
+         *  Converts impulse B response (step db/dt) into inductive db/dt
138
+         *  response for general waveform.
139
+         */
140
+        void FoldAndConvolve( CubicSplineInterpolator* Spline );
141
+
142
+        /** Convolves the transmitter waveform(s), takes the impulse response
143
+            and uses simpson's rule to evaluate the integral.
144
+            @param[in] Spline is the Cubic Spline object representing the solution.
145
+            @param[in] t is the evaluation time.
146
+         */
147
+        Real ConvolveWaveform( CubicSplineInterpolator* Spline, const Real& t );
148
+
149
+        /** Subtracts previous waveform(s) from current impulse response, and re-splines.
150
+         */
151
+        void SubtractPrevious( CubicSplineInterpolator* Spline );
152
+
153
+
154
+	// ====================  DATA MEMBERS  =========================
155
+
156
+		//EMEarth1D* EmEarth;
157
+
158
+		WireAntenna* Antenna;
159
+
160
+		ReceiverPoints* Receiver;
161
+
162
+		LayeredEarthEM* EarthMod;
163
+
164
+		DipoleSource* Dipole;
165
+
166
+        bool     bipolarWaveform;
167
+
168
+        /** Number of previous pules to model */
169
+        int      NPreviousPulse;
170
+
171
+        /** Reference time (relative to pulse abscissa) for time gates */
172
+        Real     RefTime;
173
+
174
+        /** Pulse period, if bimodal 1/2 repitition period */
175
+        Real     PulseT;
176
+
177
+        /** Transmitter repitition frequency */
178
+        Real     TxFreq;
179
+
180
+        /** Receiver type */
181
+        ReceiverType  RType;
182
+
183
+        MatrixXr ModelledData;
184
+
185
+        /** Centre of time gate */
186
+		VectorXr TimeGates;
187
+
188
+        /** Width of time gates */
189
+        VectorXr GateWidths;
190
+
191
+        /** Pulse waveform */
192
+        VectorXr Waveform;
193
+
194
+        /** Current Amplitude of pulse */
195
+        VectorXr  TxAmp;
196
+
197
+        /** Current -delta of pulse */
198
+        VectorXr  TxDelta;
199
+
200
+        /** Current derivative of pulse */
201
+        VectorXr  TxDiff;
202
+
203
+        /** times associated with TxAmp segments */
204
+        VectorXr  TxAbs;
205
+
206
+	private:
207
+
208
+}; // -----  end of class  InstrumentTem  -----
209
+
210
+} // End of namespace Lemma
211
+
212
+#endif // __TEMINSTRUMENT_H
213
+

+ 92
- 0
LemmaCore/include/integrationkernel.h View File

@@ -0,0 +1,92 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     02/07/2011
11
+  @version  $Id: integrationkernel.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  INTEGRATIONKERNEL_INC
15
+#define  INTEGRATIONKERNEL_INC
16
+
17
+#include "LemmaObject.h"
18
+
19
+namespace Lemma {
20
+
21
+    // ===================================================================
22
+    //  Class:  IntegrationKernel
23
+    /**
24
+      @class
25
+      \brief    Abstract class that computes arguments for numerical
26
+                integrators.
27
+      \details  Needs to provide Argument function, as well as be able to
28
+                set necessary integration parameters.
29
+     */
30
+    // ===================================================================
31
+    template <typename T>
32
+    class IntegrationKernel : public LemmaObject {
33
+
34
+        public:
35
+
36
+            // ====================  LIFECYCLE     =======================
37
+
38
+
39
+            // ====================  OPERATORS     =======================
40
+
41
+            // ====================  OPERATIONS    =======================
42
+
43
+            /** Returns the argument of a function at a given argument. Also
44
+             *  capable or returning related function values.
45
+             */
46
+            //template <typename T>
47
+            virtual T Argument(const Real& x, const int& iRelated)=0;
48
+
49
+            // ====================  ACCESS        =======================
50
+
51
+            // ====================  INQUIRY       =======================
52
+
53
+            virtual int GetNumRel()=0;
54
+
55
+        protected:
56
+
57
+            // ====================  LIFECYCLE     =======================
58
+
59
+            /// Default protected constructor.
60
+            IntegrationKernel (const std::string& name);
61
+
62
+            /// Default protected constructor.
63
+            ~IntegrationKernel ();
64
+
65
+            // ====================  DATA MEMBERS  =========================
66
+
67
+        private:
68
+
69
+    }; // -----  end of class  IntegrationKernel  -----
70
+
71
+    template <typename T>
72
+    IntegrationKernel<T>::IntegrationKernel(const std::string& name) :
73
+        LemmaObject(name) {
74
+    }
75
+
76
+    template<typename T>
77
+    IntegrationKernel<T>::~IntegrationKernel( ) {
78
+    }
79
+
80
+//     template <typename T>
81
+//     T IntegrationKernel<T>::Argument(const Real& x, const int& iRelated) {
82
+//         return 11.;
83
+//     }
84
+//
85
+//     template <typename T>
86
+//     int IntegrationKernel<T>::GetNumRel( ) {
87
+//         return 0;
88
+//     }
89
+
90
+}		// -----  end of Lemma  name  -----
91
+
92
+#endif   // ----- #ifndef INTEGRATIONKERNEL_INC  -----

+ 66
- 0
LemmaCore/include/integrator.h View File

@@ -0,0 +1,66 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     02/07/2011
11
+  @version  $Id: integrator.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  INTEGRATOR_INC
15
+#define  INTEGRATOR_INC
16
+
17
+#include "LemmaObject.h"
18
+
19
+namespace Lemma {
20
+
21
+    // ===================================================================
22
+    //  Class:  Integrator
23
+    /**
24
+      @class
25
+      \brief
26
+      \details
27
+     */
28
+    // ===================================================================
29
+    class Integrator : public LemmaObject {
30
+
31
+        /// Prints out basic info about the class
32
+        friend std::ostream &operator<<(std::ostream &stream,
33
+                        const Integrator &ob);
34
+
35
+        public:
36
+
37
+            // ====================  LIFECYCLE     =======================
38
+
39
+            // ====================  OPERATORS     =======================
40
+
41
+            // ====================  OPERATIONS    =======================
42
+
43
+            // ====================  ACCESS        =======================
44
+
45
+            // ====================  INQUIRY       =======================
46
+
47
+        protected:
48
+
49
+            // ====================  LIFECYCLE     =======================
50
+
51
+            /// Default protected constructor.
52
+            Integrator (const std::string& name);
53
+
54
+            /// Default protected constructor.
55
+            ~Integrator ();
56
+
57
+            // ====================  DATA MEMBERS  =========================
58
+
59
+        private:
60
+
61
+    }; // -----  end of class  Integrator  -----
62
+
63
+}		// -----  end of Lemma  name  -----
64
+
65
+#endif   // ----- #ifndef INTEGRATOR_INC  -----
66
+

+ 118
- 0
LemmaCore/include/inversesolver.h View File

@@ -0,0 +1,118 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     07/14/2010
11
+  @version  $Id: inversesolver.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  INVERSESOLVER_H_INC
15
+#define  INVERSESOLVER_H_INC
16
+
17
+#include "LemmaObject.h"
18
+#include "data.h"
19
+#include "instrument.h"
20
+#include "octreegrid.h"
21
+
22
+namespace Lemma {
23
+
24
+
25
+    // ===================================================================
26
+    //  Class:  InverseSolver
27
+    /**
28
+      @class  InverseSolver
29
+      \brief   Abstract class for inverse problem solver.
30
+      \details General solution of inverse problems.
31
+     */
32
+    // ===================================================================
33
+    class InverseSolver : public LemmaObject {
34
+
35
+        friend  std::ostream &operator<<(std::ostream &stream,
36
+                const InverseSolver &ob);
37
+
38
+        friend class OctreeGrid;
39
+
40
+        public:
41
+
42
+            // ====================  LIFECYCLE     =======================
43
+
44
+            // ====================  OPERATORS     =======================
45
+
46
+            // ====================  OPERATIONS    =======================
47
+
48
+            // ====================  ACCESS        =======================
49
+
50
+            /** @brief Sets the obsered data, any instance of Data.
51
+             *  @details This may either be field data, or forward modelled
52
+             *  data.
53
+             *  @param[in] ObsData a pointer to the observed data class.
54
+             */
55
+            void SetObservedData(Data* ObsData);
56
+
57
+            /** @brief Sets the instument that is used to create the data.
58
+             *  @details This is used for all forward modelling.
59
+             *  @param[in] inst is a pointer to the instrument class.
60
+             */
61
+            void SetInstrument(Instrument* inst);
62
+
63
+            /** @brief Returns the predicted data.
64
+             *  @return a pointer to the predicted data.
65
+             */
66
+            Data* GetPredictedData();
67
+
68
+            // ====================  INQUIRY       =======================
69
+
70
+            /** Returns the number of iterations it took to converge to a
71
+             *  solution.
72
+             */
73
+            virtual int NumberOfIterations()=0;
74
+
75
+            /** Returns true if the inversion converged successfully.
76
+             */
77
+            virtual bool Success()=0;
78
+
79
+            /** Returns a vector of \f$ \phi_M \f$
80
+             */
81
+            virtual VectorXr GetPhiMVector()=0;
82
+
83
+            /** Returns a vector of \f$ \phi_D \f$
84
+             */
85
+            virtual VectorXr GetPhiDVector()=0;
86
+
87
+        protected:
88
+
89
+            // ====================  OPERATIONS    =======================
90
+
91
+            /// Used as a callback function from iterating mesh.
92
+            virtual void FillInG(const Vector3r& pos, const Vector3r& step)=0;
93
+
94
+            // ====================  LIFECYCLE     =======================
95
+
96
+            /// Default protected constructor.
97
+            InverseSolver (const std::string &name);
98
+
99
+            /// Default protected constructor.
100
+            ~InverseSolver ();
101
+
102
+            // ====================  DATA MEMBERS  =========================
103
+
104
+            /// The Observed Data
105
+            Data* ObservedData;
106
+
107
+            /// The Predicted Data
108
+            Data* PredictedData;
109
+
110
+            /// Instrument that makes the data
111
+            Instrument*            ModelInstrument;
112
+
113
+        private:
114
+
115
+    }; // -----  end of class  InverseSolver  -----
116
+}		// -----  end of Lemma  name  -----
117
+
118
+#endif   // ----- #ifndef INVERSESOLVER_H_INC  -----

+ 146
- 0
LemmaCore/include/inversesolvertem1d.h View File

@@ -0,0 +1,146 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     03/23/2011
11
+  @version  $Id: inversesolvertem1d.h 201 2015-01-03 00:07:47Z tirons $
12
+ **/
13
+
14
+#ifndef _INVERSESOLVERTEM1D__H
15
+#define _INVERSESOLVERTEM1D__H
16
+
17
+#include "inversesolver.h"
18
+#include "layeredearthem.h"
19
+#include "WireAntenna.h"
20
+#include "dipolesource.h"
21
+#include "receiverpoints.h"
22
+#include "instrumenttem.h"
23
+#include "cg.h"
24
+
25
+namespace Lemma {
26
+	// ===================================================================
27
+	//        Class:  InverseSolverTEM1D
28
+	/// \brief  Inversion for 1D TEM data
29
+	/// \details
30
+	// ===================================================================
31
+	class InverseSolverTEM1D : public InverseSolver {
32
+
33
+		friend std::ostream &operator<<(std::ostream &stream,
34
+			const InverseSolverTEM1D &ob);
35
+
36
+		public:
37
+
38
+		// ====================  LIFECYCLE     =======================
39
+
40
+		static InverseSolverTEM1D* New();
41
+
42
+		void Delete();
43
+
44
+		// ====================  OPERATORS     =======================
45
+
46
+		// ====================  OPERATIONS    =======================
47
+
48
+		/// Perform the inverse calculation
49
+		void Calculate();
50
+
51
+		// ====================  ACCESS        =======================
52
+
53
+		/// Attach starting model
54
+		void AttachStartMod(LayeredEarthEM* inpstartmod);
55
+
56
+		/// Attach recovered model
57
+		void AttachRecMod(LayeredEarthEM* inprecmod);
58
+
59
+		/// Attach wire antenna source
60
+		void AttachWireAntenna(WireAntenna* inpwireantenna);
61
+
62
+		/// Attach dipole source
63
+		void AttachDipoleSource(DipoleSource* inpdipsource);
64
+
65
+		/// Attach receiver points
66
+		void AttachReceiver(ReceiverPoints* inpreceiver);
67
+
68
+		/// Set the time gates
69
+		void SetTimes(VectorXr &inptimes);
70
+
71
+		/// Show forward modelled data
72
+		void ShowSoln();
73
+
74
+		/// Write recovered model to file
75
+		void WriteSoln(const std::string &filename);
76
+
77
+		/// Set free parameter indices: layer, conductivity
78
+		void SetFreeParams(const VectorXi &layers, const VectorXi &cond);
79
+
80
+		/// Attach measured data for misfit comparison
81
+		void AttachMeasuredData(const MatrixXr &data);
82
+
83
+		// ====================  INQUIRY       =======================
84
+		/// Report number of iterations
85
+		int NumberOfIterations();
86
+
87
+		/// Report success/failure
88
+		bool Success();
89
+
90
+		/// Return phi m vector
91
+		VectorXr GetPhiMVector();
92
+
93
+		/// Return phi d vector
94
+		VectorXr GetPhiDVector();
95
+
96
+
97
+		protected:
98
+
99
+		/// Some crap trevor uses
100
+		void FillInG(const Vector3r& pos, const Vector3r& step);
101
+
102
+		/// Calculate Jacobian
103
+		MatrixXr CalcJac(LayeredEarthEM* m0);
104
+
105
+		// ====================  LIFECYCLE     =======================
106
+
107
+		/// Default protected constructor.
108
+		InverseSolverTEM1D (const std::string &name);
109
+
110
+		/// Default protected constructor.
111
+		~InverseSolverTEM1D ();
112
+
113
+        void Release();
114
+
115
+		// ====================  DATA MEMBERS  =========================
116
+
117
+		WireAntenna* Antenna;
118
+
119
+		DipoleSource* Dipole;
120
+
121
+		ReceiverPoints* Receiver;
122
+
123
+		LayeredEarthEM* StartingMod;
124
+
125
+		LayeredEarthEM* RecoveredMod;
126
+
127
+		InstrumentTem *InstrumentFor;
128
+
129
+		MatrixXr MeasuredData;
130
+
131
+		VectorXr Times;
132
+
133
+		/// Vector of indices for which layer conductivities are solved for
134
+		VectorXi SCondIndex;
135
+
136
+		/// Vecor of indices for which layer thicknesses are solved for
137
+		VectorXi SThickIndex;
138
+
139
+		/// Temporary vector for returning linearised step
140
+		VectorXr RecModStep;
141
+
142
+		private:
143
+
144
+}; // -----  end of class  InverseSolverTEM1D  -----
145
+} // End of namespace Lemma
146
+#endif // _INVERSESOLVERTEM1D__H

+ 85
- 0
LemmaCore/include/kernel.h View File

@@ -0,0 +1,85 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     01/29/2010
11
+  @version  $Id: kernel.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef __kernel_h
15
+#define __kernel_h
16
+
17
+#ifdef LEMMAUSEVTK
18
+#include "vtkImplicitFunction.h"
19
+#endif
20
+
21
+#include "LemmaObject.h"
22
+#include "receivercubes.h"
23
+
24
+namespace Lemma {
25
+
26
+        // ==================================================================
27
+        //        Class:  Kernel
28
+        /// \brief Pure abstract class for some kind of kernel function.
29
+        /// \details Provides a consistent interface to kernel functions.
30
+        // ==================================================================
31
+        class Kernel : public LemmaObject {
32
+
33
+            /// Prints out basic info about the class
34
+            friend std::ostream &operator<<(std::ostream &stream,
35
+                        const Kernel &ob);
36
+
37
+            public:
38
+
39
+                // ====================  LIFECYCLE     ======================
40
+
41
+                //static Kernel* New();
42
+
43
+                virtual void Delete()=0;
44
+
45
+                // ====================  OPERATORS     ======================
46
+
47
+                // ====================  OPERATIONS    ======================
48
+
49
+                // ====================  ACCESS        ======================
50
+
51
+                // ====================  INQUIRY       ======================
52
+
53
+                virtual VectorXcr ComputeSensitivity()=0;
54
+
55
+                #ifdef LEMMAUSEVTK
56
+                virtual VectorXcr ComputeSensitivity(vtkImplicitFunction* Impl)=0;
57
+                #endif
58
+
59
+                /** computes sensitivity for same value */
60
+                virtual VectorXcr ComputeSensitivity(const Real& fval)=0;
61
+
62
+                /** Computes sensitivity for array of values */
63
+                virtual VectorXcr ComputeSensitivity(const VectorXr& fval)=0;
64
+
65
+                virtual void SetFieldCubes(ReceiverCubes* pts)=0;
66
+
67
+                // ====================  DATA MEMBERS  ======================
68
+
69
+            protected:
70
+
71
+                // ====================  LIFECYCLE     ======================
72
+
73
+                /// Default protected constructor.
74
+                Kernel (const std::string& name);
75
+
76
+                /// Default protected constructor.
77
+                ~Kernel ();
78
+
79
+        private:
80
+
81
+    }; // -----  end of class  Kernel  -----
82
+
83
+}
84
+
85
+#endif // __kernel_h

+ 111
- 0
LemmaCore/include/kernelem1dbase.h View File

@@ -0,0 +1,111 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+
10
+  @author   Trevor Irons
11
+  @date     05/18/2012
12
+  @version  $Id: kernelem1dbase.h 193 2014-11-10 23:51:41Z tirons $
13
+ **/
14
+
15
+#ifndef  KERNELEM1DBASE_INC
16
+#define  KERNELEM1DBASE_INC
17
+
18
+#include "LemmaObject.h"
19
+
20
+namespace Lemma {
21
+
22
+    // Transverse electric or magnetic mode
23
+    enum EMMODE {TM, TE, NONE};
24
+
25
+    // ===================================================================
26
+    //  Class:  KernelEm1DBase
27
+    /**
28
+      @class
29
+      \brief   Pure virtual base class of KernelEm1D
30
+      \details Defines interface for HankelTransform classes
31
+     */
32
+    // ===================================================================
33
+    class KernelEm1DBase : public LemmaObject {
34
+
35
+        friend class KernelEM1DManager;
36
+
37
+        public:
38
+
39
+            // ====================  LIFECYCLE     =======================
40
+
41
+            // ====================  OPERATORS     =======================
42
+
43
+            // ====================  OPERATIONS    =======================
44
+
45
+            /** Returns the Complex bessel argument to be evaluated for a given
46
+			 * lambda value
47
+             */
48
+            virtual Complex BesselArg(const Real& lambda)=0;
49
+
50
+            /** Returns the complex bessel argument. Same as above, but does not
51
+             *  call reflection coefficient calculation in KernelEM1DReflBase.
52
+             *  @param[in] lambda is the hankel wave value.
53
+             */
54
+            virtual Complex RelBesselArg(const Real& lambda)=0;
55
+
56
+            // ====================  ACCESS        =======================
57
+            virtual void SetIk(const int& ik)=0;
58
+
59
+            virtual void SetMode(const EMMODE& mode)=0;
60
+
61
+            int GetManagerIndex() {
62
+                return this->managerIdx;
63
+            }
64
+
65
+            // ====================  INQUIRY       =======================
66
+            virtual int GetNumRel()=0;
67
+
68
+            virtual int GetBesselOrder()=0;
69
+
70
+            virtual Complex GetZm()=0;
71
+
72
+            virtual Complex GetYm()=0;
73
+
74
+            virtual Complex GetZs()=0;
75
+
76
+            virtual Complex GetKs()=0;
77
+
78
+        protected:
79
+
80
+            // ====================  LIFECYCLE     =======================
81
+
82
+            /// Default protected constructor.
83
+            KernelEm1DBase (const std::string& name) : LemmaObject(name)
84
+            {
85
+            }
86
+
87
+            /// Default protected constructor.
88
+            ~KernelEm1DBase () {
89
+                if (this->NumberOfReferences > 0)
90
+                    throw DeleteObjectWithReferences( this );
91
+            }
92
+
93
+            void Release() {
94
+                delete this;
95
+            }
96
+
97
+            // ====================  OPERATIONS    =======================
98
+
99
+
100
+            // ====================  DATA MEMBERS  =========================
101
+
102
+            /** Where does this kernel live on the vector managed by the manager */
103
+            int  managerIdx;
104
+
105
+        private:
106
+
107
+    }; // -----  end of class  KernelEm1DBase  -----
108
+
109
+} // namespace Lemma
110
+
111
+#endif   // ----- #ifndef KERNELEM1DBASE_INC  -----

+ 217
- 0
LemmaCore/include/kernelem1dmanager.h View File

@@ -0,0 +1,217 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     06/26/2012
11
+  @version   0.0
12
+ **/
13
+
14
+#ifndef  KERNELEM1DMANAGER_INC
15
+#define  KERNELEM1DMANAGER_INC
16
+
17
+//#include "dipolesource.h"
18
+//#include "kernelem1dreflbase.h"
19
+#include "kernelem1dbase.h"
20
+#include "kernelem1dspec.h"
21
+
22
+namespace Lemma {
23
+
24
+    class DipoleSource;
25
+    class KernelEM1DReflBase;
26
+
27
+    // ===================================================================
28
+    //  Class:  KernelEM1DManager
29
+    /**
30
+      @class
31
+      \brief
32
+      \details
33
+     */
34
+    // ===================================================================
35
+    class KernelEM1DManager : public LemmaObject {
36
+
37
+        public:
38
+
39
+            friend std::ostream &operator<<(std::ostream &stream,
40
+                        const KernelEM1DManager &ob);
41
+
42
+            // ====================  LIFECYCLE     =======================
43
+
44
+            /** Returns a pointer to a new object of type KernelEM1DManager.
45
+             * It allocates all necessary memory.
46
+             */
47
+            static KernelEM1DManager* New();
48
+
49
+            /** Deletes this object. Delete also disconnects any
50
+             * attachments to this object.
51
+             */
52
+            void Delete();
53
+
54
+            // ====================  OPERATORS     =======================
55
+
56
+            // ====================  OPERATIONS    =======================
57
+
58
+            template<EMMODE Mode, int Ikernel, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
59
+            int AddKernel( );
60
+            /*
61
+            {
62
+
63
+                KernelEm1DSpec<Mode, Ikernel, Isource, Irecv>* NewKern =
64
+                    KernelEm1DSpec<Mode, Ikernel, Isource, Irecv>::New();
65
+                KernelVec.push_back( NewKern );
66
+                NewKern->managerIdx = KernelVec.size()-1;
67
+                switch (Mode) {
68
+                    case TE:
69
+                        if (TEReflBase == NULL) {
70
+                            TEReflBase = KernelEM1DReflSpec<TE, Isource, Irecv>::New();
71
+                            TEReflBase->Initialise(Earth);
72
+                            TEReflBase->SetUpSource(Dipole, ifreq);
73
+                            TEReflBase->SetUpReceiver( rx_z );
74
+                        }
75
+                        NewKern->SetReflBase(TEReflBase);
76
+                        break;
77
+                    case TM:
78
+                        if (TMReflBase == NULL) {
79
+                            TMReflBase = KernelEM1DReflSpec<TM, Isource, Irecv>::New();
80
+                            TMReflBase->Initialise(Earth);
81
+                            TMReflBase->SetUpSource(Dipole, ifreq);
82
+                            TMReflBase->SetUpReceiver( rx_z );
83
+                        }
84
+                        NewKern->SetReflBase(TMReflBase);
85
+                        break;
86
+                }
87
+                return static_cast<int>(KernelVec.size()-1);
88
+            }
89
+            */
90
+
91
+            void ResetSource(const int& ifreq);
92
+
93
+            /** For use in related Kernel calculations. This function calles
94
+             * ComputeReflectionCoeffs on TEReflBase and TMReflBase, if they
95
+             * exist. After this has been called, KernelEM1DBase::RelBesselArg() may be safely
96
+             * called. This method stores solutions of the same idx. rho0 is the intial lambda argument
97
+             */
98
+            void ComputeReflectionCoeffs(const Real& lambda, const int& idx, const Real& rho0);
99
+
100
+            /** Clears the vector of kernels */
101
+            void ClearVec() {
102
+                for (unsigned int ik=0; ik<this->KernelVec.size(); ++ik) {
103
+                    this->KernelVec[ik]->Delete();
104
+                }
105
+                KernelVec.clear();
106
+            }
107
+
108
+            // ====================  ACCESS        =======================
109
+
110
+            /** Sets the LayeredEarthEM class that will be used by the kernels.
111
+             */
112
+            void SetEarth( LayeredEarthEM*   Earth);
113
+
114
+            /** Sets the source of the kernels */
115
+            void SetDipoleSource( DipoleSource*   Dipole, const int& ifreq, const Real& rx_zin);
116
+
117
+            /** Returns pointer to specified kernel indice. Indices are assigned in the same
118
+                order as they are created by AddKernel.
119
+             */
120
+            KernelEm1DBase*    GetKernel(const unsigned int& ik);
121
+
122
+            /** Returns pointer to connected dipole.
123
+             */
124
+            DipoleSource*    GetDipole( );
125
+
126
+            inline std::vector<KernelEm1DBase*>  GetSTLVector() {
127
+                return KernelVec;
128
+            }
129
+
130
+            // ====================  INQUIRY       =======================
131
+
132
+        protected:
133
+
134
+            // ====================  LIFECYCLE     =======================
135
+
136
+            /** Default protected constructor. */
137
+            KernelEM1DManager (const std::string& name);
138
+
139
+            /** Default protected constructor. */
140
+            ~KernelEM1DManager ();
141
+
142
+            /**
143
+             * @copybrief LemmaObject::Release()
144
+             * @copydetails LemmaObject::Release()
145
+             */
146
+            void Release();
147
+
148
+            // ====================  DATA MEMBERS  =========================
149
+
150
+            /** List of KernelEm1D instances */
151
+            std::vector<KernelEm1DBase*>           KernelVec;
152
+
153
+            /** Reflection base used for TE mode */
154
+            KernelEM1DReflBase*                    TEReflBase;
155
+
156
+            /** Reflection base used for TM mode */
157
+            KernelEM1DReflBase*                    TMReflBase;
158
+
159
+            /** EmEarth Class */
160
+            LayeredEarthEM*                        Earth;
161
+
162
+            /** EM dipole souce */
163
+            DipoleSource*                          Dipole;
164
+
165
+            /** Frequency index for the sources */
166
+            int                                    ifreq;
167
+
168
+            /** Receiver height */
169
+            Real                                   rx_z;
170
+
171
+        private:
172
+
173
+    }; // -----  end of class  KernelEM1DManager  -----
174
+
175
+    // template methods
176
+    template<EMMODE Mode, int Ikernel, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
177
+    int KernelEM1DManager::AddKernel( ) {
178
+
179
+        KernelEm1DSpec<Mode, Ikernel, Isource, Irecv>* NewKern =
180
+                    KernelEm1DSpec<Mode, Ikernel, Isource, Irecv>::New();
181
+        KernelVec.push_back( NewKern );
182
+        NewKern->managerIdx = KernelVec.size()-1;
183
+        switch (Mode) {
184
+            case TE:
185
+                if (TEReflBase == NULL) {
186
+                    TEReflBase = KernelEM1DReflSpec<TE, Isource, Irecv>::New();
187
+                    TEReflBase->Initialise(Earth);
188
+                    TEReflBase->SetUpSource(Dipole, ifreq);
189
+                    TEReflBase->SetUpReceiver( rx_z );
190
+                }
191
+                NewKern->SetReflBase(TEReflBase);
192
+                break;
193
+            case TM:
194
+                if (TMReflBase == NULL) {
195
+                    TMReflBase = KernelEM1DReflSpec<TM, Isource, Irecv>::New();
196
+                    TMReflBase->Initialise(Earth);
197
+                    TMReflBase->SetUpSource(Dipole, ifreq);
198
+                    TMReflBase->SetUpReceiver( rx_z );
199
+                }
200
+                NewKern->SetReflBase(TMReflBase);
201
+                break;
202
+        }
203
+        return static_cast<int>(KernelVec.size()-1);
204
+     }
205
+
206
+
207
+//     /** Clears the vector of kernels */
208
+//     void ClearVec() {
209
+//         for (unsigned int ik=0; ik<this->KernelVec.size(); ++ik) {
210
+//             this->KernelVec[ik]->Delete();
211
+//         }
212
+//         KernelVec.clear();
213
+//     }
214
+
215
+}		// -----  end of Lemma  name  -----
216
+
217
+#endif   // ----- #ifndef KERNELEM1DMANAGER_INC  -----

+ 253
- 0
LemmaCore/include/kernelem1dreflbase.h View File

@@ -0,0 +1,253 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     05/18/2012
11
+  @version  $Id: kernelem1dreflbase.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  KERNELEM1DREFLBASE_INC
15
+#define  KERNELEM1DREFLBASE_INC
16
+
17
+#include "dipolesource.h"
18
+#include "kernelem1dbase.h"
19
+#include "layeredearthem.h"
20
+//#include "kernelem1dspec.h"
21
+
22
+namespace Lemma {
23
+
24
+    //class DipoleSource;
25
+
26
+    enum DIPOLE_LOCATION { INAIR, INGROUND };
27
+
28
+    // forward declaration for friend
29
+    template<EMMODE Mode, int Ikernel, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
30
+    class KernelEm1DSpec;
31
+
32
+
33
+    // ===================================================================
34
+    //  Class:  KernelEM1DReflBase
35
+    /**
36
+      @class
37
+      \brief   Abstract class defining EM1DRefl class.
38
+      \details Derived classes are template specialized for optimal performance.
39
+     */
40
+    // ===================================================================
41
+    class KernelEM1DReflBase : public LemmaObject {
42
+
43
+        template<EMMODE Mode, int Ikernel, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
44
+        friend class KernelEm1DSpec;
45
+        friend class KernelEM1DManager;
46
+
47
+        public:
48
+
49
+            // ====================  LIFECYCLE     =======================
50
+
51
+            // ====================  OPERATORS     =======================
52
+
53
+            // ====================  OPERATIONS    =======================
54
+
55
+            void Initialise(LayeredEarthEM* EarthIn) {
56
+
57
+                nlay = EarthIn->GetNumberOfLayers();
58
+                zh = VectorXcr::Zero(nlay);
59
+                yh = VectorXcr::Zero(nlay);
60
+                u = VectorXcr::Zero(nlay);
61
+                cf = VectorXcr::Zero(nlay);    // nlay -1 (lay 0 empty)
62
+                rtu = VectorXcr::Zero(nlay);   // nlay -1 Interfaces only
63
+                rtd = VectorXcr::Zero(nlay);   // nlay -1 Interfaces only
64
+                kk = VectorXcr::Zero(nlay);
65
+                Zyu = VectorXcr::Zero(nlay);
66
+                Zyd = VectorXcr::Zero(nlay);
67
+                Zyi = VectorXcr::Zero(nlay);
68
+                th = VectorXcr::Zero(nlay);
69
+
70
+                // Don't attach Earth, because this is performance critical.
71
+                // Everying is internal, it's OK relax Frankie
72
+                //if (Earth != NULL) {
73
+                //    Earth->DetachFrom(this);
74
+                //    Earth = NULL;
75
+                //}
76
+                //EarthIn->AttachTo(this);
77
+                Earth = EarthIn;
78
+
79
+                LayerThickness.resize(nlay);
80
+                for (int ilay=0; ilay<nlay; ++ilay) {
81
+                    LayerThickness(ilay) =  Earth->GetLayerThickness(ilay);
82
+                }
83
+
84
+                LayerDepth.resize(nlay);
85
+                for (int ilay=0; ilay<nlay; ++ilay) {
86
+                    LayerDepth(ilay) =  Earth->GetLayerDepth(ilay);
87
+                }
88
+
89
+            }
90
+
91
+            void SetUpSource(DipoleSource *Dipole, const int &ifreq) {
92
+
93
+                zh(0) = Complex(0, Dipole->GetAngularFrequency(ifreq)*MU0);
94
+                yh(0) = Complex(0, Dipole->GetAngularFrequency(ifreq)*EPSILON0);
95
+                kk(0) = -zh(0) * yh(0);
96
+
97
+                Earth->EvaluateColeColeModel(Dipole->GetAngularFrequency(ifreq));
98
+
99
+                for (int ilay=1; ilay<Earth->GetNumberOfLayers(); ++ilay) {
100
+                    zh(ilay) = zh(0) * Earth->GetLayerSusceptibility(ilay);
101
+                    yh(ilay) = Earth->GetLayerConductivity(ilay) +
102
+                            yh(0)*Earth->GetLayerPermitivity(ilay);
103
+                    kk(ilay)   = -zh(ilay)*yh(ilay);
104
+                }
105
+
106
+                tx_z = Dipole->GetLocation(2);
107
+                lays = 0;
108
+                Real Depth(0);
109
+                for (int ilay=1; ilay<nlay; ++ilay) {
110
+                    if (tx_z > Depth) {
111
+                        lays = ilay;
112
+                    }
113
+                    Depth += LayerThickness(ilay);
114
+                }
115
+            }
116
+
117
+            void SetUpReceiver(const Real &rz) {
118
+                rx_z = rz;
119
+                Real Depth(0.);
120
+                layr = 0;
121
+                for (int ilay=1; ilay<Earth->GetNumberOfLayers(); ++ilay) {
122
+                    if (rx_z > Depth) {
123
+                        layr = ilay;
124
+                    }
125
+                    Depth += LayerThickness(ilay);
126
+                }
127
+            }
128
+
129
+            // ====================  ACCESS        =======================
130
+            Complex GetYm() {
131
+                return yh(layr);
132
+            }
133
+
134
+            Complex GetZm() {
135
+                return zh(layr);
136
+            }
137
+
138
+            Complex GetZs() {
139
+                return zh(lays);
140
+            }
141
+
142
+            Complex GetKs() {
143
+                return kk(lays);
144
+            }
145
+
146
+            // ====================  INQUIRY       =======================
147
+
148
+        protected:
149
+
150
+            // ====================  LIFECYCLE     =======================
151
+
152
+            /// Default protected constructor.
153
+            KernelEM1DReflBase (const std::string& name) : LemmaObject(name)
154
+            {
155
+            }
156
+
157
+            /// Default protected constructor.
158
+            ~KernelEM1DReflBase () {
159
+                if (this->NumberOfReferences > 0)
160
+                    throw DeleteObjectWithReferences( this );
161
+            }
162
+
163
+            void Release() {
164
+                delete this;
165
+            }
166
+
167
+            // ====================  OPERATIONS    =======================
168
+
169
+            /** Computes reflection coefficients. Depending on the
170
+             * specialisation, this will either be TM or TE mode.
171
+             */
172
+            virtual void ComputeReflectionCoeffs(const Real& lambda)=0;
173
+
174
+            /** Precomputes expensive calculations that are reused by insances
175
+             * of KernelEM1DSpec in the calculation of Related potentials.
176
+             */
177
+            virtual void PreComputePotentialTerms()=0;
178
+
179
+            // ====================  DATA MEMBERS  =========================
180
+
181
+			/// Bessel order, only 0 or 1 supported
182
+			int id; // Needs to be dim nRel, or separate
183
+
184
+            /// Layer the source is in
185
+			int lays;
186
+
187
+			/// Layer the receiver is in
188
+			int layr;
189
+
190
+			/// Number of Layers
191
+			int nlay;
192
+
193
+            /// Number of Related kernels to be computed
194
+            int nRelated;
195
+
196
+            /// Used in related kernel precompute calls
197
+            int relIud;
198
+
199
+			/// Receiver z position
200
+			Real rx_z;
201
+
202
+			/// Transmitter z position
203
+			Real tx_z;
204
+
205
+            /// bessel arg squared
206
+            Real rams;
207
+
208
+            /** Related part of con term */
209
+            Complex  relCon;
210
+
211
+            Complex  relenukadz;
212
+
213
+            Complex  relexp_pbs1;
214
+
215
+            Complex  relexp_pbs2;
216
+
217
+            Complex  rel_a;
218
+
219
+			/// TM or TE mode
220
+			EMMODE mode;
221
+
222
+            /// Pointer to layered earth
223
+            LayeredEarthEM *Earth;
224
+
225
+			Complex       uk;
226
+			Complex       um;
227
+			VectorXcr     cf;  // nlay
228
+			VectorXcr      u;  // nlay
229
+			VectorXcr     yh;  // nlay
230
+			VectorXcr     zh;  // nlay
231
+			VectorXcr     kk;  // nlay
232
+			VectorXcr    Zyu;  //(nlay); //Zyu.setZero();
233
+			VectorXcr    Zyd;  //(nlay); //Zyd.setZero();
234
+			VectorXcr    Zyi;  //(nlay); //Zyi.setZero();
235
+			VectorXcr     th;  //(nlay);
236
+			VectorXr     LayerThickness;
237
+			VectorXr     LayerDepth;
238
+
239
+			/// Reflection/Transmission coeffients for upgoing waves in a
240
+			/// layered earth model
241
+			VectorXcr    rtu;
242
+
243
+			/// Reflection/Transmission coeffients for downgoing waves in
244
+			/// a layered earth model
245
+			VectorXcr    rtd;
246
+
247
+        private:
248
+
249
+    }; // -----  end of class  KernelEM1DReflBase  -----
250
+
251
+}		// -----  end of Lemma  name  -----
252
+
253
+#endif   // ----- #ifndef KERNELEM1DREFLBASE_INC  -----

+ 373
- 0
LemmaCore/include/kernelem1dreflspec.h View File

@@ -0,0 +1,373 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     05/18/2012
11
+  @version  $Id: kernelem1dreflspec.h 123 2014-02-05 23:47:20Z tirons $
12
+ **/
13
+
14
+#ifndef  KERNELEM1DREFLSPEC_INC
15
+#define  KERNELEM1DREFLSPEC_INC
16
+
17
+#include "dipolesource.h"
18
+#include "kernelem1dreflbase.h"
19
+#include "layeredearthem.h"
20
+
21
+// #include<unordered_map> // for caching results
22
+
23
+namespace Lemma {
24
+
25
+    // forward declare
26
+    //struct cache;
27
+    // Simple container to hold reflection results
28
+    struct  cache {
29
+        Real                       rho0;
30
+        Real                       lambda[805];
31
+        Real                       rams[805];
32
+        Complex                    uk[805];
33
+        Complex                    um[805];
34
+        Real                       zh0i[805];
35
+        VectorXcr                  Rtd[805];
36
+        VectorXcr                  Rtu[805];
37
+        VectorXcr                  u[805];
38
+        VectorXcr                  cf[805];
39
+        VectorXcr                  kk[805];
40
+        const Real                 epsilon;
41
+        //bool                       nc;
42
+        cache( ) : epsilon (std::numeric_limits<Real>::epsilon() ) { // TODO reset to precision of Real
43
+            //Rtd = VectorXcr::Zero(805);
44
+            //Rtu = VectorXcr::Zero(805);
45
+        }
46
+    };
47
+
48
+    // forward declaration for friend
49
+    template<EMMODE Mode, int Ikernel, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
50
+    class KernelEm1DSpec;
51
+
52
+    // ===================================================================
53
+    //  Class:  KernelEM1DReflSpec
54
+    /**
55
+      @class
56
+      \brief   Specialized version of KernelEM1DReflBase
57
+      \details Through use of template specialisations, this KernelEm1D
58
+               class delivers much better performance.
59
+     */
60
+    // ===================================================================
61
+    template<EMMODE Mode, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
62
+    class KernelEM1DReflSpec : public KernelEM1DReflBase {
63
+
64
+        public:
65
+
66
+            template<EMMODE Mode2, int Ikernel2, DIPOLE_LOCATION Isource2, DIPOLE_LOCATION Irecv2>
67
+            friend class KernelEm1DSpec;
68
+            friend class KernelEM1DManager;
69
+
70
+            // ====================  LIFECYCLE     =======================
71
+
72
+            static KernelEM1DReflSpec* New() {
73
+                KernelEM1DReflSpec<Mode, Isource, Irecv>*  Obj =
74
+                    new KernelEM1DReflSpec<Mode, Isource, Irecv>("KernelEM1DReflSpec<>");
75
+                Obj->AttachTo(Obj);
76
+                return Obj;
77
+            }
78
+
79
+            void Delete() {
80
+                this->DetachFrom(this);
81
+            }
82
+
83
+            // ====================  OPERATORS     =======================
84
+
85
+            // ====================  OPERATIONS    =======================
86
+
87
+            // ====================  ACCESS        =======================
88
+
89
+            // ====================  INQUIRY       =======================
90
+
91
+        protected:
92
+
93
+            // ====================  LIFECYCLE     =======================
94
+
95
+            /// Default protected constructor.
96
+            KernelEM1DReflSpec (const std::string& name) : KernelEM1DReflBase(name)
97
+            {
98
+            }
99
+
100
+            /// Default protected constructor.
101
+            ~KernelEM1DReflSpec () {
102
+                if (this->NumberOfReferences > 0)
103
+                    throw DeleteObjectWithReferences( this );
104
+            }
105
+
106
+            void Release() {
107
+                delete this;
108
+            }
109
+
110
+            // ====================  OPERATIONS    =======================
111
+
112
+            /** Computes reflection coefficients. Depending on the
113
+             * specialisation, this will either be TM or TE mode.
114
+             */
115
+            void ComputeReflectionCoeffs(const Real &lambda);
116
+
117
+            /* Computes reflection coefficients. Depending on the
118
+             * specialisation, this will either be TM or TE mode. This method
119
+             * stores previous results in a struct. For a given index, and
120
+             * lambda, the result will be the same. Turned out to be of limited utility.
121
+             */
122
+            //void ComputeReflectionCoeffs(const Real &lambda, const int& idx);
123
+
124
+            /** Precomputes expensive calculations that are reused by insances
125
+             * of KernelEM1DSpec in the calculation of Related potentials. This
126
+             * method is specialised based on template parameters
127
+             */
128
+            void PreComputePotentialTerms();
129
+
130
+            /*
131
+             * Sets the cache in CACHE to use. Somewhat expensive, avoid calling in tight loops
132
+             */
133
+            //void SetTCache(const Real& rho0);
134
+
135
+            // ====================  DATA MEMBERS  =========================
136
+
137
+        private:
138
+
139
+            //** Storage container for reused results */
140
+            //static std::unordered_map<Real, cache> CACHE;
141
+
142
+            //** Currenly used cache */
143
+            //cache* tcache;
144
+            //#pragma omp threadprivate(tcache)
145
+
146
+    }; // -----  end of class  KernelEM1DReflSpec  -----
147
+
148
+    //template<EMMODE Mode, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
149
+    //std::unordered_map<Real, cache> KernelEM1DReflSpec<Mode, Isource, Irecv>::CACHE;
150
+
151
+    //template<EMMODE Mode, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
152
+    //cache*  KernelEM1DReflSpec<Mode, Isource, Irecv>::tcache;
153
+
154
+    ///////////////////////////////////////////////
155
+    // Declarations of specialisations
156
+
157
+    template<>
158
+    void KernelEM1DReflSpec<TM, INAIR, INAIR>::ComputeReflectionCoeffs(const Real& lambda);
159
+
160
+    template<>
161
+    void KernelEM1DReflSpec<TE, INAIR, INAIR>::ComputeReflectionCoeffs(const Real& lambda);
162
+
163
+    template<>
164
+    void KernelEM1DReflSpec<TM, INAIR, INGROUND>::ComputeReflectionCoeffs(const Real& lambda);
165
+
166
+    template<>
167
+    void KernelEM1DReflSpec<TE, INAIR, INGROUND>::ComputeReflectionCoeffs(const Real& lambda);
168
+
169
+    template<>
170
+    void KernelEM1DReflSpec<TM, INAIR, INAIR>::PreComputePotentialTerms( );
171
+
172
+    template<>
173
+    void KernelEM1DReflSpec<TE, INAIR, INAIR>::PreComputePotentialTerms( );
174
+
175
+    template<>
176
+    void KernelEM1DReflSpec<TM, INAIR, INGROUND>::PreComputePotentialTerms( );
177
+
178
+    template<>
179
+    void KernelEM1DReflSpec<TE, INAIR, INGROUND>::PreComputePotentialTerms( );
180
+
181
+    ///////////////////////////////////////////////
182
+    // Default mode definitions
183
+
184
+/*
185
+    template<EMMODE Mode, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
186
+    void KernelEM1DReflSpec<Mode, Isource, Irecv>::SetTCache(const Real& rho0) {
187
+       #ifdef LEMMAUSEOMP
188
+        #pragma omp critical
189
+        #endif
190
+        {
191
+        this->tcache = &this->CACHE[rho0];
192
+        }
193
+    }
194
+*/
195
+
196
+/*
197
+    template<EMMODE Mode, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
198
+    void KernelEM1DReflSpec<Mode, Isource, Irecv>::ComputeReflectionCoeffs(const Real& lambda, const int& idx) {
199
+
200
+        if ( (std::abs(this->tcache->lambda[idx]-lambda) <= this->tcache->epsilon) &&
201
+            this->tcache->u[idx].size() > 0  && std::abs(this->kk(0) - this->tcache->kk[idx](0)) <= this->tcache->epsilon ) {
202
+            //std::cout << "USING CACHED RESULTS !!!!!!" << std::endl;
203
+            // load all the values we need
204
+            this->u   = this->tcache->u[idx];
205
+            this->rams = this->tcache->rams[idx];
206
+            this->cf = this->tcache->cf[idx];
207
+            //this->kk = this->tcache->kk[idx];
208
+            this->uk = this->tcache->uk[idx];
209
+            this->um = this->tcache->um[idx];
210
+            this->rtd = this->tcache->Rtd[idx];
211
+            this->rtu = this->tcache->Rtu[idx];
212
+
213
+        } else { // else do the work
214
+        }
215
+
216
+        ComputeReflectionCoeffs(lambda);
217
+
218
+        //#pragma omp critical
219
+        //{
220
+        //std::cout << idx << "\t" << lambda << "\t" << rtd.transpose() << std::endl;
221
+        //}
222
+        // store the results
223
+        this->tcache->u[idx]      = this->u;
224
+        this->tcache->cf[idx]     = this->cf;
225
+        this->tcache->kk[idx]     = this->kk;
226
+        this->tcache->uk[idx]     = this->uk;
227
+        this->tcache->um[idx]     = this->um;
228
+        this->tcache->Rtd[idx]    = this->rtd;
229
+        this->tcache->Rtu[idx]    = this->rtu;
230
+        this->tcache->zh0i[idx]    = std::imag(this->zh[0]);
231
+        this->tcache->lambda[idx] = lambda;
232
+        this->tcache->rams[idx]   = rams;
233
+
234
+        }
235
+
236
+        return;
237
+    }
238
+*/
239
+
240
+    template<EMMODE Mode, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
241
+    void KernelEM1DReflSpec<Mode, Isource, Irecv>::ComputeReflectionCoeffs(const Real& lambda) {
242
+        static bool called = false;
243
+        if (!called) {
244
+            std::cout << "unspecialised Reflection function KernelEM1DReflSpec<"
245
+                      << Mode << ", " << Isource << ", "
246
+                      << Irecv << " >::ComputeReflectionCoeffs( const Real& lambda ) --> SLOW PERFORMANCE EXPECTED\n";
247
+            called = true;
248
+        }
249
+
250
+        rams = lambda*lambda;
251
+        //////////////////////////////////////////
252
+        // Compute TEM stuff
253
+
254
+        // This call to sqrt takes ~ 15% of execution time
255
+        u  = (rams-kk.array()).sqrt();
256
+        uk = u(lays);
257
+        um = u(layr);
258
+
259
+        switch (Mode) {
260
+
261
+            // TM mode
262
+            case (TM):
263
+                Zyu(1) = -u(0)/yh(0);
264
+                Zyi    =  u.array() / yh.array();
265
+                break;
266
+
267
+            // TE mode
268
+            case (TE):
269
+                Zyu(1) = -u(0)/zh(0);
270
+                Zyi    =  u.array() / zh.array();
271
+                break;
272
+
273
+            default:
274
+                throw 11; //IllegalMode(this);
275
+        }
276
+
277
+        Zyd.tail<1>() = Zyi.tail<1>();
278
+
279
+        for (int ilay=1; ilay<nlay-1; ++ilay) {
280
+            cf(ilay) =
281
+                std::exp(-(Real)(2.)*u(ilay)*LayerThickness(ilay));
282
+            th(ilay) = ((Real)(1.)-cf(ilay)) / ((Real)(1.)+cf(ilay));
283
+        }
284
+
285
+        // Can't use blocks, b/c recursive
286
+        for (int N=1; N<lays; ++N){
287
+            Zyu(N+1)=Zyi(N)*(Zyu(N)-Zyi(N)*th(N)) /
288
+                            (Zyi(N)-Zyu(N)*th(N)) ;
289
+        }
290
+
291
+        int ne = nlay-2;
292
+        for (int N=ne; N >=lays+1; --N) {
293
+            Zyd(N) = Zyi(N)*(Zyd(N+1)+Zyi(N)*th(N)) /
294
+                            (Zyi(N)+Zyd(N+1)*th(N)) ;
295
+        }
296
+
297
+        rtd(nlay-1) = 0;
298
+
299
+        if (layr < lays) {
300
+            // Receiver above source layer
301
+            int ls = layr;
302
+            if (ls == 0) {
303
+                ls = layr+1;
304
+            }
305
+            for (int N=ls; N<=lays; ++N) {
306
+                rtu(N)= (Zyi(N)+Zyu(N)) /
307
+                        (Zyi(N)-Zyu(N)) ;
308
+            }
309
+            if (lays < nlay-1) {
310
+                rtd(lays) = (Zyi(lays)-Zyd(lays+1)) /
311
+                            (Zyi(lays)+Zyd(lays+1)) ;
312
+            }
313
+        } else {
314
+            // RECEIVER IN OR BELOW THE SOURCE LAYER
315
+            if (lays == layr) {  // Rx In source Layer
316
+                if (layr == 0) {
317
+                    rtd(0) = (Zyu(1)+Zyd(1)) /
318
+                             (Zyu(1)-Zyd(1)) ;
319
+                } else if (layr == nlay-1) {
320
+                    rtu(nlay-1) = (Zyi(nlay-1)+Zyu(nlay-1)) /
321
+                                  (Zyi(nlay-1)-Zyu(nlay-1)) ;
322
+                } else {
323
+                    rtu(layr) = (Zyi(layr)+Zyu(layr)) /
324
+                                (Zyi(layr)-Zyu(layr)) ;
325
+                    rtd(layr) = (Zyi(layr)-Zyd(layr+1)) /
326
+                                (Zyi(layr)+Zyd(layr+1)) ;
327
+                }
328
+            } else { // receiver below source layer
329
+                if (lays == 0) {
330
+                    rtd(0) = (Zyu(1)+Zyd(1)) /
331
+                             (Zyu(1)-Zyd(1)) ;
332
+                } else {
333
+                    rtu(lays) = (Zyi(lays)+Zyu(lays)) /
334
+                                (Zyi(lays)-Zyu(lays)) ;
335
+                }
336
+                int le = layr;
337
+                if (le == nlay-1) --le;
338
+                int ls = lays;
339
+                if (lays == 0   ) ++ls;
340
+
341
+                // TODO use blocks to vectorize maybe?
342
+                // This works but gives same to slightly worse
343
+                // performance as loop.
344
+//                 int nn = le-ls+1;
345
+//                 rtd.segment(ls, nn) =
346
+//                      (Zyi.segment(ls  , nn).array() -
347
+//                       Zyd.segment(ls+1, nn).array()).array() /
348
+//                      (Zyi.segment(ls  , nn).array() +
349
+//                       Zyd.segment(ls+1, nn).array()).array() ;
350
+                for (int N=ls; N<=le; ++N) {
351
+                    rtd(N) = (Zyi(N)-Zyd(N+1)) /
352
+                             (Zyi(N)+Zyd(N+1)) ;
353
+                }
354
+            }
355
+        } // End in or below source layer
356
+        return;
357
+    }
358
+
359
+    template<EMMODE Mode, DIPOLE_LOCATION Isource, DIPOLE_LOCATION Irecv>
360
+    void KernelEM1DReflSpec<Mode, Isource, Irecv>::PreComputePotentialTerms( ) {
361
+        static bool called = false;
362
+        if (!called) {
363
+            std::cerr << "unspecialised function KernelEM1DReflSpec<"
364
+                      << Mode << ", " << Isource << ", "
365
+                      << Irecv << " >::PreComputePotentialTerms\n";
366
+            called = true;
367
+        }
368
+    }
369
+
370
+
371
+}		// -----  end of Lemma  name  -----
372
+
373
+#endif   // ----- #ifndef KERNELEM1DREFLSPEC_INC  -----

+ 1485
- 0
LemmaCore/include/kernelem1dspec.h
File diff suppressed because it is too large
View File


+ 166
- 0
LemmaCore/include/layeredearth.h View File

@@ -0,0 +1,166 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     06/24/2009
11
+  @version   0.0
12
+ **/
13
+
14
+#ifndef __LAYEREDEARTH_H
15
+#define __LAYEREDEARTH_H
16
+
17
+#include "earthmodel.h"
18
+
19
+namespace Lemma {
20
+
21
+	const int MAXLAYERS	= 10;
22
+
23
+	// =======================================================================
24
+	//        Class:  LayeredEarth
25
+	/// Abstract 1D layered earth.
26
+	// =======================================================================
27
+	class LayeredEarth : public EarthModel {
28
+
29
+		public:
30
+
31
+			// ====================    FRIENDS     ===========================
32
+			/** Recursively prints out information about this class
33
+             */
34
+            friend std::ostream &operator<<(std::ostream &stream,
35
+						const LayeredEarth &ob);
36
+
37
+			// ====================  LIFECYCLE     ===========================
38
+
39
+			// ====================  OPERATORS     ===========================
40
+
41
+			// ====================  OPERATIONS    ===========================
42
+
43
+			// ====================  ACCESS        ===========================
44
+
45
+			/** Sets the number of layers and resizes all model parameters to
46
+			 *  be the correct size, finally initialises all values to free
47
+			 *  space.
48
+             */
49
+			virtual void SetNumberOfLayers(const int& nlay)=0;
50
+
51
+			/** Sets the thickness of the layers
52
+             */
53
+			void SetLayerThickness(const VectorXr &thick);
54
+
55
+			// ====================  INQUIRY       ===========================
56
+
57
+			/** Returns the number of layers in the model */
58
+			int GetNumberOfLayers( );
59
+
60
+			/** Returns the number of layers in the model, excluding the air
61
+			 * layer
62
+             */
63
+			int GetNumberOfNonAirLayers( );
64
+
65
+			/** Returns the layer that a depth is in.
66
+			 * @param[in] depth is the depth you desire to know the layer of
67
+			 * @return the indice of the layer that depth is in.
68
+             */
69
+			int GetLayerAtThisDepth(const Real& depth);
70
+
71
+			/** Returns the thickness of a layer
72
+             *  @param[in] lay is the layer indice
73
+             *  @return the thickness of a layer
74
+             */
75
+			Real GetLayerThickness(const int & lay);
76
+
77
+			/** Returns the depth of the bottom interface of a layer
78
+             *  @param[in] lay is the layer indice
79
+             *  @return the depth of the bottom interface of a layer
80
+             */
81
+			Real GetLayerDepth(const int & lay);
82
+
83
+            #ifdef HAVE_YAMLCPP
84
+            /** YAML Serializing method
85
+             */
86
+            YAML::Node Serialize() const;
87
+            //static LayeredEarth* DeSerialize(const YAML::Node& node);
88
+            #endif
89
+
90
+		protected:
91
+
92
+			// ====================  LIFECYCLE     ===========================
93
+
94
+			/** Default protected constructor. */
95
+			LayeredEarth (const std::string& name);
96
+
97
+            #ifdef HAVE_YAMLCPP
98
+            /** Default protected constructor. */
99
+			LayeredEarth (const YAML::Node& node);
100
+            #endif
101
+
102
+			/** Default protected constructor. */
103
+			~LayeredEarth ();
104
+
105
+			// ====================  DATA MEMBERS  ===========================
106
+
107
+			/** Number of layers in the model, including the air layer,
108
+			 * and counting from 0
109
+             */
110
+			int               NumberOfLayers;
111
+
112
+			/** Number of interfaces in the model. Equal to NumberOfLayers - 1
113
+			 */
114
+            int               NumberOfInterfaces;
115
+
116
+			/** Vector of layer thicknesses */
117
+			VectorXr          LayerThickness;
118
+
119
+	}; // -----  end of class  LayeredEarth  -----
120
+
121
+
122
+    ///////////////////////////////////////////////////////////////////
123
+    // Error classes
124
+
125
+    /** If a model with less than two layers is specified, throw error. Not set up
126
+     * for whole space solutions.
127
+     */
128
+    class EarthModelWithLessThanTwoLayers : public std::runtime_error {
129
+        public:
130
+            EarthModelWithLessThanTwoLayers( );
131
+    };
132
+
133
+    /** If a solver has a max number of layers, and this is exceeded, throw this
134
+     * error.
135
+     */
136
+    class EarthModelWithMoreThanMaxLayers : public std::runtime_error {
137
+        public:
138
+            /** Thrown when an Earth model with more than the maximum number of
139
+             *  Layers is given
140
+             */
141
+            EarthModelWithMoreThanMaxLayers( );
142
+    };
143
+
144
+    /** If the model parameters have different lengths than the earth model, throw
145
+     * this error.
146
+     */
147
+    class EarthModelParametersDoNotMatchNumberOfLayers : public std::runtime_error {
148
+        public:
149
+            /** Thrown when the parameters do not match the number of Layers
150
+             */
151
+            EarthModelParametersDoNotMatchNumberOfLayers ( );
152
+    };
153
+
154
+    /** If a request if made for a non-valid earth model parameter, throw this
155
+     * error.
156
+     */
157
+    class RequestForNonValidEarthModelParameter : public std::runtime_error {
158
+        public:
159
+            /** Thrown when a request is made for a non-valid earth parameter
160
+             */
161
+            RequestForNonValidEarthModelParameter ( );
162
+    };
163
+
164
+} // namespace Lemma
165
+
166
+#endif // __LAYEREDEARTH_H

+ 314
- 0
LemmaCore/include/layeredearthem.h View File

@@ -0,0 +1,314 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     06/24/2009
11
+  @version   0.0
12
+ **/
13
+
14
+#ifndef __LAYEREDEARTHEM_H
15
+#define __LAYEREDEARTHEM_H
16
+
17
+#include "layeredearth.h"
18
+#include <iomanip>
19
+
20
+namespace Lemma {
21
+
22
+    // =======================================================================
23
+    //        Class:  LayeredEarthEM
24
+    /// \brief  1D layered earth. Attributes include all aspects of
25
+    /// Cole-Cole model.
26
+    /// \details   Primarily used for EM calculations.
27
+    // =======================================================================
28
+    class LayeredEarthEM : public LayeredEarth {
29
+
30
+        public:
31
+
32
+            // ====================    FRIENDS     ===========================
33
+
34
+            /** Recursively streams information about this class */
35
+            friend std::ostream &operator<<(std::ostream &stream,
36
+                        const LayeredEarthEM &ob);
37
+
38
+            // ====================  LIFECYCLE     ===========================
39
+
40
+            /**
41
+             *  Public constructor. Creates a new instance of the class and
42
+             *  assigns a reference to the thrown pointer.
43
+             */
44
+            static LayeredEarthEM* New();
45
+
46
+            /**
47
+             * @copybrief LemmaObject::Delete()
48
+             * @copydetails LemmaObject::Delete()
49
+             */
50
+            void Delete();
51
+
52
+            #ifdef HAVE_YAMLCPP
53
+            /** YAML Serializing method
54
+             */
55
+            YAML::Node Serialize() const;
56
+
57
+
58
+            //static LayeredEarthEM* DeSerialize(const YAML::Node& node);
59
+            #endif
60
+
61
+            /** @return a deep copy
62
+             */
63
+			LayeredEarthEM* Clone();
64
+
65
+            // ====================  OPERATORS     ===========================
66
+
67
+            // ====================  OPERATIONS    ===========================
68
+
69
+            /** Evaluates the cole-cole model for suceptability and
70
+             * permeability.
71
+             * @param[in] omega is the frequency in Hz
72
+             */
73
+            void EvaluateColeColeModel(const Real& omega);
74
+
75
+            // ====================  ACCESS        ===========================
76
+
77
+            /** Sets the number of layers and resizes all model parameters to
78
+             *  be the correct size, finally initialises all values to free
79
+             *  space.
80
+             *  @param[in] nlay is the number of layers
81
+             */
82
+            virtual void SetNumberOfLayers(const int& nlay);
83
+
84
+            /** Sets Complex Conductivity of the layers
85
+             *  @param[in] sigma is a vector of the conducivity of the layers
86
+             */
87
+            void SetLayerConductivity(const VectorXcr &sigma);
88
+
89
+            /** Sets Complex Conductivity of a single layer
90
+             *  @param[in] sigma is  the conducivity of the layer
91
+             *  @param[in] ilay is  the layer index
92
+             */
93
+            void SetLayerConductivity(const int& ilay, const Complex &sigma);
94
+
95
+            /* Sets Complex resitivity of the layers
96
+             *  @param[in] ohm is a vector of the resistivity of the layers
97
+                Singularity at 0 resistivity in air. Need to reformaulat things a bit
98
+             */
99
+            //void SetLayerResistivity(const VectorXcr &ohm);
100
+
101
+            /** Sets the thickness of the layers
102
+             *  @param[in] thick is a vector of the thicknesses of the layers.
103
+             *  Must be two less than the total number of Layers as the top and
104
+             *  bottom layers are assumed infinite.
105
+             */
106
+            void SetLayerThickness(const VectorXr &thick);
107
+
108
+            /** Sets the High frequency susceptibility
109
+             */
110
+            void SetLayerHighFreqSusceptibility(const VectorXr& sushi);
111
+
112
+            /** Sets the Low frequency susceptibility
113
+             */
114
+            void SetLayerLowFreqSusceptibility(const VectorXr& sushi);
115
+
116
+            /** Sets the Layer breath susceptibility
117
+             */
118
+            void SetLayerBreathSusceptibility(const VectorXr& susbr);
119
+
120
+            /** Sets the Layer tau susceptibility
121
+             */
122
+            void SetLayerTauSusceptibility(const VectorXr& susta);
123
+
124
+            /** Sets the High frequency permitivity
125
+             */
126
+            void SetLayerHighFreqPermitivity(const VectorXr& sushi);
127
+
128
+            /** Sets the Low frequency permitivity
129
+             */
130
+            void SetLayerLowFreqPermitivity(const VectorXr& sushi);
131
+
132
+            /** Sets the Layer breath permitivity
133
+             */
134
+            void SetLayerBreathPermitivity(const VectorXr& oerbr);
135
+
136
+            /** Sets the Layer breath permitivity
137
+             */
138
+            void SetLayerTauPermitivity(const VectorXr& oerbr);
139
+
140
+            // ====================  INQUIRY       ===========================
141
+
142
+            /** Returns the thickness of a layer
143
+                @return a VectorXcr of the layer conductivities.
144
+             */
145
+            VectorXcr GetLayerConductivity( );
146
+
147
+            /** Returns the conductivity of a layer
148
+             *  @param[in] ilay is the layer indice of interest
149
+             *  @return the complex valued conductivity of the layer of
150
+             *  interest.
151
+             */
152
+            Complex GetLayerConductivity(const int &ilay);
153
+
154
+            /** Returns the susceptibility of a layer
155
+             *  @param[in] ilay is the layer indice of interest.
156
+             *  @return a Complex value of the electrical susceptibility of the
157
+             *  probes layer.
158
+             */
159
+            Complex GetLayerSusceptibility(const int &ilay);
160
+
161
+            /** Returns the Susceptibility of Cole-Cole model
162
+             *  @return a VectorXcr of the suceptibilities of the model.
163
+             */
164
+            VectorXcr GetLayerSusceptibility( );
165
+
166
+            /** Returns the low freq susceptibility of a layer
167
+             */
168
+            Real GetLayerLowFreqSusceptibility(const int &ilay);
169
+
170
+            /** Returns the low freq susceptibility of a layer
171
+             */
172
+            VectorXr GetLayerLowFreqSusceptibility( );
173
+
174
+            /** Returns the low freq susceptibility of a layer
175
+             */
176
+            Real GetLayerHighFreqSusceptibility(const int &ilay);
177
+
178
+            /** Returns the low freq susceptibility of a layer
179
+             */
180
+            VectorXr GetLayerHighFreqSusceptibility( );
181
+
182
+            /** Returns the low freq susceptibility of a layer
183
+             */
184
+            Real GetLayerTauSusceptibility(const int &ilay);
185
+
186
+            /** Returns the low freq susceptibility of a layer
187
+             */
188
+            VectorXr GetLayerTauSusceptibility( );
189
+
190
+            /** Returns the low freq susceptibility of a layer
191
+             */
192
+            Real GetLayerBreathSusceptibility(const int &ilay);
193
+
194
+            /** Returns the low freq susceptibility of a layer
195
+             */
196
+            VectorXr GetLayerBreathSusceptibility( );
197
+
198
+            /** Returns the Relative Permitivity of the cole cole model
199
+             */
200
+            VectorXcr GetLayerPermitivity( );
201
+
202
+            /** Returns the conductivity of a layer
203
+             *  @param[in] ilay is the layer indice of interest.
204
+             *  @return a Complex value of the electrical permitivity of the
205
+             *  probed layer.
206
+             */
207
+            Complex GetLayerPermitivity(const int &ilay);
208
+
209
+            /** Low Freq permivitity
210
+             */
211
+            VectorXr  GetLayerLowFreqPermitivity( );
212
+
213
+            /** Returns the low freq susceptibility of a layer
214
+             */
215
+            Real GetLayerLowFreqPermitivity(const int &ilay);
216
+
217
+            /** Returns the low freq susceptibility of a layer
218
+             */
219
+            Real GetLayerHighFreqPermitivity(const int &ilay);
220
+
221
+            /** Returns the low freq susceptibility of a layer
222
+             */
223
+            VectorXr GetLayerHighFreqPermitivity( );
224
+
225
+            /** Returns the low freq susceptibility of a layer
226
+             */
227
+            Real GetLayerTauPermitivity(const int &ilay);
228
+
229
+            /** Returns the low freq susceptibility of a layer
230
+             */
231
+            VectorXr GetLayerTauPermitivity( );
232
+
233
+            /** Returns the low freq susceptibility of a layer
234
+             */
235
+            Real GetLayerBreathPermitivity(const int &ilay);
236
+
237
+            /** Returns the low freq susceptibility of a layer
238
+             */
239
+            VectorXr GetLayerBreathPermitivity( );
240
+
241
+        protected:
242
+
243
+            // ====================  LIFECYCLE     ===========================
244
+
245
+            /** Default protected constructor. */
246
+            LayeredEarthEM (const std::string &name);
247
+
248
+            #ifdef HAVE_YAMLCPP
249
+            /** Default protected constructor. */
250
+			LayeredEarthEM (const YAML::Node& node);
251
+            #endif
252
+
253
+            /** Default protected constructor. */
254
+            ~LayeredEarthEM ();
255
+
256
+            /**
257
+             * @copybrief LemmaObject::Release()
258
+             * @copydetails LemmaObject::Release()
259
+             */
260
+            void Release();
261
+
262
+            // ====================  DATA MEMBERS  ===========================
263
+
264
+            /** Vector of layer Conductivity */
265
+            VectorXcr         LayerConductivity;
266
+
267
+            /** Vector of layer Susceptibility (chi)
268
+             *  This is calculated using the Cole-Cole model
269
+             *  \f[ sus(i) = sush(i)
270
+             *   + \frac{(susl(i)-sush(i))}  {(1+(jw * sustau(i))^{susalp(i)})} \f]
271
+             */
272
+            VectorXcr         LayerSusceptibility;
273
+
274
+            /** Vector of low frequency susceptibility, for use in Cole-Cole
275
+              model */
276
+            VectorXr          LayerLowFreqSusceptibility;
277
+
278
+            /** Vector of high frequency susceptibility, for use in Cole-Cole
279
+             model */
280
+            VectorXr          LayerHighFreqSusceptibility;
281
+
282
+            /** Vector of relaxation time constants, for use in Cole-Cole model
283
+             */
284
+            VectorXr          LayerTauSusceptibility;
285
+
286
+            /** Vector relaxation breath, for use in Cole-Cole model
287
+             */
288
+            VectorXr          LayerBreathSusceptibility;
289
+
290
+            /** Vector of Layer Permitivity (epsilon)
291
+             *  Calculated using the Cole-Cole model
292
+             *  \f[ epr(i) = eprh(i)
293
+             *     + \frac{ (eprl(i)-eprh(i))}  { (1+(jw*eprtau(i))^{epralp(i)})} \f]
294
+             */
295
+            VectorXcr         LayerPermitivity;
296
+
297
+            /** Low frequency permitivity for each layer */
298
+            VectorXr          LayerLowFreqPermitivity;
299
+
300
+            /** High frequency permitivity for each layer */
301
+            VectorXr          LayerHighFreqPermitivity;
302
+
303
+            /** Decay time constant for each layer */
304
+            VectorXr          LayerTauPermitivity;
305
+
306
+            /** Relaxation breath for each layer */
307
+            VectorXr          LayerBreathPermitivity;
308
+
309
+    }; // -----  end of class  LayeredEarthEM  -----
310
+
311
+
312
+} // namespace Lemma
313
+
314
+#endif // __LAYEREDEARTHEM_H

+ 333
- 0
LemmaCore/include/lemma.h View File

@@ -0,0 +1,333 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     06/19/2009 09:12:20 AM  The Birth of Lemma!
11
+  @version  $Id: lemma.h 203 2015-01-09 21:19:04Z tirons $
12
+ **/
13
+
14
+/** \mainpage Lemma is an ElectroMagnetics Modelling API
15
+    \image html lemma.png
16
+
17
+    \authors Trevor Irons and M. Andrew Kass and others
18
+
19
+    Lemma is a recursive acronym that stands for <B>L</B>emma is an
20
+    <B>E</B>lectro<B>M</B>agnetics <B>M</B>odelling <B>A</B>PI.
21
+    Lemma is a cross-platform library delivering an expressive API that
22
+    can be used to easily create versatile programs.
23
+    We are building a powerful, flexible,
24
+    expresive framework that allows for the straightforward creation of
25
+    geophysical EM applications. Lemma is not itself a program, instead
26
+    it is a collection of building blocks to make applications.
27
+    We chose this name because:
28
+
29
+    - In mathematics a Lemma is a proven proposition which is used as a
30
+    stepping stone to a larger result rather than as a statement in-and-of
31
+    itself.
32
+    - In addition to the electromagnetic modelling, some other facilities are
33
+    provided such as numerical optimization and inversion capabilities. These
34
+    tools are also considered stepping stones to final products.
35
+
36
+    We feel that this is a partucularily approprate name, as Lemma's
37
+    API can be leveraged create powerful applications such as forward
38
+    modelling and inverting frequency and time-domain
39
+    surveys of arbitrary survey design, SNMR surveys, CSAMT and more.
40
+
41
+    \section Motivation
42
+    Why another Geophysical EM project? For starters, there
43
+    aren't that many quality open source packages out there. Those that do
44
+    exist are generally specialized to perform a single task and extending
45
+    them is a major undertaking. Lemma's approach is much different, by
46
+    providing a set of general tools users can easily assemble applications
47
+    that suite their needs.
48
+
49
+    While most geophysical EM modeling packages are concerned with forward
50
+    modeling <B>DATA</B> between specific transmitters and receivers located
51
+    on the surface of the earth; Lemma is fundamentally concerned with
52
+    modelling <B>FIELDS</B> due to sources, the field values can be calculated
53
+    everywhere within the domain. This allows for solving multiphysics EM
54
+    problems. Tradional EM data may be forward modelled using the Lemma::Instrument
55
+    classes.
56
+
57
+    \section Capabilities Capabilities
58
+    In the long term, we have many goals for this software project. Due to its
59
+    design, Lemma can be built upon and extended easily. The initial aim is to
60
+    provide flexible 1D and 3D EM modelling in the time and frequency domains.
61
+    The project is still in beta, but we have made a lot of progress already.
62
+    We will release our first non-beta release as soon as the following are
63
+    supported.
64
+
65
+    \subsection FDM Frequency-domain forward modelling
66
+    Lemma was initially called EMMODFD: Electromagnetic Modelling in the Frequency
67
+    Domain. As such this is the most mature area of Lemma.
68
+
69
+    \par 1D
70
+    Frequency domain solutions to electrical and magnetic dipoles can be computed
71
+    quasi-analytically in 1D. Calculations can be made in or above the layered
72
+    media, and complex electrical conductivity and magnetic susceptibility are
73
+    supported according to the Cole-Cole model. Sources may be embdedded in the
74
+    media or in the resisitive air layer. Lemma can also can compute fields due
75
+    to arbitrarily shaped ungrounded wire loops, topography of the loops is also
76
+    supported. Two separate approaches to solving the Hankel transform, one
77
+    based on Anderson's digitial filtering technique, and another based on Gaussian
78
+    quadrature.
79
+
80
+    \par 3D
81
+    A fast 3D solver that can modify the 1D results based
82
+    on arbitrary electrical conductivity model is nearing completion.
83
+
84
+    \par future work
85
+    We are also planning on supporting grounded wires in the near future.
86
+
87
+    \subsection TDM Time-domain forward modelling
88
+	A 1D time-domain solution has been implemented that utilises both a
89
+	dipole source as well as a wire loop.  Currently, only one receiver is
90
+	modelled at a time, but will be generalised.  In addition, utilities
91
+	to read in data files for modelling have been implemented.
92
+    We would like to offer 3D time domain support, but this will not be
93
+    provided before our first stable release.
94
+
95
+    \subsection DataFormats Data Formats
96
+    The EM community is plagued with myriad data formats. Often each equiptment
97
+    manufacturer provides their own data format and interoperability is a
98
+    constant struggle. We are working on a flexible data format based on the XML
99
+    format that can be adapted to many types of data. The template for this
100
+    format will be publically released and we hope it catches on in the community.
101
+    At the least, it will provide a mechanism to compare datasets and datatypes
102
+    within Lemma.
103
+
104
+    \section Modules Modules
105
+    Due to Lemma's design, it is easy to extend the platform. In some cases this
106
+    extension results in adding functionality that is not directly related to
107
+    ElectroMagnetics. The following modules utilise parts of Lemma to provide
108
+    their functionality.
109
+
110
+    \subsection Merlin Merlin.
111
+    This module provides nuclear magnetic resonance functionality.
112
+
113
+
114
+    \section Tutorials
115
+        - \ref Tutorial - Basic intruduction to Lemma, including aquiring and
116
+          compiling the code, class structure, and building your own
117
+          applications.
118
+        - \ref Extending Tutorial on how to extend Lemma.
119
+
120
+
121
+    \section Development Development and design
122
+    Ths package is primarily being developed by the Center for Gravity,
123
+    Electrical, and Magnetic Studies (CGEM) at the Colorado School of Mines (CSM), the United
124
+    States Geological Survey (USGS), and Broken Spoke Development, LLC. It draws on work by
125
+    many others including Ki Ha Lee, and Walt Anderson. All new work and
126
+    interfaces are written entirely in C++. Several small external projects are
127
+    included, which are written in standard C, and FORTRAN 77. We adapt a
128
+    modern, test driven, object oriented, C++ framework.
129
+
130
+    \section Legalities
131
+
132
+    \subsection Copyrights
133
+    The following copyrights apply to the source.
134
+    Most of the code was developed either by Trevor
135
+    Copyright (C) 2008-2010 Trevor Irons <tirons@mines.edu> or
136
+    M. Andrew Kass Copyright (C) 2010 <mkass@numericalgeo.com>.
137
+
138
+    The 1D EM solver was derived (but updated heavily) from a fortran
139
+    programme written by Ki Ha Lee in 1984. We have communicated with Ki Ha,
140
+    and he assured us that this code is in the public domian.
141
+
142
+    A Gaussian quadrature hankel transform originally written by Alan Chave was
143
+    ported to C++. This code is in the public domain, and was published in Geophysics.
144
+
145
+    A digital filtering approach to the Hankel transform written by Walt
146
+    Anderson was also rewritten for Lemma. The origional fortran code is also in
147
+    the public domain. Using this Hankel transform works
148
+    arround the copyright issue mentioned above, but may not produce accurate
149
+    results for high frequencies.
150
+
151
+    Please note that Ki Ha Lee and Walt Anderson had no part in this work, and
152
+    the above should not be interpreted as any sort of endorsement by those
153
+    parties.
154
+
155
+    \subsection License
156
+
157
+    This Source Code Form is subject to the terms of the Mozilla Public
158
+    License, v. 2.0. If a copy of the MPL was not distributed with this
159
+    file, You can obtain one at http://mozilla.org/MPL/2.0/.
160
+
161
+    \section Contributing Suggestions and contributions
162
+        We welcome contributions and suggestions. Feel free to email the development
163
+        team at info@lemmasoftware.org.
164
+        Under the terms of the MPL, if you modify a Lemma file, you are obligated to
165
+        share those contributions back with the community.
166
+
167
+    \section Useful Useful links
168
+        - Home page https://lemmasoftware.org
169
+        - SVN repository https://svn.lemmasoftware.org
170
+        - Broken Spoke Develpment http://numericalgeo.com
171
+        - CGEM at the Coloroado School of Mines http://geophysics.mines.edu/cgem/
172
+**/
173
+
174
+#pragma once
175
+
176
+#ifndef __LEMMA_H
177
+#define __LEMMA_H
178
+
179
+    // Include some basic stuff that will always be needed
180
+    #include <iostream>
181
+    #include <iomanip>
182
+    #include <complex>
183
+    #include <fstream>
184
+    #include <string>
185
+    #include <vector>
186
+    #include <stdexcept>
187
+    #include <sstream>
188
+
189
+    #include <Eigen/Core>
190
+    #include <cstddef>
191
+    #include <Eigen/StdVector>
192
+    #include <Eigen/Sparse>
193
+    #include <unsupported/Eigen/FFT>
194
+    //#include <unsupported/Eigen/SparseExtra>
195
+    #include <Eigen/Geometry>
196
+
197
+    /** \brief The only namespace used by Lemma
198
+     *
199
+     *  \details The rational behind this namespace is that built-in
200
+     *  types should be used wherever possible, but not
201
+     *  not built-in names. This allows for code that is better
202
+     *  enacsulated and easier to modify. The typedefs and constants
203
+     *  specified here are defined so that
204
+     *  precision/inplimentation can easily be changed.
205
+     *  All floating precision types should be typedefed in this file
206
+     *  and should not be used natively within any code.
207
+     *  Lemma uses
208
+     *  the Eigen Matrix/Vector/Linear Algebra library.
209
+     *  <http://eigen.tuxfamily.org> and a lot of the namespece typedefs
210
+     *  are specifying Eigen types.
211
+     */
212
+    namespace Lemma {
213
+
214
+        /// Real defines precision for the whole API, default is double
215
+#ifdef  LEMMA_SINGLE_PRECISION
216
+        typedef float Real;
217
+#else      // -----      LEMMA_SINGLE_PRECISION  -----
218
+        typedef double Real;
219
+#endif     // -----  not LEMMA_SINGLE_PRECISION  -----
220
+
221
+        /// Complex version of Real.
222
+        typedef std::complex<Real> Complex;
223
+
224
+        /// A 3 component Eigen vector of Reals
225
+        typedef Eigen::Matrix<Real, 3, 1> Vector3r;
226
+
227
+        /// A 3 X Dynamic Component Eigen matrix of Reals
228
+        typedef Eigen::Matrix<Real, 3, Eigen::Dynamic> Vector3Xr;
229
+
230
+        /// Variable length Eigen vector of Reals
231
+        typedef Eigen::Matrix<Real, Eigen::Dynamic, 1> VectorXr;
232
+
233
+        /// Variable length Eigen vector of integers (int)
234
+        typedef Eigen::Matrix<int, Eigen::Dynamic, 1> VectorXi;
235
+
236
+        /// Variable length Eigen vector of Complexes
237
+        typedef Eigen::Matrix<Complex, Eigen::Dynamic, 1> VectorXcr;
238
+
239
+        /// A 3 Component Eigen vector of Complexes
240
+        typedef Eigen::Matrix<Complex, 3, 1> Vector3cr;
241
+
242
+        /// A 3 X Dynamic Component Eigen matrix of Complexes
243
+        typedef Eigen::Matrix<Complex, 3, Eigen::Dynamic> Vector3Xcr;
244
+
245
+        /// Variable length Eigen Matrix of Reals
246
+        typedef Eigen::Matrix<Real, Eigen::Dynamic, Eigen::Dynamic> MatrixXr;
247
+
248
+        /// Variable length Eigen Matrix of ints
249
+        typedef Eigen::Matrix<int, Eigen::Dynamic, Eigen::Dynamic> MatrixXi;
250
+
251
+        /// Variable length Eigen vector of Complexes
252
+        typedef Eigen::Matrix<Complex, Eigen::Dynamic, Eigen::Dynamic> MatrixXcr;
253
+
254
+        ////////////////////////////////////////
255
+        // Constants used across the programmes
256
+
257
+        /// Restating the obvious, this is pi
258
+        const Real PI = 4.0*atan(1.0);
259
+
260
+        /// Permitivity of Free Space
261
+        //const Real EPSILON0 = 8.854187817e-12;
262
+        const Real EPSILON0 = 8.854187817e-12;
263
+
264
+        /// Permeability of free space
265
+        const Real MU0 = 4.*PI*1e-7;
266
+
267
+        /// 1/4 of \f$ \pi\f$
268
+        const Real QPI = .25/PI;
269
+
270
+        /// Some functions will convert units from SI (standard) to Gauss
271
+        /// This is because NMR calculations are much more natural in Gauss
272
+        enum MAGUNITS  {TESLA, NANOTESLA, GAUSS};
273
+
274
+        /// Unit of temperature entered
275
+        enum TEMPUNITS {CELCIUS, KELVIN};
276
+
277
+        /// Unit of time entered
278
+        enum TIMEUNITS {SEC, MILLISEC, MICROSEC, NANOSEC, PICOSEC};
279
+
280
+        /// Unit of time entered
281
+        enum FREQUENCYUNITS {HZ, KHZ, MHZ, GHZ};
282
+
283
+		/// FEM coil relative orientations
284
+		enum FEMCOILORIENTATION {COAXIAL, COPLANAR};
285
+
286
+		/// General orientation relative to coordinate system
287
+		enum ORIENTATION {X, Y, Z, NX, NY, NZ};
288
+
289
+        /// Type of field
290
+        enum FIELDTYPE         {HFIELDREAL, HFIELDIMAG, EFIELDREAL, EFIELDIMAG};
291
+
292
+        /// Compenent of vector field
293
+        enum FIELDCOMPONENT    {XCOMPONENT=0, YCOMPONENT=1, ZCOMPONENT=2};
294
+
295
+        /// Spatial component of vector
296
+        enum SPATIALCOORDINANT  {XCOORD=0, YCOORD=1, ZCOORD=2};
297
+
298
+        /** Evaluation method for Hankel integrals.
299
+         *  ANDERSON801     Walt Anderson's 801 point filter
300
+         *  CHAVE           Alan Chave's gaussian quadrature integration method
301
+         *  FHTKEY201       Key's 201 point filter
302
+         *  FHTKEY201       Key's 101 point filter
303
+         *  FHTKEY51        Key's 51 point filter
304
+         *  QWEKEY          Key's Gaussian quadrature integration method
305
+         */
306
+        enum HANKELTRANSFORMTYPE { ANDERSON801, CHAVE, FHTKEY201, FHTKEY101, FHTKEY51, QWEKEY };
307
+
308
+        /** Enum is OK because these are the only physically possible sources.
309
+         @param NOSOURCETYPE is default.
310
+         @param ELECTRICDIPOLE is an electric dipole
311
+         @param MAGNETICDIPOLE is a magnetic dipole
312
+        */
313
+        enum DipoleSourceType {NOSOURCETYPE, GROUNDEDELECTRICDIPOLE, UNGROUNDEDELECTRICDIPOLE, MAGNETICDIPOLE};
314
+
315
+        /// Only three polarizations are supported. They may be summed to
316
+        /// approximate others
317
+        /// @param NOPOLARISATION is uninitialized, default value
318
+        /// @param XPOLARISATION is a dipole oriented in the x direction
319
+        /// @param YPOLARISATION is a dipole oriented in the y direction
320
+        /// @param ZPOLARISATION is a dipole oriented in the z direction
321
+        enum DipoleSourcePolarisation {NOPOLARISATION, XPOLARISATION,
322
+            YPOLARISATION,  ZPOLARISATION};
323
+
324
+        /// The polarity may be either negative or positinve
325
+        enum DipoleSourcePolarity {NEGATIVE, POSITIVE};
326
+
327
+        /** The fields to make calculations on
328
+        */
329
+        enum FIELDCALCULATIONS {E, H, BOTH};
330
+
331
+    }
332
+
333
+#endif // __Lemma_H

+ 1369
- 0
LemmaCore/include/logbarriercg.h
File diff suppressed because it is too large
View File


+ 1959
- 0
LemmaCore/include/logbarriercg_newton.h
File diff suppressed because it is too large
View File


+ 73
- 0
LemmaCore/include/modelreader.h View File

@@ -0,0 +1,73 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     02/18/2011
11
+  @version  $Id: modelreader.h 201 2015-01-03 00:07:47Z tirons $
12
+ **/
13
+
14
+#ifndef __MODELREADER_H
15
+#define __MODELREADER_H
16
+
17
+#include "LemmaObject.h"
18
+#include "layeredearthem.h"
19
+#include "PolygonalWireAntenna.h"
20
+#include "receiverpoints.h"
21
+
22
+namespace Lemma {
23
+
24
+// ===================================================================
25
+//        Class:  ModelReader
26
+/// \brief Model and instrument reader for forward modelling.
27
+/// \details This is an abstract class.
28
+// ===================================================================
29
+class ModelReader : public LemmaObject {
30
+
31
+	friend std::ostream &operator<<(std::ostream &stream,
32
+		const ModelReader &ob);
33
+
34
+	public:
35
+
36
+		// ====================  LIFECYCLE     =======================
37
+
38
+		static ModelReader* New();
39
+
40
+		void Delete();
41
+
42
+		// ====================  OPERATORS     =======================
43
+
44
+		// ====================  OPERATIONS    =======================
45
+
46
+		// ====================  ACCESS        =======================
47
+
48
+		// ====================  INQUIRY       =======================
49
+
50
+
51
+
52
+	protected:
53
+
54
+		// ====================  LIFECYCLE     =======================
55
+
56
+		/// Default protected constructor.
57
+		ModelReader (const std::string &name);
58
+
59
+		/// Default protected constructor.
60
+		~ModelReader ();
61
+        /**
62
+        * @copybrief LemmaObject::Release()
63
+        * @copydetails LemmaObject::Release()
64
+        */
65
+		void Release();
66
+		// ====================  DATA MEMBERS  =========================
67
+
68
+	private:
69
+
70
+}; // -----  end of class  ModelReader  -----
71
+} // end of namespace lemma
72
+#endif // __MODELREADER_H
73
+

+ 68
- 0
LemmaCore/include/modelreaderfem1d.h View File

@@ -0,0 +1,68 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     01/03/2013
11
+  @version  $Id$
12
+ **/
13
+
14
+#ifndef __MODELREADERFEM1D_H
15
+#define __MODELREADERFEM1D_H
16
+
17
+#include "modelreader.h"
18
+
19
+namespace Lemma {
20
+
21
+
22
+// ===================================================================
23
+//        Class:  ModelReaderFem1D
24
+/// \brief
25
+/// \details
26
+// ===================================================================
27
+	class ModelReaderFem1D : public ModelReader {
28
+
29
+		friend std::ostream &operator<<(std::ostream &stream,
30
+			const ModelReaderFem1D &ob);
31
+
32
+	public:
33
+
34
+	// ====================  LIFECYCLE     =======================
35
+
36
+	static ModelReaderFem1D* New();
37
+
38
+	void Delete();
39
+
40
+	// ====================  OPERATORS     =======================
41
+
42
+	// ====================  OPERATIONS    =======================
43
+
44
+	// ====================  ACCESS        =======================
45
+
46
+	// ====================  INQUIRY       =======================
47
+
48
+
49
+
50
+	protected:
51
+
52
+	// ====================  LIFECYCLE     =======================
53
+
54
+	/// Default protected constructor.
55
+	ModelReaderFem1D (const std::string &name);
56
+
57
+	/// Default protected constructor.
58
+	~ModelReaderFem1D ();
59
+
60
+	void Release();
61
+
62
+	// ====================  DATA MEMBERS  =========================
63
+
64
+	private:
65
+
66
+}; // -----  end of class  ModelReaderFem1D  -----
67
+} // end of namespace Lemma
68
+#endif // __MODELREADERFEM1D_H

+ 83
- 0
LemmaCore/include/modelreadertem1d.h View File

@@ -0,0 +1,83 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     02/19/2011
11
+  @version  $Id: modelreadertem1d.h 87 2013-09-05 22:44:05Z tirons $
12
+ **/
13
+
14
+#ifndef __MODELREADERTEM1D_H
15
+#define __MODELREADERTEM1D_H
16
+
17
+#include "modelreader.h"
18
+
19
+namespace Lemma {
20
+
21
+// ===================================================================
22
+//        Class:  ModelReaderTem1D
23
+/// \brief Model reader class for forward modelling 1D TEM data
24
+/// \details This is a mostly abstract class.
25
+// ===================================================================
26
+class ModelReaderTem1D : public ModelReader {
27
+
28
+	friend std::ostream &operator<<(std::ostream &stream,
29
+		const ModelReaderTem1D &ob);
30
+
31
+	public:
32
+
33
+		// ====================  LIFECYCLE     =======================
34
+
35
+		static ModelReaderTem1D* New();
36
+
37
+		void Delete();
38
+
39
+		// ====================  OPERATORS     =======================
40
+
41
+		// ====================  OPERATIONS    =======================
42
+
43
+		//void ReadParameters(/* Pass file name */);
44
+
45
+		// ====================  ACCESS        =======================
46
+
47
+		// ====================  INQUIRY       =======================
48
+
49
+
50
+	protected:
51
+
52
+		// ====================  LIFECYCLE     =======================
53
+
54
+		/// Default protected constructor.
55
+		ModelReaderTem1D (const std::string &name);
56
+
57
+		/// Default protected constructor.
58
+		~ModelReaderTem1D ();
59
+
60
+		void Release();
61
+
62
+		/// Read in the Earth Model file and attach
63
+		//void ReadModel();
64
+
65
+		/// Read in the instrument parameters and attach
66
+		//void ReadInstrument();
67
+
68
+		/// Read in the waveform file (future)
69
+		//void ReadWaveform();
70
+
71
+		// ====================  DATA MEMBERS  =========================
72
+
73
+		//std::string modelfile;
74
+
75
+		//std::string instrumentfile;
76
+
77
+		//std::string waveformfile;
78
+
79
+	private:
80
+
81
+}; // -----  end of class  ModelReaderTem1D  -----
82
+} // end of namespace lemma
83
+#endif // __MODELREADERTEM1D_H

+ 116
- 0
LemmaCore/include/modelreadertem1dubc.h View File

@@ -0,0 +1,116 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     02/19/2011
11
+  @version  $Id: modelreadertem1dubc.h 87 2013-09-05 22:44:05Z tirons $
12
+ **/
13
+
14
+#ifndef __MODELREADERTEM1DUBC_H
15
+#define __MODELREADERTEM1DUBC_H
16
+
17
+#include "modelreadertem1d.h"
18
+
19
+namespace Lemma {
20
+
21
+// ===================================================================
22
+//        Class:  ModelReaderTem1DUBC
23
+/// \brief Model reader class for forward modelling 1D TEM data
24
+/// \details Reads UBC 1D TEM forward model format
25
+// ===================================================================
26
+class ModelReaderTem1DUBC : public ModelReaderTem1D {
27
+
28
+	friend std::ostream &operator<<(std::ostream &stream,
29
+		const ModelReaderTem1DUBC &ob);
30
+
31
+	public:
32
+
33
+		// ====================  LIFECYCLE     =======================
34
+
35
+		static ModelReaderTem1DUBC* New();
36
+
37
+		void Delete();
38
+
39
+		// ====================  OPERATORS     =======================
40
+
41
+		// ====================  OPERATIONS    =======================
42
+
43
+		void ReadParameters(const std::string &params);
44
+
45
+		// ====================  ACCESS        =======================
46
+
47
+		/// Attaches a LayeredEarthEM object
48
+		void SetEMEarth1D(LayeredEarthEM* earth);
49
+
50
+		/// Attaches a WireAntenna object
51
+		void SetTransmitter(WireAntenna *antennae);
52
+
53
+		/// Attaches a ReceiverPoints object
54
+		void SetReceiver(ReceiverPoints* receiver);
55
+
56
+		VectorXr GetTimes();
57
+
58
+		// ====================  INQUIRY       =======================
59
+
60
+
61
+	protected:
62
+
63
+		// ====================  LIFECYCLE     =======================
64
+
65
+		/// Default protected constructor.
66
+		ModelReaderTem1DUBC (const std::string &name);
67
+
68
+		/// Default protected constructor.
69
+		~ModelReaderTem1DUBC ();
70
+
71
+		void Release();
72
+
73
+		/// Read in the Earth Model file and attach
74
+		void ReadModel();
75
+
76
+		/// Read in the instrument parameters and attach
77
+		void ReadInstrument();
78
+
79
+		/// Read in the waveform file (future)
80
+		void ReadWaveform();
81
+
82
+		// ====================  DATA MEMBERS  =========================
83
+
84
+		std::string modelfile;
85
+
86
+		std::string instrumentfile;
87
+
88
+		std::string waveformfile;
89
+
90
+		WireAntenna* Trans;
91
+
92
+		ReceiverPoints* Receivers;
93
+
94
+		LayeredEarthEM* EarthMod;
95
+
96
+		/// Simulated noise flag
97
+		bool addednoise;
98
+
99
+		/// Simulated noise percentage
100
+		Real noisepercent;
101
+
102
+		/// Baseline threshold percentage
103
+		Real noisethresh;
104
+
105
+		/// Seed for random number generator
106
+		Real noiseseed;
107
+
108
+		VectorXr receivermoment;
109
+
110
+		VectorXr modtimes;
111
+
112
+	private:
113
+
114
+}; // -----  end of class  ModelReaderTem1DUBC  -----
115
+} // end of namespace lemma
116
+#endif // __MODELREADERTEM1DUBC_H

+ 25
- 0
LemmaCore/include/modules.h View File

@@ -0,0 +1,25 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     11/26/2010
11
+  @version  $Id: modules.h 87 2013-09-05 22:44:05Z tirons $
12
+ **/
13
+
14
+/**
15
+      \defgroup Merlin Merlin
16
+      @brief    Merlin is a nuclear magnetic resonance module.
17
+      @details  Much of Merlin focuses on surface, or earth's field NMR (SNMR)
18
+       but many of the algorithms may be extended to general NMR.
19
+
20
+     \defgroup Wavelet Wavelet
21
+      @brief    A wavlet transfer module.
22
+      @details  Provides multidimensional wavelet transforms and solver routines.
23
+ */
24
+
25
+

+ 352
- 0
LemmaCore/include/octreegrid.h View File

@@ -0,0 +1,352 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     03/19/2010
11
+  @version  $Id: octreegrid.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  OCTREEGRID_INC
15
+#define  OCTREEGRID_INC
16
+
17
+// This class depends on VTK!
18
+
19
+#ifdef  LEMMAUSEVTK
20
+#include "grid.h"
21
+#include "vtkHyperOctree.h"        // In Filtering
22
+#include "vtkHyperOctreeCursor.h"
23
+#include "vtkHyperOctreeSampleFunction.h"
24
+#include "vtkImplicitFunction.h"
25
+#include "vtkCell.h"
26
+#include "vtkGenericCell.h"
27
+
28
+#ifdef  LEMMA_SINGLE_PRECISION
29
+#include "vtkFloatArray.h"
30
+#else      // -----  not LEMMA_SINGLE_PRECISION  -----
31
+#include "vtkDoubleArray.h"
32
+#endif     // -----  not LEMMA_SINGLE_PRECISION  -----
33
+
34
+#include "kernel.h"
35
+#include "receiverpoints.h"
36
+#include "receivercubes.h"
37
+#include "layeredearth.h"
38
+//#include "layeredearthnmr.h"
39
+#include "inversesolver.h"
40
+
41
+#include "FastDelegate.h"
42
+#include "FastDelegateBind.h"
43
+
44
+namespace Lemma {
45
+
46
+    // forward declaration
47
+    class InverseSolver ;
48
+
49
+    // ===================================================================
50
+    //        Class:  OctreeGrid
51
+    /** An Octree class, builds off VtkHyperOctree so this class can
52
+        only be used when compiled with VTK libs.
53
+        An Octree is a heirarchial 3D mesh with rectangular cells containing
54
+        either 0 or 8 children.
55
+     */
56
+    // ===================================================================
57
+    class OctreeGrid : public Grid {
58
+
59
+        friend class InverseSolver;
60
+        //friend class SNMRInversion1D;        // From Merlin Module
61
+
62
+        friend std::ostream &operator<<(std::ostream &stream,
63
+                const OctreeGrid &ob);
64
+
65
+        public:
66
+
67
+            // ====================  LIFECYCLE     =======================
68
+
69
+            /**
70
+             * new grid octreee
71
+             */
72
+            static OctreeGrid* New();
73
+
74
+            /**
75
+             * @copybrief LemmaObject::Delete()
76
+             * @copydetails LemmaObject::Delete()
77
+             */
78
+            void Delete();
79
+
80
+            // ====================  OPERATORS     =======================
81
+
82
+
83
+            // ====================  ACCESS        =======================
84
+
85
+            /** Sets the kernel function to be used to make the mesh.
86
+             *  @param[in] kern is a kernel that is used to generate a mesh.
87
+             */
88
+            void SetKernel(Kernel* kern);
89
+
90
+            /// Sets a 1D model associated with this kernel.
91
+            /// @param[in] model1d is a pointer to a LayeredEarth model that
92
+            /// will be used to pre-subdivide leaves that overlap several
93
+            /// layers.
94
+            void SetLayeredEarth(LayeredEarth* model1d);
95
+
96
+            /** Sets the size of the mesh
97
+                @param[in] size is the size of the mesh. The mesh must start at
98
+                [0,0,0] and goes to [sizex, sizey, sizez].
99
+             */
100
+            void SetSize(const Vector3r& size);
101
+
102
+            /** Sets the origin of the mesh
103
+                @param[in] origin is the origin of the mesh.
104
+             */
105
+            void SetOrigin(const Vector3r& origin);
106
+
107
+            /** Sets the minimum depth to model. This must be greater than 0.
108
+                @param[in] depth is the new minimum depth.
109
+             */
110
+            void SetMinimumDepth(const Real& depth);
111
+
112
+            /** Fills in the leaf data with the kernel sensitivity
113
+             */
114
+            void FillMeshWithKernel();
115
+
116
+            /** Fills in the leaf data with the kernel sensitivity
117
+             */
118
+            void FillMeshWithKernel(vtkImplicitFunction* Impl);
119
+
120
+            /** Sets the size of the mesh
121
+             */
122
+            void SetSize(const Real &x, const Real &y, const Real &z);
123
+
124
+            /** Generates mesh to specified tolerance.
125
+             *  @param[in] tol is the kernel tolerance.
126
+             */
127
+            void GenerateMesh(const Real &tol);
128
+
129
+
130
+            /** Generates a mesh to specified tolerance, but initially splits
131
+             *  based on implicit function.
132
+             *  @param[in] tol is the kernel tolerance.
133
+             *  @param[in] Impl is the implicit dataset used for initial
134
+             *  subdivision
135
+             *  @param[in] impltol is the tolerance for the initial model based
136
+             *  subdividing.
137
+             */
138
+            void GenerateMesh(const Real& tol, vtkImplicitFunction* Impl,
139
+                              const Real& impltol);
140
+
141
+            /** Generates an Octree mesh using a pre-sampled input Octree Dataset.
142
+                Speeds up repeated kernel calculations when the underlying model in
143
+                the above ImplicitFunction needs to be called often or is complex.
144
+             */
145
+            void GenerateMesh(const Real& tol, vtkImplicitFunction* Impl,
146
+                    vtkHyperOctreeSampleFunction* OctSamp);
147
+
148
+            /** Evaluates the kernel on the mesh. In some cases this is the same thing
149
+                as generate mesh, but if more that one calculation are needed on a
150
+                mesh you can use this method. It interfaces with the kernels by
151
+                calling
152
+             */
153
+            Complex EvaluateKernelOnMesh();
154
+
155
+            /** Returns a receiver cube class that represents the same Geometry as the
156
+                HyperOctree. This is useful as it can be passed directly to em1dearth,
157
+                and currently, an Octree cannot. But this requires storage of all the
158
+                cell volumes and locations. In the future, you should be able to pass
159
+                around this class just like a ReceiverCubes.
160
+             */
161
+            void ReceiverCubeRepresentation();
162
+
163
+            /** Returns the receiver cube class. */
164
+            ReceiverCubes* GetReceiverCubes();
165
+
166
+            /** returns the kernel sum from generation */
167
+            Complex GetKernelSum();
168
+
169
+            /** Accessor to underlying vtkClass.
170
+             *  @return a vtkHyperOctree that can be used for visualization.
171
+             */
172
+            vtkHyperOctree* GetVtkHyperOctree( );
173
+
174
+            /** Traverse the data structure and call a function at each leaf
175
+             */
176
+            void TraverseAndCall(InverseSolver* Inverse);
177
+
178
+            /** Traverse the data structure and call a function at each leaf
179
+             */
180
+            void TraverseAndCall( vtkImplicitFunction* Impl );
181
+
182
+            /**
183
+             */
184
+            void TraverseLeaves(vtkImplicitFunction* Impl);
185
+
186
+            /**
187
+             */
188
+            void FollowExistingTree(vtkHyperOctree* Leader, vtkHyperOctreeCursor* LeaderCursor,
189
+                    vtkImplicitFunction* Impl);
190
+
191
+            // ====================  OPERATIONS    =======================
192
+
193
+            /** Binds any derived member function of a derived class of
194
+                LayeredEarth to SampleScalarFromLayeredEarthFD. This function is then
195
+                used to sample the Octree mesh for that parameter. The member function
196
+                needs to be of the type GetLayerXXX(const int Layer& lay).
197
+                @param[in] earth is a pointer to a derived class of LayeredEarth
198
+                @param[in] fcnptr is a function pointer to a member function. It
199
+                should be called like &LayeredEarthNMR::GetLayerPorosity
200
+                @param[in] name is a std::string identifier.
201
+             */
202
+            template <class Derived>
203
+            void SampleScalarFromLayeredEarth(LayeredEarth* earth,
204
+                    Real (Derived::*fcnptr)(const int& id), const std::string &name) {
205
+
206
+                SampleScalarFromLayeredEarthFD.bind(static_cast<Derived*>(earth), fcnptr);
207
+                GetLayerInt.bind(earth, &LayeredEarth::GetLayerAtThisDepth);
208
+                // TODO, don't use KernelArray, instead create new Array, and set it
209
+                // in there. Then delete?
210
+                this->KernelArray->SetName(name.c_str());
211
+                this->KernelArray->SetNumberOfTuples(Octree->GetNumberOfLeaves());
212
+                SampleScalar();
213
+                this->Octree->GetLeafData()->SetScalars( KernelArray );
214
+                this->Octree->GetLeafData()->AddArray( KernelArray );
215
+            }
216
+
217
+            /** Sends cursor to root
218
+             */
219
+            void CursorToRoot();
220
+
221
+            // ====================  INQUIRY       =======================
222
+
223
+        protected:
224
+
225
+            // ====================  LIFECYCLE     =======================
226
+
227
+            /** Default protected constructor. */
228
+            OctreeGrid (const std::string &name);
229
+
230
+            /** Default protected constructor. */
231
+            ~OctreeGrid ();
232
+
233
+            /**
234
+             * @copybrief LemmaObject::Release()
235
+             * @copydetails LemmaObject::Release()
236
+             */
237
+            void Release();
238
+
239
+            // ====================  OPERATIONS    =======================
240
+
241
+            /** Used internally. The leaf data is saved and then set as the vtk leaf
242
+             *  data.
243
+             */
244
+            void SetLeafDataFromGridCreation();
245
+
246
+            /** Return position of leaf, returns centre location
247
+             */
248
+            void GetPosition( Real* p );
249
+
250
+            /** Used to fill leaf data with a scalar value from a layered earth
251
+             *  model
252
+             */
253
+            fastdelegate::FastDelegate1< const int&, Real > SampleScalarFromLayeredEarthFD;
254
+
255
+            /** Used to get the Layer of delagated model.
256
+             */
257
+            fastdelegate::FastDelegate1< const Real&, int >  GetLayerInt;
258
+
259
+            /** Recursively determines the mesh to use
260
+             */
261
+            void EvaluateKids( );
262
+
263
+            /** Recursively determines the mesh to use
264
+                @param[in] kval is the current leaf kernel value
265
+                           which may be reused in analysis.
266
+             */
267
+            void EvaluateKids( Complex kval );
268
+
269
+            /** Same as above, but uses an implict function.
270
+             */
271
+            void EvaluateKids (vtkImplicitFunction* Impl);
272
+
273
+            /** Same as above, but lets function value be passed directly
274
+             */
275
+            void EvaluateKids (const Real& fval, vtkImplicitFunction* Impl);
276
+
277
+            /** Same as above but is passed a static fval to reuse. Useful when underlying model is smooth
278
+             */
279
+            void EvaluateKidsStatic(const Real& fval);
280
+
281
+            /** Same as above, but lets function value be passed directly
282
+             */
283
+            void SampleFunction(vtkImplicitFunction* Impl);
284
+
285
+            /** Recursively determines the mesh to use
286
+             */
287
+            void FillGrid( );
288
+
289
+            /** Recursively determines the mesh to use
290
+             */
291
+            void FillGrid(vtkImplicitFunction* Impl);
292
+
293
+            /** Used internally to build a receiver cube representation
294
+             */
295
+            void AssembleReceiverCubes( );
296
+
297
+            /** Samples a scalar from a LayeredEarth object. Used internally and calls
298
+             *  SampleScalarFromLayeredEarthFD, which can be set using
299
+             *  SampleScalarFromLayeredEarth.
300
+             */
301
+            void SampleScalar();
302
+
303
+
304
+
305
+            // Returns ReceiverPoints for the Octree.
306
+            //void ComputeFieldOnOctree( WireAntenna* loop );
307
+
308
+            // ====================  DATA MEMBERS  =========================
309
+
310
+        private:
311
+
312
+            Vector3r                Size;
313
+            Vector3r                Origin;
314
+            Vector3r                step;
315
+            Vector3r                cpos;
316
+
317
+            int                     level;
318
+            int                     maxlevel;
319
+            int                     index;
320
+            int                     counter;
321
+
322
+            Real                    cvol;
323
+            Real                    tvol;
324
+            Real                    tol;
325
+            Complex                 KernelSum;
326
+
327
+            Eigen::Matrix<Real, 8, 3> Posadd;
328
+
329
+            std::vector<Real>       leafdata;
330
+            std::vector<vtkIdType>  leafids;
331
+
332
+            Kernel                 *SenseKernel;
333
+            ReceiverCubes          *Cubes;
334
+            LayeredEarth           *Model1D;
335
+
336
+            vtkHyperOctree               *Octree;
337
+            vtkHyperOctreeCursor         *Cursor;
338
+            vtkHyperOctreeSampleFunction *OctSamp;
339
+
340
+            #ifdef  LEMMA_SINGLE_PRECISION
341
+            vtkFloatArray          *KernelArray;
342
+            #else      // -----  not LEMMA_SINGLE_PRECISION  -----
343
+            vtkDoubleArray         *KernelArray;
344
+            #endif     // -----  not LEMMA_SINGLE_PRECISION  -----
345
+            vtkDataArray           *SampleArray;
346
+
347
+    }; // -----  end of class  OctreeGrid  -----
348
+
349
+}       // -----  end of Lemma  name  -----
350
+
351
+#endif     // -----  not LEMMAUSEVTK  -----
352
+#endif   // ----- #ifndef OCTREEGRID_INC  -----

+ 62
- 0
LemmaCore/include/pulse.h View File

@@ -0,0 +1,62 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     02/05/2010
11
+  @version  $Id: pulse.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  _PULSE_H_INC
15
+#define  _PULSE_H_INC
16
+
17
+#include "LemmaObject.h"
18
+
19
+namespace Lemma {
20
+
21
+    // =======================================================================
22
+    //        Class:  Pulse
23
+    /// \brief Pure abstract class defining interace to some sort of pulse.
24
+    /// \details
25
+    // =======================================================================
26
+    class Pulse : public LemmaObject {
27
+
28
+        public:
29
+
30
+            /** Recursively prints information about this object
31
+             */
32
+            friend std::ostream &operator<<(std::ostream &stream,
33
+                    const Pulse &ob);
34
+
35
+            // ====================  LIFECYCLE     ===========================
36
+
37
+            // ====================  OPERATORS     ===========================
38
+
39
+            // ====================  OPERATIONS    ===========================
40
+
41
+            // ====================  ACCESS        ===========================
42
+
43
+            // ====================  INQUIRY       ===========================
44
+
45
+            // ====================  DATA MEMBERS  ===========================
46
+
47
+        protected:
48
+
49
+            // ====================  LIFECYCLE     ===========================
50
+
51
+            /// Default protected constructor.
52
+            Pulse (const std::string &name);
53
+
54
+            /// Default protected constructor.
55
+            ~Pulse ();
56
+
57
+    }; // -----  end of class  Pulse  -----
58
+
59
+}       // -----  end of Lemma  name  -----
60
+
61
+
62
+#endif   // ----- #ifndef _PULSE_H_INC  -----

+ 111
- 0
LemmaCore/include/quasinewtonbfgs.h View File

@@ -0,0 +1,111 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     08/09/2010
11
+  @version  $Id: quasinewtonbfgs.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  QUASINEWTONBFGS_INC
15
+#define  QUASINEWTONBFGS_INC
16
+
17
+#include "inversesolver.h"
18
+
19
+namespace Lemma {
20
+
21
+
22
+    // ===================================================================
23
+    //  Class:  QuasiNewtonBFGS
24
+    /**
25
+      @class  QuasiNewtonBFGS
26
+      \brief  Implimentation of a quasi-newton BFGS solver applied to
27
+              inverse problems.
28
+      \details Based of the algorithm described in Nocedal and Wright book.
29
+     */
30
+    // ===================================================================
31
+    class QuasiNewtonBFGS : public InverseSolver {
32
+
33
+        friend  std::ostream &operator<<(std::ostream &stream,
34
+                const QuasiNewtonBFGS &ob);
35
+
36
+        public:
37
+
38
+            // ====================  LIFECYCLE     =======================
39
+
40
+            /** Returns a pointer to a new object of type QuasiNewtonBFGS.
41
+             * It allocates all necessary memory.
42
+             */
43
+            static QuasiNewtonBFGS* New();
44
+
45
+            /**
46
+             * @copybrief LemmaObject::Delete()
47
+             * @copydetails LemmaObject::Delete()
48
+             */
49
+            void Delete();
50
+
51
+            // ====================  OPERATORS     =======================
52
+
53
+            // ====================  OPERATIONS    =======================
54
+
55
+            // ====================  ACCESS        =======================
56
+
57
+            // ====================  INQUIRY       =======================
58
+
59
+            /** @copybrief InverseSolver::NumberOfIterations()
60
+             *  @copydetails InverseSolver::NumberOfIterations()
61
+             */
62
+            int NumberOfIterations();
63
+
64
+            /** @copybrief InverseSolver::Success()
65
+             *  @copydetails InverseSolver::Success()
66
+             */
67
+            bool Success();
68
+
69
+            /** @copybrief InverseSolver::GetPhiMVector()
70
+             *  @copydetails InverseSolver::GetPhiMVector()
71
+             */
72
+            VectorXr GetPhiMVector();
73
+
74
+            /** @copybrief InverseSolver::GetPhiDVector()
75
+             *  @copydetails InverseSolver::GetPhiDVector()
76
+             */
77
+            VectorXr GetPhiDVector();
78
+
79
+            /// TODO remove this, test
80
+            void PrintNorm();
81
+
82
+        protected:
83
+
84
+            // ====================  LIFECYCLE     =======================
85
+
86
+            /// Default protected constructor.
87
+            QuasiNewtonBFGS (const std::string& cname);
88
+
89
+            /// Default protected constructor.
90
+            ~QuasiNewtonBFGS ();
91
+
92
+            /**
93
+             * @copybrief LemmaObject::Release()
94
+             * @copydetails LemmaObject::Release()
95
+             */
96
+            void Release();
97
+
98
+            // ====================  OPERATIONS    =======================
99
+
100
+            /// Just a filler
101
+            void FillInG(const Vector3r& pos, const Vector3r& step);
102
+
103
+            // ====================  DATA MEMBERS  =========================
104
+
105
+        private:
106
+
107
+    }; // -----  end of class  QuasiNewtonBFGS  -----
108
+
109
+}		// -----  end of Lemma  name  -----
110
+
111
+#endif   // ----- #ifndef QUASINEWTONBFGS_INC  -----

+ 169
- 0
LemmaCore/include/receivercubes.h View File

@@ -0,0 +1,169 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     06/17/2010
11
+  @version  $Id: receivercubes.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  RECEIVERCUBES_INC
15
+#define  RECEIVERCUBES_INC
16
+
17
+#include "receiverpoints.h"
18
+
19
+namespace Lemma {
20
+
21
+
22
+    // ===================================================================
23
+    //        Class:  ReceiverCubes
24
+    /** This class builds on Reciver points, but supports a cube around
25
+     * each point. It is a direct descendent and may be used wherever
26
+     * ReceiverPoints is used
27
+     */
28
+    // ===================================================================
29
+    class ReceiverCubes : public ReceiverPoints {
30
+
31
+        friend std::ostream &operator<<(std::ostream &stream,
32
+                const ReceiverCubes &ob);
33
+
34
+        friend class EmDipEarth1D;
35
+
36
+        public:
37
+
38
+            // ====================  LIFECYCLE     =======================
39
+
40
+            /**
41
+             *  Returns pointer to new DipoleSource. Location is
42
+             *  initialized to (0,0,0) type and polarization are
43
+             *  initialized  to nonworking values that will throw
44
+             *  exceptions if used.
45
+             */
46
+            static ReceiverCubes* New();
47
+
48
+            /**
49
+             * @copybrief LemmaObject::Delete()
50
+             * @copydetails LemmaObject::Delete()
51
+             */
52
+            void Delete();
53
+
54
+            // ====================  OPERATORS     =======================
55
+
56
+            // ====================  OPERATIONS    =======================
57
+
58
+            /** Sets the number of reciver cubes.
59
+             *  This method also resizes all the dynamic vectors in the class
60
+             *  to support this size.
61
+             *  @param[in] nrec is the number of cubes in the class.
62
+             */
63
+            void SetNumberOfReceivers(const int &nrec);
64
+
65
+            /** Sets the length of the x dimension of a single cube.
66
+             * @param[in] i is the cube number.
67
+             * @param[in] lx is the length of this cube, in this dimension.
68
+             */
69
+            void SetLengthX(const int &i, const Real &lx);
70
+
71
+            /** Sets the length of the y dimension of a single cube.
72
+             * @param[in] i is the cube number.
73
+             * @param[in] ly is the length of this cube, in this dimension.
74
+             */
75
+            void SetLengthY(const int &i, const Real &ly);
76
+
77
+            /** Sets the length of the z dimension of a single cube.
78
+             * @param[in] i is the cube number.
79
+             * @param[in] lz is the length of this cube, in this dimension.
80
+             */
81
+            void SetLengthZ(const int &i, const Real &lz);
82
+
83
+            /** Sets the lengths of all three dimensions of a single cube.
84
+             * @param[in] i is the cube number.
85
+             * @param[in] lx is the length of this cube, in this dimension.
86
+             * @param[in] ly is the length of this cube, in this dimension.
87
+             * @param[in] lz is the length of this cube, in this dimension.
88
+             */
89
+            void SetLength(const int &i, const Real& lx, const Real& ly,
90
+                            const Real &lz);
91
+
92
+            /** Sets the length of the x dimension of a single cube.
93
+             * @param[in] i is the cube number.
94
+             * @param[in] V is a vector of lenths.
95
+             */
96
+            void SetLength(const int &i, const Vector3r &V);
97
+
98
+
99
+            /** Gets the x dimension of cube i
100
+              * @param[in] i is the cube in quesion
101
+              * @return The legth of the x dimension of cube i
102
+              */
103
+            Real GetLengthX(const int &i);
104
+
105
+            /** Gets the y dimension of cube i
106
+              * @param[in] i is the cube in quesion
107
+              * @return The length of the y dimension of cube i
108
+              */
109
+            Real GetLengthY(const int &i);
110
+
111
+            /** Gets the z dimension of cube i
112
+              * @param[in] i is the cube in quesion
113
+              * @return The length of the z dimension of cube i
114
+              */
115
+            Real GetLengthZ(const int &i);
116
+
117
+            /** Gets the z dimension of cube i
118
+              * @param[in] i is the cube in quesion
119
+              * @return A vector of the lengths of the cube
120
+              */
121
+            Vector3r GetLength(const int& i);
122
+
123
+            /** Returns the volume of a cube
124
+              * @param[in] i is the cube of interest
125
+              * @return is the volume
126
+              */
127
+            Real GetVolume(const int&i);
128
+
129
+            /** Returns the volume of all the receiver cubes.
130
+              */
131
+            Real GetVolumeSum();
132
+
133
+            // ====================  ACCESS        =======================
134
+
135
+            // ====================  INQUIRY       =======================
136
+
137
+            // Returns the volume of a cube.
138
+            //Real GetCubeVolume(const int&i);
139
+            //VectorXr GetCubeVolumes();
140
+
141
+        protected:
142
+
143
+            // ====================  LIFECYCLE     =======================
144
+
145
+            /// Default protected constructor.
146
+            ReceiverCubes (const std::string &name);
147
+
148
+            /// Default protected constructor.
149
+            ~ReceiverCubes ();
150
+
151
+            /**
152
+             * @copybrief LemmaObject::Release()
153
+             * @copydetails LemmaObject::Release()
154
+             */
155
+            void Release();
156
+
157
+            // ====================  DATA MEMBERS  =========================
158
+
159
+            /// Dimension of each cube stored here, first indice is x, second y, and
160
+            /// third z
161
+            Vector3Xr Lengths;
162
+
163
+        private:
164
+
165
+    }; // -----  end of class  ReceiverCubes  -----
166
+
167
+}       // -----  end of Lemma  name  -----
168
+
169
+#endif   // ----- #ifndef RECEIVERCUBES_INC  -----

+ 281
- 0
LemmaCore/include/receiverpoints.h View File

@@ -0,0 +1,281 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     12/02/2009
11
+  @version  $Id: receiverpoints.h 199 2014-12-29 19:25:20Z tirons $
12
+ **/
13
+
14
+#ifndef __RECEIVERPOINTS_H
15
+#define __RECEIVERPOINTS_H
16
+
17
+#ifdef LEMMAUSEVTK
18
+#include "vtkPointData.h"
19
+#include "vtkFieldData.h"
20
+#include "vtkGlyph3D.h"
21
+#include "vtkArrowSource.h"
22
+#include "vtkActor.h"
23
+#include "vtkPolyDataMapper.h"
24
+#include "vtkPoints.h"
25
+#include "vtkPolyData.h"
26
+#include "vtkDoubleArray.h"
27
+#include "vtkDataObject.h"
28
+#endif
29
+
30
+#include "LemmaObject.h"
31
+#include "dipolesource.h"
32
+
33
+#ifdef HAVE_YAMLCPP
34
+#include "yaml-cpp/yaml.h"
35
+#endif
36
+
37
+namespace Lemma {
38
+
39
+    // =======================================================================
40
+    //        Class:  ReceiverPoints
41
+    /// \brief  Points in the subsurface to make EM calculations,
42
+    ///  more general than the grids.
43
+    // =======================================================================
44
+    class ReceiverPoints : public LemmaObject {
45
+
46
+        public:
47
+
48
+            // ====================    FRIENDS     ===========================
49
+
50
+            /** Stream operator printing out information about this class.
51
+             */
52
+            friend std::ostream &operator<<(std::ostream &stream,
53
+                        const ReceiverPoints &ob);
54
+
55
+            friend class EMEarth1D;
56
+            friend class DipoleSource;
57
+
58
+            // ====================  LIFECYCLE     ===========================
59
+
60
+            /**
61
+             *  Returns pointer to new DipoleSource. Location is
62
+             *  initialized to (0,0,0) type and polarization are
63
+             *  initialized  to nonworking values that will throw
64
+             *  exceptions if used.
65
+             */
66
+            static ReceiverPoints* New();
67
+
68
+
69
+            /**
70
+             * @copybrief LemmaObject::Delete()
71
+             * @copydetails LemmaObject::Delete()
72
+             */
73
+            void Delete();
74
+
75
+            // ====================  OPERATORS     ===========================
76
+
77
+            // ====================  OPERATIONS    ===========================
78
+
79
+            // ====================  ACCESS        ===========================
80
+
81
+            /// Sets the number of receivers
82
+            virtual void SetNumberOfReceivers(const int &nrec);
83
+
84
+            /// Returns the location of a single receiver as an Eigen Vector
85
+            void SetLocation(const int& nrec, const Vector3r& loc);
86
+
87
+            /// Returns the location of a single receiver as an Eigen Vector
88
+            void SetLocation(const int& nrec, const Real& xp, const Real& yp,
89
+                            const Real& zp);
90
+
91
+            // ====================  INQUIRY       ===========================
92
+
93
+            /// Returns the number of receiverpoints.
94
+            int GetNumberOfReceivers();
95
+
96
+            /// Returns all the receiver locations as a 3 X matrix
97
+            Vector3Xr GetLocations();
98
+
99
+            /// Returns all the receiver locations as a general matrix, useful for python wrapper
100
+            MatrixXr GetLocationsMat();
101
+
102
+            /// Returns the E field for all locations
103
+            /// nfreq is the freqency desired
104
+            Vector3Xcr GetEfield(const int &nfreq);
105
+
106
+            /// Returns the E field for all locations
107
+            /// nfreq is the freqency desired, cast to general dynamic matrix, for python interoperability
108
+            MatrixXcr GetEfieldMat(const int &nfreq);
109
+
110
+            /// Returns the H field for all locations
111
+            /// nfreq is the freqency desired, cast to general dynamic matrix, for python interoperability
112
+            MatrixXcr GetHfieldMat(const int &nfreq);
113
+
114
+            /// Returns the H field for all locations
115
+            /// nfreq is the freqency desired
116
+            Vector3Xcr GetHfield(const int &nfreq);
117
+
118
+            /// Returns all of the computed H fields. Every frequency
119
+            std::vector<Vector3Xcr> GetHfield( );
120
+
121
+            /// Returns all of the computed E fields. Every frequency
122
+            std::vector<Vector3Xcr> GetEfield( );
123
+
124
+            /// Returns the E field of a single receiver as an Eigen Vector
125
+            /// nfreq is the freqency desired
126
+            Vector3cr GetEfield(const int &nfreq, const int& loc);
127
+
128
+            /// Returns the H field of a single receiver as an Eigen Vector
129
+            /// nfreq is the freqency desired
130
+            Vector3cr GetHfield(const int &nfreq, const int& loc);
131
+
132
+            /// Returns the B field of a single receiver as an Eigen Vector
133
+            /// nfreq is the freqency desired
134
+            Vector3cr GetBfield(const int &nfreq, const int& loc);
135
+
136
+            #ifdef LEMMAUSEVTK
137
+            /// Returns vtk Glyph actor that can be placed into scenes
138
+            vtkActor* GetVtkGlyphActor(const FIELDTYPE &ftype,
139
+                const Real& clip, const Real &scale,
140
+                const int &nfreq);
141
+
142
+            /// Returns a vtk Data Object that can easily be plotted
143
+            vtkDataObject * GetVtkDataObject(const FIELDTYPE &ftype,
144
+                const int& nbin,
145
+                const int& start, const int& end,
146
+                const FIELDCOMPONENT& fcomp,
147
+                const SPATIALCOORDINANT& scord);
148
+
149
+            /// Returns a vtk Data Object that can easily be plotted
150
+            vtkDataObject * GetVtkDataObjectFreq(const FIELDTYPE &ftype,
151
+                const int& nrec,
152
+                const int& fstart, const int& fend,
153
+                const FIELDCOMPONENT& fcomp,
154
+                const VectorXr& Freqs);
155
+            #endif
156
+
157
+            /// Returns the location of a single receiver as an Eigen Vector
158
+            Vector3r GetLocation(const int& loc);
159
+
160
+            /// Returns the x component of the location
161
+            Real GetLocationX(const int& loc);
162
+
163
+            /// Returns the y component of the location
164
+            Real GetLocationY(const int& loc);
165
+
166
+            /// Returns the z component of the location
167
+            Real GetLocationZ(const int& loc);
168
+
169
+            /// Resets fields
170
+            void ClearFields();
171
+
172
+            /// Sets the mask variable to true for this point.
173
+            void MaskPoint(const int& i);
174
+
175
+            /// Turns the mask off for this point.
176
+            void UnMaskPoint(const int& i);
177
+
178
+            /// Removes making on all points
179
+            void UnMaskAllPoints();
180
+
181
+            /// Returns the mask for this point
182
+            int GetMask(const int& i);
183
+
184
+            #ifdef HAVE_YAMLCPP
185
+        	/**
186
+             *  Uses YAML to serialize this object.
187
+             *  @return a YAML::Node
188
+             */
189
+            YAML::Node Serialize() const;
190
+
191
+            /**
192
+             *   Constructs an object from a YAML::Node.
193
+             */
194
+            static ReceiverPoints* DeSerialize(const YAML::Node& node);
195
+            #endif
196
+
197
+        protected:
198
+
199
+            // ====================  LIFECYCLE     ===========================
200
+
201
+            /// Default protected constructor.
202
+            ReceiverPoints (const std::string& name);
203
+
204
+            #ifdef HAVE_YAMLCPP
205
+            /// Default protected constructor.
206
+            ReceiverPoints (const YAML::Node& node);
207
+            #endif
208
+
209
+            /// Default protected constructor.
210
+            ~ReceiverPoints ();
211
+
212
+            /**
213
+             * @copybrief LemmaObject::Release()
214
+             * @copydetails LemmaObject::Release()
215
+             */
216
+            void Release();
217
+
218
+            // ====================  OPERATIONS    ===========================
219
+
220
+            /// Sets the number of H bins. These bins are often frequencies.
221
+            void SetNumberOfBinsH(const int& nbins);
222
+
223
+            /// Sets the number of E bins. These bins are often frequencies.
224
+            void SetNumberOfBinsE(const int& nbins);
225
+
226
+            /** Internal function that resizes the EField data structure */
227
+            void ResizeEField();
228
+
229
+            /** Internal function that resizes the HField data structure */
230
+            void ResizeHField();
231
+
232
+            /// Sets the value of the E field
233
+            void SetEfield(const int &nfreq, const int& loc,
234
+                const Complex &ex, const Complex &ey, const Complex &ez);
235
+
236
+            /// Sets the value of the H field
237
+            void SetHfield(const int &nfreq, const int& loc,
238
+                const Complex &hx, const Complex &hy, const Complex &hz);
239
+
240
+            /// Appends the value of the E field. This method is not
241
+            /// thread safe.
242
+            void AppendEfield(const int&nfreq, const int& loc,
243
+                const Complex &ex, const Complex &ey, const Complex &ez);
244
+
245
+            /// Appends the value of the H field. This method is not
246
+            /// thread safe.
247
+            void AppendHfield(const int &nfreq, const int& loc,
248
+                const Complex &hx, const Complex &hy, const Complex &hz);
249
+
250
+            // ====================  DATA MEMBERS  ===========================
251
+
252
+            /// Number of receivers
253
+            int                         NumberOfReceivers;
254
+
255
+            /// Number of fields
256
+            int                         NumberOfBinsE;
257
+
258
+            /// Number of fields
259
+            int                         NumberOfBinsH;
260
+
261
+            /// Used to mask this point so no computation is made at
262
+            /// this point.
263
+            VectorXi                    Mask;
264
+
265
+            /// Locations of receivers
266
+            Vector3Xr                   Locations;
267
+
268
+        private:
269
+
270
+            // NOTE, these are not serialized in output!
271
+
272
+            /// Electric field at receiver locations
273
+            std::vector<Vector3Xcr>     Efield;
274
+
275
+            /// H field at receiver locations
276
+            std::vector<Vector3Xcr>     Hfield;
277
+
278
+    }; // -----  end of class  ReceiverPoints  -----
279
+}
280
+
281
+#endif // __RECEIVERPOINTS

+ 237
- 0
LemmaCore/include/rectilineargrid.h View File

@@ -0,0 +1,237 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     10/28/2010
11
+  @version  $Id: rectilineargrid.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  RECTILINEARGRID_INC
15
+#define  RECTILINEARGRID_INC
16
+
17
+#include "grid.h"
18
+
19
+namespace Lemma {
20
+
21
+    // ===================================================================
22
+    //  Class:  RectilinearGrid
23
+    /**
24
+      @class
25
+      \brief   Impliments a rectilinear grid.
26
+      \details A rectilinear grid can vary regularily in space but must be
27
+               constant variation across each dimension. In this way three
28
+               vectors can define the entire grid, and each cell is right
29
+               aligned with all its neighbours.
30
+     */
31
+    // ===================================================================
32
+    class RectilinearGrid : public Grid {
33
+
34
+        friend std::ostream &operator<<(std::ostream &stream,
35
+			const RectilinearGrid &ob);
36
+
37
+        public:
38
+
39
+            // ====================  LIFECYCLE     =======================
40
+
41
+            /** Returns a pointer to a new object of type RectilinearGrid.
42
+             * It allocates all necessary memory.
43
+             */
44
+            static RectilinearGrid* New();
45
+
46
+            /**
47
+             *  @copybrief   LemmaObject::Delete()
48
+             *  @copydetails LemmaObject::Delete()
49
+             */
50
+            void Delete();
51
+
52
+            // ====================  OPERATORS     =======================
53
+
54
+            // ====================  OPERATIONS    =======================
55
+
56
+            /**
57
+             *  Sets the dimensions in x, y and z
58
+             *  @param[in] nx is the number of cells in x
59
+             *  @param[in] ny is the number of cells in y
60
+             *  @param[in] nz is the number of cells in z
61
+             */
62
+            void SetDimensions (const int &nx, const int &ny, const int &nz);
63
+
64
+            /**
65
+             *  Sets the offset in x, y and z. This sets the corner position of the top SW corner.
66
+             *  @param[in] ox is the number of cells in x
67
+             *  @param[in] oy is the number of cells in y
68
+             *  @param[in] oz is the number of cells in z
69
+             */
70
+            void SetOffset (const Real &ox, const Real &oy, const Real &oz);
71
+
72
+            /**
73
+             *  Sets the spacing in x, y and z
74
+             *  @param[in] dx is a Vector of cell spacing in x, must be same
75
+             *  size ad nx
76
+             *  @param[in] dy is a Vector of cell spacing in x, must be same
77
+             *  size ad ny
78
+             *  @param[in] dz is a Vector of cell spacing in x, must be same
79
+             *  size ad nz
80
+             */
81
+            void SetSpacing (const VectorXr &dx, const VectorXr &dy,
82
+                const VectorXr &dz);
83
+
84
+
85
+            // ====================  ACCESS        =======================
86
+
87
+            /** Returns the number of cells in x
88
+             *  @return number of cells in x
89
+             */
90
+            int GetNx();
91
+
92
+            /** Returns the number of cells in y
93
+             *  @return number of cells in y
94
+             */
95
+            int GetNy();
96
+
97
+            /** Returns the number of cells in z
98
+             *  @return number of cells in z
99
+             */
100
+            int GetNz();
101
+
102
+            /** Returns the offset of cells in x
103
+             *  @return offset of cells in x
104
+             */
105
+            Real GetOx();
106
+
107
+            /** Returns the number of cells in y
108
+             *  @return number of cells in y
109
+             */
110
+            Real GetOy();
111
+
112
+            /** Returns the offset of cells in z
113
+             *  @return offset of cells in z
114
+             */
115
+            Real GetOz();
116
+
117
+            /** Returns Spacing Vector
118
+             *  @return dx
119
+             */
120
+            VectorXr GetDx();
121
+
122
+            /** Returns a spacing
123
+             *  @return dx[ix]
124
+             */
125
+            Real GetDx(const int& ix);
126
+
127
+            /** Returns Spacing Vector
128
+             *  @return dy
129
+             */
130
+            VectorXr GetDy();
131
+
132
+            /** Returns a spacing
133
+             *  @return dy[iy]
134
+             */
135
+            Real GetDy(const int& iy);
136
+
137
+            /** Returns Spacing Vector
138
+             *  @return dz
139
+             */
140
+            VectorXr GetDz();
141
+
142
+            /** Returns Spacing Vector
143
+             *  @return dz[iz]
144
+             */
145
+            Real GetDz(const int& iz);
146
+
147
+            // ====================  INQUIRY       =======================
148
+
149
+        protected:
150
+
151
+            // ====================  LIFECYCLE     =======================
152
+
153
+            /// Default protected constructor.
154
+            RectilinearGrid (const std::string &name);
155
+
156
+            /// Default protected constructor.
157
+            ~RectilinearGrid ();
158
+
159
+            /**
160
+             *  @copybrief   LemmaObject::Release()
161
+             *  @copydetails LemmaObject::Release()
162
+             */
163
+            void Release();
164
+
165
+            // ====================  DATA MEMBERS  =========================
166
+
167
+            /// Number of cells in the x dimension
168
+            int nx;
169
+
170
+            /// Number of cells in the y dimension
171
+            int ny;
172
+
173
+            /// Number of cells in the z dimension
174
+            int nz;
175
+
176
+            /// Grid offset in x dimension
177
+            Real ox;
178
+
179
+            /// Grid offset in y dimension
180
+            Real oy;
181
+
182
+            /// Grid offset in z dimension
183
+            Real oz;
184
+
185
+            /// Cell spacing in the x dimension
186
+            VectorXr dx;
187
+
188
+            /// Cell spacing in the y dimension
189
+            VectorXr dy;
190
+
191
+            /// Cell spacing in the z dimension
192
+            VectorXr dz;
193
+
194
+/*          @todo find a good way to store models that works with portions threadprivate
195
+            /// Container holding Vectors of Real data at centre of cell.
196
+            std::vector<VectorXr>   RealCellData;
197
+
198
+            /// Container holding names of Real data
199
+            std::vector<std::string> RealCellDataNames;
200
+
201
+            /// Container holding Vectors of Real data on edges.
202
+            std::vector<VectorXr>   RealEdgeData;
203
+
204
+            /// Container holding names of Real data on edges
205
+            std::vector<std::string> RealEdgeDataNames;
206
+
207
+            /// Container holding Vectors of Complex data on edges.
208
+            std::vector<VectorXcr>   ComplexEdgeData;
209
+
210
+            /// Container holding names of Real data on edges
211
+            std::vector<std::string> ComplexEdgeDataNames;
212
+
213
+            /// Container holding Vectors of Real properties.
214
+            std::vector<VectorXr>   RealCellProperties;
215
+
216
+            /// Container holding names of Real cell properties
217
+            std::vector<std::string> RealCellPropertyNames;
218
+
219
+            /// Container holding Vectors of Real data.
220
+            std::vector<VectorXcr>   ComplexCellData;
221
+
222
+            /// Container holding names of Real data
223
+            std::vector<std::string> ComplexCellDataNames;
224
+
225
+            /// Container holding Vectors of Complex properties.
226
+            std::vector<VectorXcr>   ComplexCellProperties;
227
+
228
+            /// Container holding names of Real cell properties
229
+            std::vector<std::string> ComplexCellPropertyNames;
230
+*/
231
+        private:
232
+
233
+    }; // -----  end of class  RectilinearGrid  -----
234
+
235
+}		// -----  end of Lemma  name  -----
236
+
237
+#endif   // ----- #ifndef RECTILINEARGRID_INC  -----

+ 97
- 0
LemmaCore/include/sintransintegrationkernel.h View File

@@ -0,0 +1,97 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     02/08/2011
11
+  @version  $Id: sintransintegrationkernel.h 87 2013-09-05 22:44:05Z tirons $
12
+ **/
13
+
14
+#ifndef  SINTRANSINTEGRATIONKERNEL_INC
15
+#define  SINTRANSINTEGRATIONKERNEL_INC
16
+
17
+#include "integrationkernel.h"
18
+
19
+namespace Lemma {
20
+
21
+    // ===================================================================
22
+    //  Class:  SinTransIntegrationKernel
23
+    /**
24
+      @class
25
+      \brief    Integration kernel for testing sinine transform.
26
+      \details  Evaluates sinine at the argument, using lagged convolution.
27
+                all of these kernels have exact solutions.
28
+     */
29
+    // ===================================================================
30
+    class SinTransIntegrationKernel : public IntegrationKernel<Real> {
31
+
32
+        public:
33
+
34
+            // ====================  LIFECYCLE     =======================
35
+
36
+            /** Returns a pointer to a new object of type SinTransIntegrationKernel.
37
+             * It allocates all necessary memory.
38
+             */
39
+            static SinTransIntegrationKernel* New();
40
+
41
+            /** Deletes this object. Delete also disconnects any
42
+             * attachments to this object.
43
+             */
44
+            void Delete();
45
+
46
+            // ====================  OPERATORS     =======================
47
+
48
+            Real Argument(const Real&x, const int& iRelated);
49
+
50
+            int GetNumRel();
51
+
52
+            /// Sets the value 'A' used in test cases
53
+            void SetA(const Real& A);
54
+
55
+            /** Sets the integral to evaluate (1, 2, 3)
56
+             */
57
+            void SetIntegral(const int& i);
58
+
59
+            /** Returns the analytical answer at A and B */
60
+            Real GetAnalytical(const Real& B);
61
+            // ====================  OPERATIONS    =======================
62
+
63
+            // ====================  ACCESS        =======================
64
+
65
+            // ====================  INQUIRY       =======================
66
+
67
+        protected:
68
+
69
+            // ====================  LIFECYCLE     =======================
70
+
71
+            /** Deletes this object. Delete also disconnects any
72
+             * attachments to this object.
73
+             */
74
+            void Release();
75
+
76
+            /// Default protected constructor.
77
+            SinTransIntegrationKernel (const std::string& name);
78
+
79
+            /// Default protected constructor.
80
+            ~SinTransIntegrationKernel ();
81
+
82
+            // ====================  DATA MEMBERS  =========================
83
+
84
+            /** Value used in test cases  */
85
+            Real A;
86
+
87
+            /** Test integral to evaluate */
88
+            int Integral;
89
+
90
+        private:
91
+
92
+    }; // -----  end of class  SinTransIntegrationKernel  -----
93
+
94
+
95
+}		// -----  end of Lemma  name  -----
96
+
97
+#endif   // ----- #ifndef SINTRANSINTEGRATIONKERNEL_INC  -----

+ 103
- 0
LemmaCore/include/temintegrationkernel.h View File

@@ -0,0 +1,103 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   M. Andy Kass
10
+  @date     02/10/2011
11
+  @version  $Id: temintegrationkernel.h 190 2014-10-16 23:02:09Z tirons $
12
+ **/
13
+
14
+#ifndef __TEMINTEGRATIONKERNEL_H
15
+#define __TEMINTEGRATIONKERNEL_H
16
+
17
+#include "integrationkernel.h"
18
+#include "emearth1d.h"
19
+
20
+namespace Lemma {
21
+
22
+
23
+// ===================================================================
24
+//        Class:  TemIntegrationKernel
25
+/// \brief  Integration kernel for calculation of TEM data
26
+/// \details Calculates the integration kernel for the sine transform
27
+// ===================================================================
28
+
29
+class TemIntegrationKernel : public IntegrationKernel<Real>{
30
+
31
+	//friend std::ostream &operator<<(std::ostream &stream,
32
+	//	const TemIntegrationKernel &ob);
33
+
34
+	public:
35
+
36
+	// ====================  LIFECYCLE     =======================
37
+
38
+		static TemIntegrationKernel* New();
39
+
40
+		void Delete();
41
+
42
+	// ====================  OPERATORS     =======================
43
+
44
+	// ====================  OPERATIONS    =======================
45
+
46
+	// ====================  ACCESS        =======================
47
+
48
+		/// Calculates the integration argument.  Passed a frequency.
49
+		Real Argument(const Real&x, const int& iRelated);
50
+
51
+		int GetNumRel();
52
+
53
+		/// Attach EMEarth1D object to TemIntegrationKernel
54
+		void SetEMEarth1D(EMEarth1D* earth);
55
+
56
+		/// Attach Transmitter object
57
+		void SetTransmitter(WireAntenna *antennae);
58
+
59
+		/// Attach Dipole object
60
+		void SetDipole(DipoleSource* dipolesource);
61
+
62
+		/// Attach Receiver object
63
+		void SetReceiver(ReceiverPoints *receiver);
64
+
65
+        /**
66
+         *   @param[in] comp is the component to integrate
67
+         */
68
+        void SetComponent(const FIELDCOMPONENT& comp);
69
+	// ====================  INQUIRY       =======================
70
+
71
+
72
+
73
+	protected:
74
+
75
+	// ====================  LIFECYCLE     =======================
76
+
77
+		/// Default protected constructor.
78
+		TemIntegrationKernel (const std::string& name);
79
+
80
+		/// Default protected constructor.
81
+		~TemIntegrationKernel ();
82
+
83
+		void Release();
84
+
85
+	// ====================  DATA MEMBERS  =========================
86
+
87
+        FIELDCOMPONENT  component;
88
+
89
+		EMEarth1D* EmEarthInt;
90
+
91
+		WireAntenna* Trans;
92
+
93
+		DipoleSource* DipoleS;
94
+
95
+		ReceiverPoints* Receivers;
96
+
97
+	private:
98
+
99
+}; // -----  end of class  TemIntegrationKernel  -----
100
+
101
+} // End of namespace Lemma
102
+
103
+#endif // __TEMINTEGRATIONKERNEL_H

+ 82
- 0
LemmaCore/include/timer.h View File

@@ -0,0 +1,82 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     01/27/2010
11
+  @version  $Id: timer.h 87 2013-09-05 22:44:05Z tirons $
12
+ **/
13
+
14
+#ifndef  TIMER_H_INC
15
+#define  TIMER_H_INC
16
+
17
+#include <iostream>
18
+#include <fstream>
19
+#include <ctime>
20
+#ifdef LEMMAUSEOMP
21
+#include "omp.h"
22
+#endif
23
+
24
+#include "lemma.h"
25
+
26
+namespace Lemma {
27
+
28
+/** \brief Simple timer class.
29
+  * \details Can be used either with multithreaded applications, using
30
+  * OpenMP defined functions, or using system wall time. System wall time
31
+  * is not good for parallel programs as it reports cpu core execution time.
32
+  */
33
+class jsw_timer {
34
+
35
+    public:
36
+
37
+        /**
38
+          * Constructor that automatically starts the timer.
39
+          */
40
+        jsw_timer(): start ( std::clock() ), elapsed ( 0.0 ) {
41
+
42
+        }
43
+
44
+        /** begins the timer.
45
+          */
46
+        void begin() {
47
+            #ifdef LEMMAUSEOMP
48
+            start =  omp_get_wtime();
49
+            #else
50
+            start = std::clock();
51
+            #endif
52
+            elapsed = 0.0;
53
+        }
54
+
55
+        /** Ends the timer.
56
+          * @return the time that the stopwatch ended at.
57
+          */
58
+        Real end() {
59
+
60
+            #ifdef LEMMAUSEOMP
61
+            elapsed = static_cast<Real> (omp_get_wtime()) - start;
62
+            return elapsed;
63
+            #else
64
+            elapsed = static_cast<Real> ( std::clock() ) - start;
65
+            return elapsed /= CLOCKS_PER_SEC;
66
+            #endif
67
+
68
+        }
69
+
70
+        /**
71
+          * @return the elapsed time between start and end.
72
+          */
73
+        Real last() const { return elapsed; }
74
+
75
+    private:
76
+        std::clock_t start;
77
+        Real    elapsed;
78
+};
79
+
80
+}       // -----  end of Lemma  name  -----
81
+
82
+#endif   // ----- #ifndef TIMER_H_INC  -----

+ 130
- 0
LemmaCore/include/windowfilter.h View File

@@ -0,0 +1,130 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API */
2
+
3
+/* This Source Code Form is subject to the terms of the Mozilla Public
4
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
5
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6
+
7
+/**
8
+  @file
9
+  @author   Trevor Irons
10
+  @date     07/20/2010
11
+  @version  $Id: windowfilter.h 193 2014-11-10 23:51:41Z tirons $
12
+ **/
13
+
14
+#ifndef  WINDOWFILTER_INC
15
+#define  WINDOWFILTER_INC
16
+#include "filter.h"
17
+
18
+namespace Lemma {
19
+    /** Types of filter window that are supported.
20
+     */
21
+    enum WINDOWTYPE { HAMMING, /*!< A hamming window */
22
+                      HANNING, /*!< A hanning window */
23
+                      RECTANGULAR /*!< Rectangular window */
24
+                    };
25
+
26
+    // ===================================================================
27
+    //  Class:  WindowFilter
28
+    /**
29
+      @class   WindowFilter
30
+      \brief   Fourier domain window filter.
31
+      \details Current types are Hamming and Hanning. Others to be added.
32
+     */
33
+    // ===================================================================
34
+    class WindowFilter : public Filter {
35
+
36
+        public:
37
+
38
+            // ====================  LIFECYCLE     =======================
39
+
40
+            /**
41
+             * Returns a pointer to a new object of type WindowFilter.
42
+             * It allocates all necessary memory.
43
+             */
44
+            static WindowFilter* New();
45
+
46
+            /**
47
+             * @copybrief LemmaObject::Delete()
48
+             * @copydetails LemmaObject::Delete()
49
+             */
50
+            void Delete();
51
+
52
+            // ====================  OPERATORS     =======================
53
+
54
+            // ====================  OPERATIONS    =======================
55
+
56
+            /// Sets the bandwith of the window.
57
+            /// @param[in] width Bandwidth in Hz
58
+            void SetBandwidth(const Real& width);
59
+
60
+            /// Sets the sampling rate of an input time domain signal.
61
+            /// @param[in] dt is the sampling rate, in seconds.
62
+            void SetSamplingInterval(const Real& dt);
63
+
64
+            /// Specifies the length of the time series to apply filter to.
65
+            void SetNumberOfSamples(const int& nt);
66
+
67
+            /// Sets the type of window to compute.
68
+            void SetWindowType(const WINDOWTYPE& type);
69
+
70
+            /** Returns the number of frequency bins for whole data record.
71
+             *  this is different then the length of the filter. This is
72
+             *  simply the length of the real to complex FFT, or
73
+             *  Nw = Nt%2 ? (Nt-1)/2+1 : (Nt)/2+1;
74
+             *  @return the number of frequency bins.
75
+             */
76
+            int GetNumberOfFrequencyBins();
77
+
78
+            // ====================  ACCESS        =======================
79
+
80
+            // ====================  INQUIRY       =======================
81
+
82
+            /// Returns a Vector of the filter coefficients.
83
+            VectorXr GetFilterCoefficients( );
84
+
85
+        protected:
86
+
87
+            // ====================  LIFECYCLE     =======================
88
+
89
+            /// Default protected constructor.
90
+            WindowFilter (const std::string& name);
91
+
92
+            /// Default protected constructor.
93
+            ~WindowFilter ();
94
+
95
+            /**
96
+             * @copybrief LemmaObject::Release()
97
+             * @copydetails LemmaObject::Release()
98
+             */
99
+            void Release();
100
+
101
+            // ====================  DATA MEMBERS  =========================
102
+
103
+            /// Width of the window
104
+            int         Width;
105
+
106
+            /// Length of time series
107
+            int         Nt;
108
+
109
+            /// Length of the frequency series representation
110
+            int         Nw;
111
+
112
+            /// Sampling rate of a time domain signal
113
+            Real        SamplingRate;
114
+
115
+            /// Bandwith of filter
116
+            Real        Bandwidth;
117
+
118
+            /// The filter coefficients
119
+            VectorXr    Coefficients;
120
+
121
+            /// The type of filter to use
122
+            WINDOWTYPE  Type;
123
+
124
+        private:
125
+
126
+    }; // -----  end of class  WindowFilter  -----
127
+
128
+}       // -----  end of Lemma  name  -----
129
+
130
+#endif   // ----- #ifndef WINDOWFILTER_INC  -----

+ 0
- 23
LemmaCore/lemma.h View File

@@ -1,23 +0,0 @@
1
-/* This file is part of Lemma, a geophysical modelling and inversion API.
2
- * More information is available at http://lemmasoftware.org
3
- */
4
-
5
-/* This Source Code Form is subject to the terms of the Mozilla Public
6
- * License, v. 2.0. If a copy of the MPL was not distributed with this
7
- * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
- */
9
-
10
-/**
11
- * @file
12
- * @date      01/16/2016 04:40:33 PM
13
- * @version   $Id$
14
- * @author    Trevor Irons (ti)
15
- * @email     tirons@egi.utah.edu
16
- * @copyright Copyright (c) 2016, University of Utah
17
- * @copyright Copyright (c) 2016, Trevor Irons & Lemma Software, LLC
18
- */
19
-
20
-#include "yaml-cpp/yaml.h"
21
-
22
-float thingy();
23
-

+ 111
- 0
LemmaCore/src/AEMSurvey.cpp View File

@@ -0,0 +1,111 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      09/24/2013 04:09:04 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2013, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2013, Trevor Irons
18
+ */
19
+
20
+#include "AEMSurvey.h"
21
+
22
+namespace Lemma {
23
+
24
+// ====================  FRIEND METHODS  =====================
25
+
26
+std::ostream &operator<<(std::ostream &stream, const AEMSurvey &ob) {
27
+
28
+    stream << *(LemmaObject*)(&ob);
29
+
30
+    return stream;
31
+}
32
+
33
+// ====================  LIFECYCLE     =======================
34
+
35
+//--------------------------------------------------------------------------------------
36
+//       Class:  AEMSurvey
37
+//      Method:  AEMSurvey
38
+// Description:  constructor (protected)
39
+//--------------------------------------------------------------------------------------
40
+AEMSurvey::AEMSurvey (const std::string& name) : LemmaObject(name) {
41
+
42
+}  // -----  end of method AEMSurvey::AEMSurvey  (constructor)  -----
43
+
44
+
45
+//--------------------------------------------------------------------------------------
46
+//       Class:  AEMSurvey
47
+//      Method:  New()
48
+// Description:  public constructor
49
+//--------------------------------------------------------------------------------------
50
+AEMSurvey* AEMSurvey::New() {
51
+    AEMSurvey*  Obj = new AEMSurvey("AEMSurvey");
52
+    Obj->AttachTo(Obj);
53
+    return Obj;
54
+}
55
+
56
+//--------------------------------------------------------------------------------------
57
+//       Class:  AEMSurvey
58
+//      Method:  ~AEMSurvey
59
+// Description:  destructor (protected)
60
+//--------------------------------------------------------------------------------------
61
+AEMSurvey::~AEMSurvey () {
62
+
63
+    for (unsigned int isc=0; isc<Sources.size(); ++isc) Sources[isc]->Delete();
64
+
65
+}  // -----  end of method AEMSurvey::~AEMSurvey  (destructor)  -----
66
+
67
+//--------------------------------------------------------------------------------------
68
+//       Class:  AEMSurvey
69
+//      Method:  Delete
70
+// Description:  public destructor
71
+//--------------------------------------------------------------------------------------
72
+void AEMSurvey::Delete() {
73
+    this->DetachFrom(this);
74
+}
75
+
76
+//--------------------------------------------------------------------------------------
77
+//       Class:  AEMSurvey
78
+//      Method:  Release
79
+// Description:  destructor (protected)
80
+//--------------------------------------------------------------------------------------
81
+void AEMSurvey::Release() {
82
+    delete this;
83
+}
84
+
85
+//--------------------------------------------------------------------------------------
86
+//       Class:  AEMSurvey
87
+//      Method:  GetSource
88
+//--------------------------------------------------------------------------------------
89
+DipoleSource* AEMSurvey::GetSource ( const int& isource ) {
90
+    return Sources[isource] ;
91
+}		// -----  end of method AEMSurvey::GetSource  -----
92
+
93
+//--------------------------------------------------------------------------------------
94
+//       Class:  AEMSurvey
95
+//      Method:  GetFrequencies
96
+//--------------------------------------------------------------------------------------
97
+VectorXr AEMSurvey::GetFrequencies (  ) {
98
+    return Freqs;
99
+}		// -----  end of method AEMSurvey::GetFrequencies  -----
100
+
101
+
102
+//--------------------------------------------------------------------------------------
103
+//       Class:  AEMSurvey
104
+//      Method:  GetNumberOfSources
105
+//--------------------------------------------------------------------------------------
106
+int AEMSurvey::GetNumberOfSources (  ) {
107
+    return  static_cast<int>(Sources.size());
108
+}		// -----  end of method AEMSurvey::GetNumberOfSources  -----
109
+
110
+
111
+}		// -----  end of Lemma  name  -----

+ 169
- 0
LemmaCore/src/AEMSurveyReader.cpp View File

@@ -0,0 +1,169 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      09/24/2013 04:36:14 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2013, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2013, Trevor Irons
18
+ */
19
+
20
+#include "AEMSurveyReader.h"
21
+
22
+namespace Lemma {
23
+
24
+    // ====================  FRIEND METHODS  =====================
25
+
26
+    std::ostream &operator<<(std::ostream &stream, const AEMSurveyReader &ob) {
27
+
28
+        stream << *(LemmaObject*)(&ob);
29
+
30
+        return stream;
31
+    }
32
+
33
+    // ====================  LIFECYCLE     =======================
34
+
35
+    //--------------------------------------------------------------------------------------
36
+    //       Class:  AEMSurveyReader
37
+    //      Method:  AEMSurveyReader
38
+    // Description:  constructor (protected)
39
+    //--------------------------------------------------------------------------------------
40
+    AEMSurveyReader::AEMSurveyReader (const std::string& name) :
41
+        LemmaObject(name), Survey(NULL) {
42
+
43
+    }  // -----  end of method AEMSurveyReader::AEMSurveyReader  (constructor)  -----
44
+
45
+
46
+    //--------------------------------------------------------------------------------------
47
+    //       Class:  AEMSurveyReader
48
+    //      Method:  New()
49
+    // Description:  public constructor
50
+    //--------------------------------------------------------------------------------------
51
+    AEMSurveyReader* AEMSurveyReader::New() {
52
+        AEMSurveyReader*  Obj = new AEMSurveyReader("AEMSurveyReader");
53
+        Obj->AttachTo(Obj);
54
+        return Obj;
55
+    }
56
+
57
+    //--------------------------------------------------------------------------------------
58
+    //       Class:  AEMSurveyReader
59
+    //      Method:  ~AEMSurveyReader
60
+    // Description:  destructor (protected)
61
+    //--------------------------------------------------------------------------------------
62
+    AEMSurveyReader::~AEMSurveyReader () {
63
+        if (Survey) Survey->Delete();
64
+    }  // -----  end of method AEMSurveyReader::~AEMSurveyReader  (destructor)  -----
65
+
66
+    //--------------------------------------------------------------------------------------
67
+    //       Class:  AEMSurveyReader
68
+    //      Method:  Delete
69
+    // Description:  public destructor
70
+    //--------------------------------------------------------------------------------------
71
+    void AEMSurveyReader::Delete() {
72
+        this->DetachFrom(this);
73
+    }
74
+
75
+    //--------------------------------------------------------------------------------------
76
+    //       Class:  AEMSurveyReader
77
+    //      Method:  Release
78
+    // Description:  destructor (protected)
79
+    //--------------------------------------------------------------------------------------
80
+    void AEMSurveyReader::Release() {
81
+        delete this;
82
+    }
83
+
84
+
85
+    //--------------------------------------------------------------------------------------
86
+    //       Class:  AEMSurveyReader
87
+    //      Method:  GetSurvey
88
+    //--------------------------------------------------------------------------------------
89
+    AEMSurvey* AEMSurveyReader::GetSurvey (  ) {
90
+        return Survey;
91
+    }		// -----  end of method AEMSurveyReader::GetSurvey  -----
92
+
93
+
94
+    //--------------------------------------------------------------------------------------
95
+    //       Class:  AEMSurveyReader
96
+    //      Method:  ReadASCIIAEMFile
97
+    //--------------------------------------------------------------------------------------
98
+    void AEMSurveyReader::ReadASCIIAEMFile (  const std::string& fname ) {
99
+
100
+        if (Survey) Survey->Delete();
101
+        Survey = AEMSurvey::New();
102
+        ASCIIParser* Parser = ASCIIParser::New();
103
+        Parser->SetCommentString("//");
104
+        Parser->Open(fname);
105
+
106
+        // Sanity check
107
+        std::vector<int> ivals = Parser->ReadInts(1);
108
+        std::vector<Real> freqs;
109
+        for (int isc=0; isc<ivals[0]; ++isc) {
110
+            Real df = Parser->ReadReals(1)[0]; // frequency Hz
111
+            bool unique = true;
112
+            for (unsigned int ifreq=0; ifreq<freqs.size(); ++ifreq) {
113
+                if (df - freqs[ifreq] < 1e-2) {
114
+                    unique = false;
115
+                }
116
+            }
117
+            if (unique) freqs.push_back(df);
118
+            std::string DT = Parser->ReadStrings(1)[0];
119
+            if (DT == "MD" || DT == "ED") {
120
+            } else {
121
+                std::cerr << "In AEMSurveyReader::ReadASCIIAEMFile. The source type: "
122
+                          << DT << " is not supported.\n";
123
+                std::exit(EXIT_FAILURE);
124
+            }
125
+            Parser->ReadReals(4); // position and moment
126
+        }
127
+
128
+        Survey->Freqs = VectorXr::Map(&freqs[0], freqs.size());
129
+
130
+        // OK, now get cracking, those sources at every location
131
+        int nb = Parser->ReadInts(1)[0];  // number of locations
132
+        for (int ib=0; ib<nb; ++ib) {
133
+            std::vector<Real> rvals = Parser->ReadReals(6); // position and moment
134
+            int bp = Parser->GetFileLocation(  );
135
+            Parser->JumpToLocation( 0 );
136
+            //std::vector<int> ivals = Parser->ReadInts(1);   // number of frequencies
137
+            int nf = Parser->ReadInts(1)[0];   // number of frequencies
138
+            for (int isc=0; isc<nf; ++isc) {
139
+                Survey->Sources.push_back(DipoleSource::New());
140
+                int cnt = Survey->Sources.size() - 1; //
141
+                // and now set it
142
+                Survey->Sources[cnt]->SetNumberOfFrequencies(1);
143
+                Survey->Sources[cnt]->SetFrequency(0, Parser->ReadReals(1)[0]);
144
+                std::string DT = Parser->ReadStrings(1)[0];
145
+                if (DT == "MD") {
146
+                     Survey->Sources[cnt]->SetType(MAGNETICDIPOLE);
147
+                } else if (DT == "ED") {
148
+                     Survey->Sources[cnt]->SetType(UNGROUNDEDELECTRICDIPOLE);
149
+                } else {
150
+                    std::cerr << "In AEMSurveyReader::ReadASCIIAEMFile. The source type: "
151
+                              << DT << " is not supported.\n";
152
+                    std::exit(EXIT_FAILURE);
153
+                }
154
+                std::vector<Real> irvals = Parser->ReadReals(4); // position and moment
155
+                Survey->Sources[cnt]->SetMoment(irvals[3]);
156
+                Survey->Sources[cnt]->SetLocation(rvals[0] + irvals[0], rvals[1] + irvals[1],
157
+                                                     rvals[2] + irvals[2]);
158
+                Survey->Sources[cnt]->SetPolarisation(rvals[3], rvals[4], rvals[5]);
159
+            }
160
+            Parser->JumpToLocation(bp);
161
+        }
162
+
163
+        Parser->Delete();
164
+
165
+        return ;
166
+    }		// -----  end of method AEMSurveyReader::ReadASCIIAEMFile  -----
167
+
168
+
169
+}		// -----  end of Lemma  name  -----

+ 216
- 0
LemmaCore/src/ASCIIParser.cpp View File

@@ -0,0 +1,216 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      09/23/2013 02:33:41 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2013, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2013, Trevor Irons
18
+ */
19
+
20
+#include "ASCIIParser.h"
21
+
22
+namespace Lemma {
23
+
24
+
25
+    // ====================  FRIEND METHODS  =====================
26
+
27
+    std::ostream &operator<<(std::ostream &stream, const ASCIIParser &ob) {
28
+
29
+        stream << *(LemmaObject*)(&ob);
30
+
31
+        return stream;
32
+    }
33
+
34
+    // ====================  LIFECYCLE     =======================
35
+
36
+    //--------------------------------------------------------------------------------------
37
+    //       Class:  ASCIIParser
38
+    //      Method:  ASCIIParser
39
+    // Description:  constructor (protected)
40
+    //--------------------------------------------------------------------------------------
41
+    ASCIIParser::ASCIIParser (const std::string& name) : LemmaObject(name),
42
+            CommentString("//"), BufferSize(255) {
43
+
44
+    }  // -----  end of method ASCIIParser::ASCIIParser  (constructor)  -----
45
+
46
+
47
+    //--------------------------------------------------------------------------------------
48
+    //       Class:  ASCIIParser
49
+    //      Method:  New()
50
+    // Description:  public constructor
51
+    //--------------------------------------------------------------------------------------
52
+    ASCIIParser* ASCIIParser::New() {
53
+        ASCIIParser*  Obj = new ASCIIParser("ASCIIParser");
54
+        Obj->AttachTo(Obj);
55
+        return Obj;
56
+    }
57
+
58
+    //--------------------------------------------------------------------------------------
59
+    //       Class:  ASCIIParser
60
+    //      Method:  ~ASCIIParser
61
+    // Description:  destructor (protected)
62
+    //--------------------------------------------------------------------------------------
63
+    ASCIIParser::~ASCIIParser () {
64
+
65
+    }  // -----  end of method ASCIIParser::~ASCIIParser  (destructor)  -----
66
+
67
+    //--------------------------------------------------------------------------------------
68
+    //       Class:  ASCIIParser
69
+    //      Method:  Delete
70
+    // Description:  public destructor
71
+    //--------------------------------------------------------------------------------------
72
+    void ASCIIParser::Delete() {
73
+        this->DetachFrom(this);
74
+    }
75
+
76
+    //--------------------------------------------------------------------------------------
77
+    //       Class:  ASCIIParser
78
+    //      Method:  Release
79
+    // Description:  destructor (protected)
80
+    //--------------------------------------------------------------------------------------
81
+    void ASCIIParser::Release() {
82
+        delete this;
83
+    }
84
+
85
+    //--------------------------------------------------------------------------------------
86
+    //       Class:  ASCIIParser
87
+    //      Method:  Open
88
+    //--------------------------------------------------------------------------------------
89
+    void ASCIIParser::Open ( const std::string& fname ) {
90
+        input.open(fname.c_str(), std::ios::in);
91
+        if (input.fail()) {
92
+           throw  GenericFileIOError(this, fname);
93
+        }
94
+        return ;
95
+    }		// -----  end of method ASCIIParser::Open  -----
96
+
97
+
98
+    //--------------------------------------------------------------------------------------
99
+    //       Class:  ASCIIParser
100
+    //      Method:  Close
101
+    //--------------------------------------------------------------------------------------
102
+    void ASCIIParser::Close (  ) {
103
+        input.close();
104
+        return ;
105
+    }		// -----  end of method ASCIIParser::Close  -----
106
+
107
+
108
+    //--------------------------------------------------------------------------------------
109
+    //       Class:  ASCIIParser
110
+    //      Method:  ReadReals
111
+    //--------------------------------------------------------------------------------------
112
+    std::vector<Real> ASCIIParser::ReadReals ( const int& nr ) {
113
+        std::string buf;
114
+        char *dump = new char[BufferSize];
115
+        std::vector<Real> vals(0);
116
+        while (input >> buf) {
117
+            if (buf.substr(0, CommentString.size()) == CommentString) {
118
+                input.getline(dump, BufferSize);
119
+            } else {
120
+                vals.push_back( atof(buf.c_str() ));
121
+            }
122
+            if (static_cast<int>(vals.size()) == nr) {
123
+                delete [] dump;
124
+                return vals;
125
+            }
126
+        }
127
+        delete [] dump;
128
+        return vals;
129
+    }		// -----  end of method ASCIIParser::ReadReals  -----
130
+
131
+    //--------------------------------------------------------------------------------------
132
+    //       Class:  ASCIIParser
133
+    //      Method:  ReadInts
134
+    //--------------------------------------------------------------------------------------
135
+    std::vector<int> ASCIIParser::ReadInts ( const int& nr ) {
136
+        std::string buf;
137
+        char *dump = new char[BufferSize];
138
+        std::vector<int> vals(0);
139
+        while (input >> buf) {
140
+            if (buf.substr(0, CommentString.size()) == CommentString) {
141
+                input.getline(dump, BufferSize);
142
+            } else {
143
+                vals.push_back( atoi(buf.c_str() ));
144
+            }
145
+            if (static_cast<int>(vals.size()) == nr) {
146
+                delete [] dump;
147
+                return vals;
148
+            }
149
+
150
+        }
151
+        delete [] dump;
152
+        return vals;
153
+    }		// -----  end of method ASCIIParser::ReadInts  -----
154
+
155
+    //--------------------------------------------------------------------------------------
156
+    //       Class:  ASCIIParser
157
+    //      Method:  ReadStings
158
+    //--------------------------------------------------------------------------------------
159
+    std::vector<std::string> ASCIIParser::ReadStrings ( const int& nr ) {
160
+        std::string buf;
161
+        char *dump = new char[BufferSize];
162
+        std::vector<std::string> vals(0);
163
+        while (input >> buf) {
164
+            if (buf.substr(0, CommentString.size()) == CommentString) {
165
+                input.getline(dump, BufferSize);
166
+            } else {
167
+                vals.push_back( buf );
168
+            }
169
+            if (static_cast<int>(vals.size()) == nr) {
170
+                delete [] dump;
171
+                return vals;
172
+            }
173
+
174
+        }
175
+        delete [] dump;
176
+        return vals;
177
+    }		// -----  end of method ASCIIParser::ReadInts  -----
178
+
179
+
180
+    //--------------------------------------------------------------------------------------
181
+    //       Class:  ASCIIParser
182
+    //      Method:  SetCommentString
183
+    //--------------------------------------------------------------------------------------
184
+    void ASCIIParser::SetCommentString ( const std::string& key ) {
185
+        CommentString = key;
186
+    }		// -----  end of method ASCIIParser::SetCommentString  -----
187
+
188
+    //--------------------------------------------------------------------------------------
189
+    //       Class:  ASCIIParser
190
+    //      Method:  SetBufferSize
191
+    //--------------------------------------------------------------------------------------
192
+    void ASCIIParser::SetBufferSize ( const int& size ) {
193
+        BufferSize = size;
194
+    }		// -----  end of method ASCIIParser::SetCommentString  -----
195
+
196
+    //--------------------------------------------------------------------------------------
197
+    //       Class:  ASCIIParser
198
+    //      Method:  GetFileLocation
199
+    //--------------------------------------------------------------------------------------
200
+    int ASCIIParser::GetFileLocation (  ) {
201
+        return input.tellg();
202
+    }		// -----  end of method ASCIIParser::GetFileLocation  -----
203
+
204
+    //--------------------------------------------------------------------------------------
205
+    //       Class:  ASCIIParser
206
+    //      Method:  JumpToLocation
207
+    //--------------------------------------------------------------------------------------
208
+    void ASCIIParser::JumpToLocation ( const int& loc ) {
209
+        input.seekg( loc );
210
+        return ;
211
+    }		// -----  end of method ASCIIParser::JumpToLocation  -----
212
+
213
+
214
+}		// -----  end of Lemma  name  -----
215
+
216
+

+ 335
- 0
LemmaCore/src/CubicSplineInterpolator.cpp View File

@@ -0,0 +1,335 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      02/07/2014 12:50:52 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI GeophysiSpline, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#include "CubicSplineInterpolator.h"
21
+
22
+#include<iostream>
23
+#include<fstream>
24
+#include<vector>
25
+#include<algorithm>
26
+#include<cmath>
27
+
28
+namespace Lemma {
29
+
30
+    // ====================  FRIEND METHODS  =====================
31
+
32
+    std::ostream &operator<<(std::ostream &stream, const CubicSplineInterpolator &ob) {
33
+
34
+        stream << *(LemmaObject*)(&ob);
35
+
36
+        return stream;
37
+    }
38
+
39
+    // ====================  LIFECYCLE     =======================
40
+
41
+    //--------------------------------------------------------------------------------------
42
+    //       Class:  CubicSplineInterpolator
43
+    //      Method:  CubicSplineInterpolator
44
+    // Description:  constructor (protected)
45
+    //--------------------------------------------------------------------------------------
46
+    CubicSplineInterpolator::CubicSplineInterpolator (const std::string& name) : LemmaObject(name) {
47
+
48
+    }  // -----  end of method CubicSplineInterpolator::CubicSplineInterpolator  (constructor)  -----
49
+
50
+
51
+    //--------------------------------------------------------------------------------------
52
+    //       Class:  CubicSplineInterpolator
53
+    //      Method:  New()
54
+    // Description:  public constructor
55
+    //--------------------------------------------------------------------------------------
56
+    CubicSplineInterpolator* CubicSplineInterpolator::New() {
57
+        CubicSplineInterpolator*  Obj = new CubicSplineInterpolator("CubicSplineInterpolator");
58
+        Obj->AttachTo(Obj);
59
+        return Obj;
60
+    }
61
+
62
+    //--------------------------------------------------------------------------------------
63
+    //       Class:  CubicSplineInterpolator
64
+    //      Method:  ~CubicSplineInterpolator
65
+    // Description:  destructor (protected)
66
+    //--------------------------------------------------------------------------------------
67
+    CubicSplineInterpolator::~CubicSplineInterpolator () {
68
+
69
+    }  // -----  end of method CubicSplineInterpolator::~CubicSplineInterpolator  (destructor)  -----
70
+
71
+    //--------------------------------------------------------------------------------------
72
+    //       Class:  CubicSplineInterpolator
73
+    //      Method:  Delete
74
+    // Description:  public destructor
75
+    //--------------------------------------------------------------------------------------
76
+    void CubicSplineInterpolator::Delete() {
77
+        this->DetachFrom(this);
78
+    }
79
+
80
+    //--------------------------------------------------------------------------------------
81
+    //       Class:  CubicSplineInterpolator
82
+    //      Method:  Release
83
+    // Description:  destructor (protected)
84
+    //--------------------------------------------------------------------------------------
85
+    void CubicSplineInterpolator::Release() {
86
+        delete this;
87
+    }
88
+
89
+    // ====================  OPERATIONS    =======================
90
+
91
+    //--------------------------------------------------------------------------------------
92
+    //       Class:  CubicSplineInterpolator
93
+    //      Method:  SetKnots
94
+    //--------------------------------------------------------------------------------------
95
+    void CubicSplineInterpolator::SetKnots ( const VectorXr& x, const VectorXr& y ) {
96
+
97
+        int n = x.size()-1;
98
+
99
+        Spline = SplineSet(n);
100
+
101
+        Spline.a = y;
102
+        Spline.x = x;
103
+        VectorXr h = VectorXr::Zero(n);
104
+        for(int i=0; i<n; ++i)
105
+            h(i) = Spline.x(i+1)-Spline.x(i);
106
+
107
+        VectorXr alpha(n-1);
108
+        for(int i=1; i<n-1; ++i)
109
+            alpha(i) =  3.*(Spline.a[i+1]-Spline.a[i])/h[i] - 3.*(Spline.a[i]-Spline.a[i-1])/h[i-1] ;
110
+
111
+        VectorXr l = VectorXr::Zero(n+1);
112
+        VectorXr mu  = VectorXr::Zero(n+1);
113
+        VectorXr z = VectorXr::Zero(n+1);
114
+        l[0] = 1;
115
+        mu[0] = 0;
116
+        z[0] = 0;
117
+
118
+        for(int i = 1; i < n-1; ++i) {
119
+            l[i] = 2 *(Spline.x[i+1]-Spline.x[i-1])-h[i-1]*mu[i-1];
120
+            mu[i] = h[i]/l[i];
121
+            z[i] = (alpha[i]-h[i-1]*z[i-1])/l[i];
122
+        }
123
+        l[n] = 1;
124
+        z[n] = 0;
125
+
126
+        for(int j = n-1; j >= 0; --j) {
127
+            Spline.c[j] = z[j] - mu[j] * Spline.c[j+1];
128
+            Spline.b[j] = (Spline.a[j+1]-Spline.a[j])/h[j]-h[j]*(Spline.c[j+1]+2*Spline.c[j])/3;
129
+            Spline.d[j] = (Spline.c[j+1]-Spline.c[j])/3/h[j];
130
+        }
131
+        // On OSX, this causes a strange bug 'sometimes', alignment?
132
+        //Spline.c = Spline.c.head(n);
133
+
134
+        return;
135
+    }		// -----  end of method CubicSplineInterpolator::SetKnots  -----
136
+
137
+
138
+    //--------------------------------------------------------------------------------------
139
+    //       Class:  CubicSplineInterplator
140
+    //      Method:  ResetKnotOrdinate
141
+    //--------------------------------------------------------------------------------------
142
+    void CubicSplineInterpolator::ResetKnotOrdinate ( const VectorXr& y ) {
143
+        VectorXr x = Spline.x;
144
+        SetKnots(x, y);
145
+        return ;
146
+    }		// -----  end of method CubicSplineInterplator::ResetKnotOrdinate  -----
147
+
148
+
149
+    //--------------------------------------------------------------------------------------
150
+    //       Class:  CubicSplineInterpolator
151
+    //      Method:  InterpolateOrderedSet
152
+    //--------------------------------------------------------------------------------------
153
+    VectorXr CubicSplineInterpolator::InterpolateOrderedSet ( const VectorXr& x ) {
154
+        VectorXr y = VectorXr::Zero(x.size());
155
+        int ii = 0;
156
+        for (int iy=0; iy<y.size(); ++iy) {
157
+            y[iy] = Interpolate(x[iy], ii);
158
+        }
159
+        return y;
160
+    }		// -----  end of method CubicSplineInterpolator::InterpolateOrderedSet  -----
161
+
162
+
163
+    //--------------------------------------------------------------------------------------
164
+    //       Class:  CubicSplineInterpolator
165
+    //      Method:  Interpolate
166
+    //--------------------------------------------------------------------------------------
167
+    Real CubicSplineInterpolator::Interpolate ( const Real& x, int& i) {
168
+        // O(n) search, could do bisection, but if these are sorted, then this is quick
169
+        while(Spline.x[i] < x && i<Spline.x.size()) {
170
+            ++i;
171
+        }
172
+        --i;
173
+
174
+        //if ( x > Spline.x[i] ) {
175
+        //    throw std::runtime_error("CubicSplineInterpolator::Interpolate ATTEMPT TO INTERPOLATE PAST LAST KNOT");
176
+        //}
177
+
178
+        return Spline.a[i] + Spline.b[i]*(x-Spline.x[i]) + Spline.c[i]*((x-Spline.x[i])*(x-Spline.x[i])) +
179
+               Spline.d[i]*((x-Spline.x[i])*(x-Spline.x[i])*(x-Spline.x[i]) );
180
+    }		// -----  end of method CubicSplineInterpolator::Interpolate  -----
181
+
182
+    //--------------------------------------------------------------------------------------
183
+    //       Class:  CubicSplineInterpolator
184
+    //      Method:  Interpolate
185
+    //--------------------------------------------------------------------------------------
186
+    Real CubicSplineInterpolator::Interpolate ( const Real& x ) {
187
+        int ii(0);
188
+        return Interpolate(x, ii);
189
+    }
190
+
191
+
192
+    //--------------------------------------------------------------------------------------
193
+    //       Class:  CubicSplineInterpolator
194
+    //      Method:  Integrate
195
+    //--------------------------------------------------------------------------------------
196
+    Real CubicSplineInterpolator::Integrate ( const Real& x0, const Real& x1, const int& n ) {
197
+
198
+        assert(n > 0);
199
+        // force n to be even?
200
+        //n += (n % 2);
201
+
202
+        Real S = Interpolate(x0) + Interpolate(x1);
203
+        Real h = (x1 - x0) / Real(n);
204
+
205
+        int ik = 0;
206
+        for (int i=1; i<n; i+=2) {
207
+            S += 4. * Interpolate(x0 + (Real)(i)*h, ik);
208
+        }
209
+
210
+        ik = 0;
211
+        for (int i=2; i<n-1; i+=2) {
212
+            S += 2. * Interpolate(x0 + (Real)(i)*h, ik);
213
+        }
214
+
215
+        return  S * h / 3.;
216
+    }
217
+
218
+
219
+    //--------------------------------------------------------------------------------------
220
+    //       Class:  CubicSplineInterpolator
221
+    //      Method:  Integrate
222
+    //--------------------------------------------------------------------------------------
223
+    Real CubicSplineInterpolator::Integrate ( const Real& x0, const Real& x1 ) {
224
+
225
+
226
+        int i0 = Interval(x0);
227
+        int i1 = Interval(x1);
228
+
229
+        Real h0 = x0 - Spline.x(i0);
230
+        if (mflag == -1) h0 = 0;
231
+        Real h1 = x1 - Spline.x(i1);
232
+
233
+        Real cubint = (((Spline.d(i1)*h1/4.0 + Spline.c(i1) )*h1/3.0 +
234
+                         Spline.b(i1) )*h1/2.0 + Spline.a(i1) )*h1
235
+                    - (((Spline.d(i0)*h0/4.0 + Spline.c(i0) )*h0/3.0 +
236
+                         Spline.b(i0) )*h0/2.0 + Spline.a(i0) )*h0;
237
+
238
+        // Include integrals over intervening intervals.
239
+        if (i1 > i0) {
240
+            for (int i=i0; i<i1-1; ++i) {
241
+                Real h = Spline.x(i+1) - Spline.x(i);
242
+                cubint +=  (((Spline.d(i)*h/4.0 + Spline.c(i) )*h/3.0 +
243
+                              Spline.b(i))*h/2.0 + Spline.a(i) )*h;
244
+            }
245
+        }
246
+        return cubint;
247
+    }		// -----  end of method CubicSplineInterpolator::Integrate  -----
248
+
249
+
250
+
251
+    //--------------------------------------------------------------------------------------
252
+    //       Class:  CubicSplineInterpolator
253
+    //      Method:  Interval
254
+    //--------------------------------------------------------------------------------------
255
+    int CubicSplineInterpolator::Interval ( const Real& x ) {
256
+
257
+        std::cerr << "ENTERING CubicSplineInterpolator::Inverval. Known bugs here"  << std::endl;
258
+        int nx = Spline.x.size() - 2; // TODO check if this is correct or just -1
259
+        // when x not in range
260
+        if (x <= Spline.x(0) || nx <= 1 ) {
261
+            mflag = -1;
262
+            return 1;
263
+        }
264
+
265
+        if (x >= Spline.x(nx)) {
266
+            mflag = 1;
267
+            return nx;
268
+        }
269
+
270
+        mflag = 0;
271
+        if (ilo >= nx) ilo = nx-1;
272
+        int ihi = ilo+1;
273
+
274
+        // if x is already in the interval
275
+        if ( x<Spline.x(ihi) && x >= Spline.x(ilo) ) {
276
+            //std::cout << "TRIVIAL INTERVAL " << Spline.x(ilo) << "\t" << x << "\t" << Spline.x(ihi) << std::endl;
277
+            return ilo;
278
+        }
279
+
280
+        if (x <= Spline.x(ilo)) { // decrease ilo to capture
281
+            int istep = 1;
282
+            for (int ix=1; ix<nx; ++ix) {
283
+                ihi = ilo;
284
+                ilo = ihi - istep;
285
+                ilo = std::max(1, ilo);
286
+                if (x >= Spline.x(ilo) || ilo == 1) break;
287
+                istep *= 2;
288
+            }
289
+        } else if (x >= Spline.x(ihi)) { // increase ihi to capture
290
+            int istep = 1;
291
+            for (int ix=1; ix<nx; ++ix) {
292
+                ilo = ihi;
293
+                ihi = ilo + istep;
294
+                ihi = std::min(ihi, nx);
295
+                if (x <= Spline.x(ihi) || ihi == nx) break;
296
+                istep *= 2;
297
+            }
298
+        }
299
+
300
+        // Now Spline.x(ilo) <= x < Spline.x(ihi) --> Narrow the interval.
301
+        //std::cout << "WIDE INTERVAL " << Spline.x(ilo) << "\t" << x << "\t" << Spline.x(ihi) << std::endl;
302
+        for (int ix=1; ix<nx; ++ix) {
303
+            int middle = (ilo+ihi) / 2;
304
+            if (middle == ilo) break;
305
+            if (x < Spline.x(middle)) {
306
+                ihi = middle;
307
+            } else {
308
+                ilo = middle;
309
+            }
310
+        }
311
+        assert ( Spline.x(ilo) < x && x < Spline.x(ihi) );
312
+        return ilo;
313
+    }		// -----  end of method CubicSplineInterpolator::Inverval  -----
314
+
315
+
316
+
317
+    //--------------------------------------------------------------------------------------
318
+    //       Class:  CubicSplineInterplator
319
+    //      Method:  GetAbscissa
320
+    //--------------------------------------------------------------------------------------
321
+    VectorXr CubicSplineInterpolator::GetKnotAbscissa (  ) {
322
+        return Spline.x;
323
+    }		// -----  end of method CubicSplineInterplator::get_GetAbscissa  -----
324
+
325
+
326
+    //--------------------------------------------------------------------------------------
327
+    //       Class:  CubicSplineInterpolator
328
+    //      Method:  GetKnotOrdinate
329
+    //--------------------------------------------------------------------------------------
330
+    VectorXr CubicSplineInterpolator::GetKnotOrdinate (  ) {
331
+        return Spline.a;
332
+    }		// -----  end of method CubicSplineInterpolator::GetKnotOrdinate  -----
333
+
334
+
335
+}		// -----  end of Lemma  name  -----

+ 165
- 0
LemmaCore/src/DCIPElectrode.cpp View File

@@ -0,0 +1,165 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      11/10/2014 10:53:53 AM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#include "DCIPElectrode.h"
21
+
22
+namespace Lemma {
23
+
24
+
25
+
26
+    // ====================  FRIEND METHODS  =====================
27
+#ifdef HAVE_YAMLCPP
28
+    std::ostream &operator << (std::ostream &stream, const DCIPElectrode &ob) {
29
+        stream << ob.Serialize()  << "\n---\n"; // End of doc --- as a direct stream should encapulate thingy
30
+        return stream;
31
+    }
32
+#else
33
+    std::ostream &operator<<(std::ostream &stream, const DCIPElectrode& ob) {
34
+        stream << *(LemmaObject*)(&ob);
35
+        return stream;
36
+    }
37
+#endif
38
+
39
+    // ====================  LIFECYCLE     =======================
40
+
41
+    //--------------------------------------------------------------------------------------
42
+    //       Class:  DCIPElectrode
43
+    //      Method:  DCIPElectrode
44
+    // Description:  constructor (protected)
45
+    //--------------------------------------------------------------------------------------
46
+    DCIPElectrode::DCIPElectrode (const std::string& name) : LemmaObject(name), Node_ID(-1), Label(std::string("None")) {
47
+
48
+    }  // -----  end of method DCIPElectrode::DCIPElectrode  (constructor)  -----
49
+
50
+#ifdef HAVE_YAMLCPP
51
+    //--------------------------------------------------------------------------------------
52
+    //       Class:  DCIPElectrode
53
+    //      Method:  DCIPElectrode
54
+    // Description:  DeSerializing constructor (protected)
55
+    //--------------------------------------------------------------------------------------
56
+    DCIPElectrode::DCIPElectrode (const YAML::Node& node) : LemmaObject(node) {
57
+        if (node.Tag() != this->Name) {
58
+            throw std::runtime_error("In DCIPElectrode(node), node is of wrong type");
59
+        }
60
+        this->Location = node["Location"].as<Vector3r>();
61
+        this->Node_ID = node["Node_ID"].as<int>();
62
+        this->Label = node["Label"].as<std::string>();
63
+    }  // -----  end of method DCIPElectrode::DCIPElectrode  (constructor)  -----
64
+#endif
65
+
66
+    //--------------------------------------------------------------------------------------
67
+    //       Class:  DCIPElectrode
68
+    //      Method:  New()
69
+    // Description:  public constructor
70
+    //--------------------------------------------------------------------------------------
71
+    DCIPElectrode* DCIPElectrode::New() {
72
+        DCIPElectrode*  Obj = new DCIPElectrode("DCIPElectrode");
73
+        Obj->AttachTo(Obj);
74
+        return Obj;
75
+    }
76
+
77
+    //--------------------------------------------------------------------------------------
78
+    //       Class:  DCIPElectrode
79
+    //      Method:  ~DCIPElectrode
80
+    // Description:  destructor (protected)
81
+    //--------------------------------------------------------------------------------------
82
+    DCIPElectrode::~DCIPElectrode () {
83
+
84
+    }  // -----  end of method DCIPElectrode::~DCIPElectrode  (destructor)  -----
85
+
86
+    //--------------------------------------------------------------------------------------
87
+    //       Class:  DCIPElectrode
88
+    //      Method:  Delete
89
+    // Description:  public destructor
90
+    //--------------------------------------------------------------------------------------
91
+    void DCIPElectrode::Delete() {
92
+        this->DetachFrom(this);
93
+    }
94
+
95
+    //--------------------------------------------------------------------------------------
96
+    //       Class:  DCIPElectrode
97
+    //      Method:  Release
98
+    // Description:  destructor (protected)
99
+    //--------------------------------------------------------------------------------------
100
+    void DCIPElectrode::Release() {
101
+        delete this;
102
+    }
103
+
104
+
105
+#ifdef HAVE_YAMLCPP
106
+    //--------------------------------------------------------------------------------------
107
+    //       Class:  DCIPElectrode
108
+    //      Method:  Serialize
109
+    //--------------------------------------------------------------------------------------
110
+    YAML::Node  DCIPElectrode::Serialize (  ) const {
111
+        YAML::Node node = LemmaObject::Serialize();
112
+        node.SetTag( this->Name );
113
+        // FILL IN CLASS SPECIFICS HERE
114
+        node["Location"] = Location;
115
+        node["Node_ID"] = Node_ID;
116
+        node["Label"] = Label;
117
+        return node;
118
+    }		// -----  end of method DCIPElectrode::Serialize  -----
119
+
120
+
121
+    //--------------------------------------------------------------------------------------
122
+    //       Class:  DCIPElectrode
123
+    //      Method:  DeSerialize
124
+    //--------------------------------------------------------------------------------------
125
+    DCIPElectrode* DCIPElectrode::DeSerialize ( const YAML::Node& node  ) {
126
+        DCIPElectrode* Object = new DCIPElectrode(node);
127
+        Object->AttachTo(Object);
128
+        DESERIALIZECHECK( node, Object )
129
+        return Object ;
130
+    }		// -----  end of method DCIPElectrode::DeSerialize  -----
131
+#endif
132
+
133
+
134
+    //--------------------------------------------------------------------------------------
135
+    //       Class:  DCIPElectrode
136
+    //      Method:  SetLocation
137
+    //--------------------------------------------------------------------------------------
138
+    void DCIPElectrode::SetLocation ( const Vector3r& loc ) {
139
+        Location = loc;
140
+        return ;
141
+    }		// -----  end of method DCIPElectrode::SetLocation  -----
142
+
143
+
144
+
145
+    //--------------------------------------------------------------------------------------
146
+    //       Class:  DCIPElectrode
147
+    //      Method:  SetTag
148
+    //--------------------------------------------------------------------------------------
149
+    void DCIPElectrode::SetLabel ( const std::string& inLabel  ) {
150
+        Label = inLabel;
151
+        return ;
152
+    }		// -----  end of method DCIPElectrode::SetTag  -----
153
+
154
+
155
+    //--------------------------------------------------------------------------------------
156
+    //       Class:  DCIPElectrode
157
+    //      Method:  get_Label
158
+    //--------------------------------------------------------------------------------------
159
+    std::string DCIPElectrode::GetLabel (  ) {
160
+        return Label;
161
+    }		// -----  end of method DCIPElectrode::get_Label  -----
162
+
163
+
164
+}		// -----  end of Lemma  name  -----
165
+

+ 377
- 0
LemmaCore/src/DCSurvey.cpp View File

@@ -0,0 +1,377 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      10/08/2014 01:52:04 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#include	"DCSurvey.h"
21
+
22
+namespace Lemma {
23
+
24
+
25
+    // ====================  FRIEND METHODS  =====================
26
+
27
+    #ifdef HAVE_YAMLCPP
28
+    std::ostream &operator << (std::ostream &stream, const DCSurvey &ob) {
29
+        stream << ob.Serialize()  << "\n---\n"; // End of doc --- a direct stream should encapsulate object
30
+        return stream;
31
+    }
32
+    #else
33
+    std::ostream &operator<<(std::ostream &stream, const DCSurvey &ob) {
34
+        stream << *(LemmaObject*)(&ob);
35
+        return stream;
36
+    }
37
+    #endif
38
+
39
+    // ====================  LIFECYCLE     =======================
40
+
41
+    //--------------------------------------------------------------------------------------
42
+    //       Class:  DCSurvey
43
+    //      Method:  DCSurvey
44
+    // Description:  constructor (protected)
45
+    //--------------------------------------------------------------------------------------
46
+    DCSurvey::DCSurvey (const std::string& name) : LemmaObject(name) {
47
+
48
+    }  // -----  end of method DCSurvey::DCSurvey  (constructor)  -----
49
+
50
+    //--------------------------------------------------------------------------------------
51
+    //       Class:  DCSurvey
52
+    //      Method:  DCSurvey
53
+    // Description:  DeSerializing constructor (protected)
54
+    //--------------------------------------------------------------------------------------
55
+    #ifdef HAVE_YAMLCPP
56
+    DCSurvey::DCSurvey (const YAML::Node& node) : LemmaObject(node) {
57
+
58
+        if (node.Tag() != "DCSurvey") {
59
+            throw std::runtime_error("DCSurvey->DeSerialize cannot deserialize non-DCSurvey");
60
+        }
61
+
62
+        std::map<YAML::Node, int>  eMap;
63
+        for(YAML::const_iterator it=node["Electrodes"].begin(); it!=node["Electrodes"].end(); ++it) {
64
+            std::string e = it->first.as<std::string>();
65
+            Electrodes.push_back( DCIPElectrode::DeSerialize( node["Electrodes"][e] ) );
66
+            Electrodes[Electrodes.size()-1]->AttachTo(this);
67
+            eMap[ node["Electrodes"][Electrodes.size()-1] ] = Electrodes.size() -1 ;
68
+            OrderedElectrodeLabels.push_back(e);
69
+            ElectrodeLabelMap[e] = std::pair<DCIPElectrode*, int>(Electrodes[Electrodes.size()-1], Electrodes.size()-1);
70
+        }
71
+
72
+        //std::cout << "J-0\n" << node["Injections"]["J-0"] << std::endl;
73
+        int ij = 0 ;
74
+        for(YAML::const_iterator it=node["Injections"].begin(); it!=node["Injections"].end(); ++it) {
75
+
76
+            //std::cout << "it->first" << it->first << std::endl;
77
+
78
+            A_Electrodes.push_back( ElectrodeLabelMap[ it->second["A"]["Label"].as<std::string>() ].second );
79
+            B_Electrodes.push_back( ElectrodeLabelMap[ it->second["B"]["Label"].as<std::string>() ].second );
80
+            J_Electrodes.push_back( it->second["J"].as<Real>() );
81
+            //std::string Jstr = it->first.as<std::string>(); // J-1
82
+
83
+            M_Electrodes.push_back( std::vector<int>() );
84
+            N_Electrodes.push_back( std::vector<int>() );
85
+
86
+            for (int ii=0; ii<it->second["Measurements"]["Number"].as<int>(); ++ii) {
87
+                std::string Mstr = std::string("V-") + to_string(ii);
88
+                //std::cout << "measurements" << it->second["Measurements"][Mstr]["M"]["Label"] << std::endl;
89
+                M_Electrodes[ij].push_back( ElectrodeLabelMap[ it->second["Measurements"][Mstr]["M"]["Label"].as<std::string>() ].second );
90
+                N_Electrodes[ij].push_back( ElectrodeLabelMap[ it->second["Measurements"][Mstr]["N"]["Label"].as<std::string>() ].second );
91
+            }
92
+            ++ ij;
93
+        }
94
+
95
+    }  // -----  end of method DCSurvey::DCSurvey  (constructor)  -----
96
+    #endif
97
+
98
+    //--------------------------------------------------------------------------------------
99
+    //       Class:  DCSurvey
100
+    //      Method:  New()
101
+    // Description:  public constructor
102
+    //--------------------------------------------------------------------------------------
103
+    DCSurvey* DCSurvey::New() {
104
+        DCSurvey*  Obj = new DCSurvey("DCSurvey");
105
+        Obj->AttachTo(Obj);
106
+        return Obj;
107
+    }
108
+
109
+    //--------------------------------------------------------------------------------------
110
+    //       Class:  DCSurvey
111
+    //      Method:  ~DCSurvey
112
+    // Description:  destructor (protected)
113
+    //--------------------------------------------------------------------------------------
114
+    DCSurvey::~DCSurvey () {
115
+
116
+    }  // -----  end of method DCSurvey::~DCSurvey  (destructor)  -----
117
+
118
+    //--------------------------------------------------------------------------------------
119
+    //       Class:  DCSurvey
120
+    //      Method:  Delete
121
+    // Description:  public destructor
122
+    //--------------------------------------------------------------------------------------
123
+    void DCSurvey::Delete() {
124
+        this->DetachFrom(this);
125
+    }
126
+
127
+    //--------------------------------------------------------------------------------------
128
+    //       Class:  DCSurvey
129
+    //      Method:  Release
130
+    // Description:  destructor (protected)
131
+    //--------------------------------------------------------------------------------------
132
+    void DCSurvey::Release() {
133
+        this->PullElectrodes();
134
+        delete this;
135
+    }
136
+
137
+    #ifdef HAVE_YAMLCPP
138
+    //--------------------------------------------------------------------------------------
139
+    //       Class:  DCSurvey
140
+    //      Method:  Serialize
141
+    //--------------------------------------------------------------------------------------
142
+    YAML::Node  DCSurvey::Serialize (  ) const {
143
+        YAML::Node node = LemmaObject::Serialize();
144
+        node.SetTag( this->Name );
145
+        node["NumberOfElectrodes"] = Electrodes.size();
146
+
147
+        // All the electrodes
148
+        for (std::map<std::string, std::pair<DCIPElectrode*, int> >::const_iterator it  = ElectrodeLabelMap.begin();
149
+                                                                                    it != ElectrodeLabelMap.end(); ++it) {
150
+            node["Electrodes"][ it->first ] = it->second.first->Serialize();
151
+        }
152
+
153
+        // Injections and Measurements
154
+        for (unsigned int ic=0; ic<A_Electrodes.size(); ++ic) {
155
+            std::string strLab = std::string("J-") + to_string(ic);
156
+            node["Injections"][strLab]["A"] = node["Electrodes"][ OrderedElectrodeLabels[ A_Electrodes[ic] ] ];
157
+            node["Injections"][strLab]["B"] = node["Electrodes"][ OrderedElectrodeLabels[ B_Electrodes[ic] ] ];
158
+            node["Injections"][strLab]["J"] = J_Electrodes[ic];
159
+            node["Injections"][strLab]["Measurements"]["Number"] = M_Electrodes[ic].size();
160
+            for (unsigned int iv=0; iv<M_Electrodes[ic].size(); ++iv) {
161
+                node["Injections"][strLab]["Measurements"][std::string("V-") + to_string(iv)]["M"] =
162
+                    node["Electrodes"][ OrderedElectrodeLabels[M_Electrodes[ic][iv]] ];
163
+                node["Injections"][strLab]["Measurements"][std::string("V-") + to_string(iv)]["N"] =
164
+                    node["Electrodes"][ OrderedElectrodeLabels[N_Electrodes[ic][iv]] ];
165
+            }
166
+        }
167
+
168
+        return node;
169
+    }		// -----  end of method DCSurvey::Serialize  -----
170
+
171
+
172
+    //--------------------------------------------------------------------------------------
173
+    //       Class:  DCSurvey
174
+    //      Method:  DeSerialize
175
+    //--------------------------------------------------------------------------------------
176
+    DCSurvey* DCSurvey::DeSerialize ( const YAML::Node& node  ) {
177
+        DCSurvey* Object = new DCSurvey(node);
178
+        Object->AttachTo(Object);
179
+        DESERIALIZECHECK( node, Object )
180
+        return Object ;
181
+    }		// -----  end of method DCSurvey::DeSerialize  -----
182
+    #endif
183
+
184
+    //--------------------------------------------------------------------------------------
185
+    //       Class:  DCSurvey
186
+    //      Method:  PoundElectrode
187
+    //--------------------------------------------------------------------------------------
188
+    int DCSurvey::PoundElectrode ( DCIPElectrode* Electrode, const std::string& tag, const int&nodeID ) {
189
+        Electrodes.push_back(Electrode);
190
+        if (tag != "NULL") {
191
+            OrderedElectrodeLabels.push_back(tag);
192
+            //ElectrodeTagMap[tag] = Electrode;
193
+            ElectrodeLabelMap[tag] = std::pair<DCIPElectrode*, int> (Electrode, Electrodes.size()-1);
194
+            Electrode->SetLabel(tag);
195
+        } else {
196
+            OrderedElectrodeLabels.push_back( std::string("E") + to_string(Electrodes.size()-1) );
197
+            //ElectrodeTagMap[std::string("E") + to_string(Electrodes.size()-1)] = Electrode;
198
+            ElectrodeLabelMap[std::string("E") + to_string(Electrodes.size()-1)] =
199
+                std::pair<DCIPElectrode*, int>(Electrode, Electrodes.size()-1);
200
+            Electrode->SetLabel( std::string("E") + to_string(Electrodes.size()-1) );
201
+        }
202
+        Electrode->AttachTo(this);
203
+        return  static_cast<int>( Electrodes.size() ) ;
204
+    }		// -----  end of method DCSurvey::PoundElectrode  -----
205
+
206
+    //--------------------------------------------------------------------------------------
207
+    //       Class:  DCSurvey
208
+    //      Method:  PoundElectrode
209
+    //--------------------------------------------------------------------------------------
210
+    DCIPElectrode* DCSurvey::PoundElectrode ( const Vector3r& loc, const std::string& tag, const int& nodeID ) {
211
+        DCIPElectrode* Electrode = DCIPElectrode::New();
212
+            Electrode->SetLocation( loc );
213
+        Electrodes.push_back(Electrode);
214
+        if (tag != "NULL") {
215
+            OrderedElectrodeLabels.push_back(tag);
216
+            ElectrodeLabelMap[tag] = std::pair<DCIPElectrode*, int> (Electrode, Electrodes.size()-1);
217
+            Electrode->SetLabel(tag);
218
+        } else {
219
+            OrderedElectrodeLabels.push_back( std::string("E") + to_string(Electrodes.size()-1) );
220
+            ElectrodeLabelMap[std::string("E") + to_string(Electrodes.size()-1)] =
221
+                std::pair<DCIPElectrode*, int>(Electrode, Electrodes.size()-1);
222
+            Electrode->SetLabel( std::string("E") + to_string(Electrodes.size()-1) );
223
+        }
224
+        Electrode->AttachTo(this);
225
+        return  Electrode;
226
+    }		// -----  end of method DCSurvey::PoundElectrode  -----
227
+
228
+    //--------------------------------------------------------------------------------------
229
+    //       Class:  DCSurvey
230
+    //      Method:  PoundElectrode
231
+    //--------------------------------------------------------------------------------------
232
+#ifdef LEMMAUSEVTK
233
+    DCIPElectrode* DCSurvey::PoundElectrode( const int& nodeID, vtkDataSet* Mesh, const std::string& tag ) {
234
+        DCIPElectrode* Electrode = DCIPElectrode::New();
235
+        double* loc = Mesh->GetPoint(nodeID);
236
+        Electrode->SetLocation( Vector3r(loc[0], loc[1], loc[2]) );
237
+        Electrodes.push_back(Electrode);
238
+        if (tag != "NULL") {
239
+            OrderedElectrodeLabels.push_back(tag);
240
+            ElectrodeLabelMap[tag] = std::pair<DCIPElectrode*, int> (Electrode, Electrodes.size()-1);
241
+            Electrode->SetLabel(tag);
242
+        } else {
243
+            OrderedElectrodeLabels.push_back( std::string("E") + to_string(Electrodes.size()-1) );
244
+            ElectrodeLabelMap[std::string("E") + to_string(Electrodes.size()-1)] =
245
+                std::pair<DCIPElectrode*, int>(Electrode, Electrodes.size()-1);
246
+            Electrode->SetLabel( std::string("E") + to_string(Electrodes.size()-1) );
247
+        }
248
+        Electrode->AttachTo(this);
249
+        return Electrode;
250
+    }		// -----  end of method DCSurvey::PoundElectrode  -----
251
+#endif
252
+
253
+    //--------------------------------------------------------------------------------------
254
+    //       Class:  DCSurvey
255
+    //      Method:  PullElectrodes
256
+    //--------------------------------------------------------------------------------------
257
+    void DCSurvey::PullElectrodes (  ) {
258
+        for (std::vector<DCIPElectrode*>::iterator it = Electrodes.begin() ; it != Electrodes.end(); ++it) {
259
+            (*it)->DetachFrom(this);
260
+        }
261
+        Electrodes.clear();
262
+        OrderedElectrodeLabels.clear();
263
+        ElectrodeLabelMap.clear();
264
+        A_Electrodes.clear();
265
+        B_Electrodes.clear();
266
+        M_Electrodes.clear();
267
+        N_Electrodes.clear();
268
+
269
+        return ;
270
+    }		// -----  end of method DCSurvey::PullElectrodes  -----
271
+
272
+
273
+    //--------------------------------------------------------------------------------------
274
+    //       Class:  DCSurvey
275
+    //      Method:  AddInjection
276
+    //--------------------------------------------------------------------------------------
277
+    int DCSurvey::AddInjection ( DCIPElectrode* A, DCIPElectrode* B, const Real& J ) {
278
+        bool fA = false;
279
+        bool fB = false;
280
+        for (unsigned int i=0; i<Electrodes.size(); ++i) {
281
+            if (Electrodes[i] == A) {
282
+                A_Electrodes.push_back(i);
283
+                M_Electrodes.push_back( std::vector<int>() );
284
+                N_Electrodes.push_back( std::vector<int>() );
285
+                fA = true;
286
+            }
287
+            if (Electrodes[i] == B) {
288
+                B_Electrodes.push_back(i);
289
+                fB = true;
290
+            }
291
+            if (fA == true && fB == true) break;
292
+        }
293
+        if (!fA) {
294
+            throw std::runtime_error( "Injection point A not found" );
295
+        }
296
+        if (!fB) {
297
+            throw std::runtime_error( "Injection point B not found" );
298
+        }
299
+        J_Electrodes.push_back(J);
300
+        return A_Electrodes.size()-1; // we want index
301
+    }		// -----  end of method DCSurvey::AddInjection  -----
302
+
303
+
304
+    //--------------------------------------------------------------------------------------
305
+    //       Class:  DCSurvey
306
+    //      Method:  AddMeasurement
307
+    //--------------------------------------------------------------------------------------
308
+    void DCSurvey::AddMeasurement ( const int& iJ, DCIPElectrode* M, DCIPElectrode* N  ) {
309
+        bool fM = false;
310
+        bool fN = false;
311
+        for (unsigned int i=0; i<Electrodes.size(); ++i) {
312
+            if (Electrodes[i] == M) {
313
+                M_Electrodes[iJ].push_back(i);
314
+                fM = true;
315
+            }
316
+            if (Electrodes[i] == N) {
317
+                N_Electrodes[iJ].push_back(i);
318
+                fN = true;
319
+            }
320
+            if (fM == true && fN == true) break;
321
+        }
322
+        if (!fM) {
323
+            throw std::runtime_error( "Injection point M not found" );
324
+        }
325
+        if (!fN) {
326
+            throw std::runtime_error( "Injection point N not found" );
327
+        }
328
+        return ;
329
+    }		// -----  end of method DCSurvey::AddMeasurement  -----
330
+
331
+    //--------------------------------------------------------------------------------------
332
+    //       Class:  DCSurvey
333
+    //      Method:  AddMeasurement
334
+    //--------------------------------------------------------------------------------------
335
+
336
+    void DCSurvey::AddMeasurement ( const int& iJ, const std::string& M, const std::string& N ) {
337
+
338
+        std::pair<DCIPElectrode*, int> Mp = ElectrodeLabelMap[M];
339
+        std::pair<DCIPElectrode*, int> Np = ElectrodeLabelMap[N];
340
+
341
+        if (Mp.first == NULL) {
342
+            throw std::runtime_error( "Injection point M not found" );
343
+        }
344
+        if (Np.first == NULL) {
345
+            throw std::runtime_error( "Injection point N not found" );
346
+        }
347
+
348
+        M_Electrodes[iJ].push_back( Mp.second );
349
+        N_Electrodes[iJ].push_back( Np.second );
350
+
351
+        return ;
352
+    }		// -----  end of method DCSurvey::AddMeasurement  -----
353
+
354
+
355
+    //--------------------------------------------------------------------------------------
356
+    //       Class:  DCSurvey
357
+    //      Method:  GetA
358
+    //--------------------------------------------------------------------------------------
359
+    void DCSurvey::GetA (const int& iA, int& iB, Real& J ) {
360
+        iB = Electrodes[A_Electrodes[iA]]->GetNodeID();
361
+        J = J_Electrodes[iA];
362
+        return ;
363
+    }		// -----  end of method DCSurvey::GetA  -----
364
+
365
+    //--------------------------------------------------------------------------------------
366
+    //       Class:  DCSurvey
367
+    //      Method:  GetB
368
+    //--------------------------------------------------------------------------------------
369
+    void DCSurvey::GetB (const int& iA, int& iB, Real& J ) {
370
+        iB = Electrodes[B_Electrodes[iA]]->GetNodeID();
371
+        J = -J_Electrodes[iA];
372
+        return ;
373
+    }		// -----  end of method DCSurvey::GetA  -----
374
+
375
+
376
+}		// -----  end of Lemma  name  -----
377
+

+ 359
- 0
LemmaCore/src/FHTKey.cpp View File

@@ -0,0 +1,359 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      02/11/2014 03:42:53 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#include "FHTKey.h"
21
+
22
+namespace Lemma {
23
+
24
+    // ====================  FRIEND METHODS  =====================
25
+
26
+    std::ostream &operator<<(std::ostream &stream, const FHTKey &ob) {
27
+
28
+        stream << *(HankelTransform*)(&ob);
29
+
30
+        return stream;
31
+    }
32
+
33
+
34
+    // ====================  STATIC CONST MEMBERS     ============
35
+
36
+    const Eigen::Matrix<Real, 201, 3>  FHTKey::WT201 =
37
+        ( Eigen::Matrix<Real, 201, 3>()   <<
38
+        // Base                   J0                      J1
39
+          4.1185887075357082e-06, 1.5020099209519960e-03, 4.7827871332506182e-10
40
+        , 4.6623077830484039e-06,-1.0381698214761684e-02,-2.9784175503440788e-09
41
+        , 5.2778064058937756e-06, 3.6840860097595164e-02, 9.7723832770897220e-09
42
+        , 5.9745606155328603e-06,-8.9903380392274704e-02,-2.2382340996085809e-08
43
+        , 6.7632974390298035e-06, 1.7082286536833860e-01, 4.0446774329470848e-08
44
+        , 7.6561600412698171e-06,-2.7115749656836280e-01,-6.1734815854553919e-08
45
+        , 8.6668946776271221e-06, 3.7649328091859574e-01, 8.3293912185608189e-08
46
+        , 9.8110623273521872e-06,-4.7220778569122657e-01,-1.0249453502284080e-07
47
+        , 1.1106278265924788e-05, 5.4778211089647089e-01, 1.1780779749909977e-07
48
+        , 1.2572483264760042e-05,-5.9823516853035097e-01,-1.2870061460834850e-07
49
+        , 1.4232250593579901e-05, 6.2345791612185331e-01, 1.3559243438349901e-07
50
+        , 1.6111133551969887e-05,-6.2650436648257724e-01,-1.3921010821521872e-07
51
+        , 1.8238058880617237e-05, 6.1197225351173345e-01, 1.4065745722769670e-07
52
+        , 2.0645772109076137e-05,-5.8470173866140451e-01,-1.4074881908375281e-07
53
+        , 2.3371341696506312e-05, 5.4911055789616858e-01, 1.4051720878600928e-07
54
+        , 2.6456729726989950e-05,-5.0878861684860843e-01,-1.4040746687777830e-07
55
+        , 2.9949437945688260e-05, 4.6652106345430200e-01, 1.4127886061686993e-07
56
+        , 3.3903239082024059e-05,-4.2426478870289325e-01,-1.4315595655055356e-07
57
+        , 3.8379004719130766e-05, 3.8339538911933357e-01, 1.4689283208027915e-07
58
+        , 4.3445642455208216e-05,-3.4472344791723936e-01,-1.5210916706348747e-07
59
+        , 4.9181156785051293e-05, 3.0876891466890510e-01, 1.5989801550138741e-07
60
+        , 5.5673850034776868e-05,-2.7570439368364807e-01,-1.6940918407911260e-07
61
+        , 6.3023681838995322e-05, 2.4562331000974616e-01, 1.8227089415749844e-07
62
+        , 7.1343808090545215e-05,-2.1839207265400126e-01,-1.9695856878603369e-07
63
+        , 8.0762323056016586e-05, 1.9393194321380827e-01, 2.1603952427106760e-07
64
+        , 9.1424231478173270e-05,-1.7198162962644575e-01,-2.3691320619292838e-07
65
+        , 1.0349368102719458e-04, 1.5242270280410272e-01, 2.6369843208466607e-07
66
+        , 1.1715648947091054e-04,-1.3494945901825492e-01,-2.9202021404039016e-07
67
+        , 1.3262300547161834e-04, 1.1946763189654602e-01, 3.2852445086324662e-07
68
+        , 1.5013134705348249e-04,-1.0565870880444576e-01,-3.6589094553627693e-07
69
+        , 1.6995106759902750e-04, 9.3482355548033913e-02, 4.1487501036863030e-07
70
+        , 1.9238730581535294e-04,-8.2612525279836244e-02,-4.6327136995173986e-07
71
+        , 2.1778548356175115e-04, 7.3077763526174969e-02, 5.2852697369750518e-07
72
+        , 2.4653662386513240e-04,-6.4536481281701225e-02,-5.9034983719954077e-07
73
+        , 2.7908337099788406e-04, 5.7096310621587334e-02, 6.7710211611560898e-07
74
+        , 3.1592680530155527e-04,-5.0384859605213800e-02,-7.5512942807901028e-07
75
+        , 3.5763415767542709e-04, 4.4599557396733047e-02, 8.7062473466409799e-07
76
+        , 4.0484754250000483e-04,-3.9316995063444334e-02,-9.6788530918130449e-07
77
+        , 4.5829384344501882e-04, 3.4838544754296139e-02, 1.1222658353725904e-06
78
+        , 5.1879590436097246e-04,-3.0664946477420088e-02,-1.2417228058919743e-06
79
+        , 5.8728519754599128e-04, 2.7221072240291456e-02, 1.4493467036899140e-06
80
+        , 6.6481616442494776e-04,-2.3901586108434601e-02,-1.5932456559208080e-06
81
+        , 7.5258244942583781e-04, 2.1281566646364738e-02, 1.8747045814274419e-06
82
+        , 8.5193527698548301e-04,-1.8612484595521447e-02,-2.0433320340041385e-06
83
+        , 9.6440425461164468e-04, 1.6655386303461400e-02, 2.4285695351967146e-06
84
+        , 1.0917209222795108e-03,-1.4472420076504743e-02,-2.6179926456520528e-06
85
+        , 1.2358454107222641e-03, 1.3057747649606617e-02, 3.1511729661391781e-06
86
+        , 1.3989966190390965e-03,-1.1226286001060300e-02,-3.3492412032881268e-06
87
+        , 1.5836863762264436e-03, 1.0266818557930830e-02, 4.0964186613549959e-06
88
+        , 1.7927581125735061e-03,-8.6738022421653585e-03,-4.2758275751239154e-06
89
+        , 2.0294306362957340e-03, 8.1103368670848164e-03, 5.3371197552207799e-06
90
+        , 2.2973476893787268e-03,-6.6573628142085938e-03,-5.4435423773626499e-06
91
+        , 2.6006340455800008e-03, 6.4551189810889585e-03, 6.9725766921672099e-06
92
+        , 2.9439590142573526e-03,-5.0524015117839084e-03,-6.9045562968161745e-06
93
+        , 3.3326083277104117e-03, 5.1989014270506263e-03, 9.1397025436977438e-06
94
+        , 3.7725655187922052e-03,-3.7597430078747883e-03,-8.7148373033635960e-06
95
+        , 4.2706040416570154e-03, 4.2640545165292636e-03, 1.2029590806160379e-05
96
+        , 4.8343915539089625e-03,-2.6994965688974474e-03,-1.0927976968519436e-05
97
+        , 5.4726079656493079e-03, 3.5928000560587229e-03, 1.5912526719455299e-05
98
+        , 6.1950790728715292e-03,-1.8061291289989019e-03,-1.3582559661331659e-05
99
+        , 7.0129278325854246e-03, 3.1436470898586703e-03, 2.1176226828087565e-05
100
+        , 7.9387456086585442e-03,-1.0244200001620755e-03,-1.6678205993448338e-05
101
+        , 8.9867860248264830e-03, 2.8888297674091743e-03, 2.8384979250408712e-05
102
+        , 1.0173184409377162e-02,-3.0605070741955765e-04,-2.0132088397797457e-05
103
+        , 1.1516206210016314e-02, 2.8125907445050334e-03, 3.8372045311188108e-05
104
+        , 1.3036528203437736e-02, 3.9337862066047565e-04,-2.3702184335455945e-05
105
+        , 1.4757556829019875e-02, 2.9102041487017727e-03, 5.2385308850007940e-05
106
+        , 1.6705788547622769e-02, 1.1170884769911178e-03,-2.6854373943701261e-05
107
+        , 1.8911217773465227e-02, 3.1876763415953362e-03, 7.2318581557902158e-05
108
+        , 2.1407798659484324e-02, 1.9097806429850762e-03,-2.8535361884516687e-05
109
+        , 2.4233967845691123e-02, 3.6621020321465411e-03, 1.0108123118106823e-04
110
+        , 2.7433236218606032e-02, 2.8203783587849949e-03,-2.6788477540644352e-05
111
+        , 3.1054858792331431e-02, 4.3626885599390430e-03, 1.4319185407094621e-04
112
+        , 3.5154593024557458e-02, 3.9050024915686802e-03,-1.8108424211338017e-05
113
+        , 3.9795557242315927e-02, 5.3324923486866077e-03, 2.0573561552327273e-04
114
+        , 4.5049202393557801e-02, 5.2303399394270488e-03, 3.6361648565843316e-06
115
+        , 5.0996412085361466e-02, 6.6309348458396984e-03, 2.9991264692859609e-04
116
+        , 5.7728747844643331e-02, 6.8775540687037451e-03, 4.8993332079278846e-05
117
+        , 6.5349858773045680e-02, 8.3371689988226087e-03, 4.4354733854670903e-04
118
+        , 7.3977077298642363e-02, 8.9468564745410102e-03, 1.3589101811995494e-04
119
+        , 8.3743225592195963e-02, 1.0554326601376745e-02, 6.6515823521273764e-04
120
+        , 9.4798660459030126e-02, 1.1562765604509096e-02, 2.9451991608624389e-04
121
+        , 1.0731358818908403e-01, 1.3414536265660639e-02, 1.0105553806271136e-03
122
+        , 1.2148068500391276e-01, 1.4879837399735491e-02, 5.7533964792254050e-04
123
+        , 1.3751806344428075e-01, 1.7084241336519569e-02, 1.5535077418254303e-03
124
+        , 1.5567263036799733e-01, 1.9088092654441269e-02, 1.0621193133794828e-03
125
+        , 1.7622388825676111e-01, 2.1768513715084332e-02, 2.4128970258747457e-03
126
+        , 1.9948823835583873e-01, 2.4416120601223806e-02, 1.8929698186109245e-03
127
+        , 2.2582385189647586e-01, 2.7711234465350204e-02, 3.7800177772191607e-03
128
+        , 2.5563618439697788e-01, 3.1127164234404547e-02, 3.2937343278959356e-03
129
+        , 2.8938421793905067e-01, 3.5184140220277452e-02, 5.9612179800391544e-03
130
+        , 3.2758752752368947e-01, 3.9497913113638941e-02, 5.6295935320552241e-03
131
+        , 3.7083428029819565e-01, 4.4449762157204989e-02, 9.4422526803168080e-03
132
+        , 4.1979029080811425e-01, 4.9758433269983887e-02, 9.4810228247137925e-03
133
+        , 4.7520927168614446e-01, 5.5667457114992429e-02, 1.4979159139973408e-02
134
+        , 5.3794443759467447e-01, 6.1949790434151823e-02, 1.5745093424331037e-02
135
+        , 6.0896164107289685e-01, 6.8682064905571841e-02, 2.3708966370000140e-02
136
+        , 6.8935424252422239e-01, 7.5616743950118387e-02, 2.5740590762136872e-02
137
+        , 7.8035994327803426e-01, 8.2584983563572259e-02, 3.7232782843117498e-02
138
+        , 8.8337984088275090e-01, 8.9193635262987042e-02, 4.1225008900614292e-02
139
+        , 1.0000000000000000e+00, 9.4874686942005279e-02, 5.7507103212277359e-02
140
+        , 1.1320158709991752e+00, 9.8891681869094042e-02, 6.4044642846235691e-02
141
+        , 1.2814599321940212e+00, 1.0004294654495730e-01, 8.6091796551857253e-02
142
+        , 1.4506329812931589e+00, 9.7016844329802857e-02, 9.4717139804457451e-02
143
+        , 1.6421395578187052e+00, 8.7789596149914384e-02, 1.2172497389177185e-01
144
+        , 1.8589280418463421e+00, 7.0509767592855419e-02, 1.2853597000398900e-01
145
+        , 2.1043360464154781e+00, 4.2778853484849347e-02, 1.5450777327408322e-01
146
+        , 2.3821418024579781e+00, 3.5584532926218175e-03, 1.4755964090969320e-01
147
+        , 2.6966223273530128e+00,-4.7210453264879347e-02, 1.5621399202016978e-01
148
+        , 3.0526192726543444e+00,-1.0489787743225988e-01, 1.1147620703185755e-01
149
+        , 3.4556134647626755e+00,-1.6020950407348281e-01, 7.7489831356083380e-02
150
+        , 3.9118092861497971e+00,-1.9459781573132096e-01,-2.7628266850147711e-02
151
+        , 4.4282301962435247e+00,-1.8490774599542381e-01,-1.0198730178317840e-01
152
+        , 5.0128268625854631e+00,-1.0754165020025190e-01,-2.2039889971111640e-01
153
+        , 5.6745995670177445e+00, 3.6037727487476613e-02,-2.1185762869925318e-01
154
+        , 6.4237367714291338e+00, 1.9759013047489976e-01,-1.6052415083152241e-01
155
+        , 7.2717719763787807e+00, 2.6132313321851336e-01, 9.1649025798681089e-02
156
+        , 8.2317612875478190e+00, 1.1713996822458939e-01, 2.3792823877700942e-01
157
+        , 9.3184844237807365e+00,-1.8758779281301441e-01, 2.6075777853738125e-01
158
+        , 1.0548672261378394e+01,-3.0238114997462151e-01,-1.5662188259001042e-01
159
+        , 1.1941264417849103e+01, 4.8163135684567732e-02,-2.8932081756330175e-01
160
+        , 1.3517700840802913e+01, 3.6399529664885466e-01, 1.3148519116247689e-02
161
+        , 1.5302251891207787e+01,-1.4910233461562913e-01, 4.2691302759079564e-01
162
+        , 1.7322392002874359e+01,-2.6373490348543854e-01,-4.0005050006489040e-01
163
+        , 1.9609222670922968e+01, 4.0362661807718703e-01, 1.1513789407450359e-01
164
+        , 2.2197951281441636e+01,-3.1409794650104578e-01, 9.3748244358717620e-02
165
+        , 2.5128433154258410e+01, 1.8179369405131079e-01,-1.6037231301955096e-01
166
+        , 2.8445785143962375e+01,-9.0738718042631769e-02, 1.5071857939129532e-01
167
+        , 3.2201080245997971e+01, 4.2946487545160242e-02,-1.2120369075996129e-01
168
+        , 3.6452133901787732e+01,-2.0586135807067835e-02, 9.4110656079982341e-02
169
+        , 4.1264394108610787e+01, 1.0392667161913182e-02,-7.3742238434584328e-02
170
+        , 4.6711949038112273e+01,-5.6117848068723023e-03, 5.9038567576124905e-02
171
+        , 5.2878667676447755e+01, 3.2402025511569896e-03,-4.8288117528475852e-02
172
+        , 5.9859491047029913e+01,-1.9858724388273777e-03, 4.0197054299576880e-02
173
+        , 6.7761893895170928e+01, 1.2807317326135252e-03,-3.3919787720641081e-02
174
+        , 7.6707539338295589e+01,-8.6253791756068252e-04, 2.8918247156763971e-02
175
+        , 8.6834151956244213e+01, 6.0296590782143555e-04,-2.4845271759013743e-02
176
+        , 9.8297638159222487e+01,-4.3548936996943465e-04, 2.1470449751150148e-02
177
+        , 1.1127448647797397e+02, 3.2375891570874245e-04,-1.8635828020057092e-02
178
+        , 1.2596448473034971e+02,-2.4698212240059978e-04, 1.6229579362363859e-02
179
+        , 1.4259379589698909e+02, 1.9279062274925971e-04,-1.4170085406786529e-02
180
+        , 1.6141844006140866e+02,-1.5357911509105972e-04, 1.2396084121011890e-02
181
+        , 1.8272823602144376e+02, 1.2453787849367440e-04,-1.0860414401084047e-02
182
+        , 2.0685126325595743e+02,-1.0255126402954421e-04, 9.5259444245356633e-03
183
+        , 2.3415891294197226e+02, 8.5558482209476271e-05,-8.3628577447233381e-03
184
+        , 2.6507160578622688e+02,-7.2170928476334345e-05, 7.3468029551253195e-03
185
+        , 3.0006526470124555e+02, 6.1436863283080017e-05,-6.4576043210966359e-03
186
+        , 3.3967864197737873e+02,-5.2693349406473615e-05, 5.6783439955994880e-03
187
+        , 3.8452161375783919e+02, 4.5471255142623729e-05,-4.9946949167265437e-03
188
+        , 4.3528456951608860e+02,-3.9433284158653591e-05, 4.3944258108608806e-03
189
+        , 4.9274904109325632e+02, 3.4332971164795619e-05,-3.8670264019660858e-03
190
+        , 5.5779973493719069e+02,-2.9987212220165472e-05, 3.4034180355556670e-03
191
+        , 6.3143815278803334e+02, 2.6257657435614391e-05,-2.9957260668529964e-03
192
+        , 7.1479801051045558e+02,-2.3037978256349448e-05, 2.6370977166248776e-03
193
+        , 8.0916269245647072e+02, 2.0245071331016652e-05,-2.3215540117372982e-03
194
+        , 9.1598501008114988e+02,-1.7812925644382519e-05, 2.0438677474690805e-03
195
+        , 1.0369095690092008e+03, 1.5688305607849465e-05,-1.7994616759226389e-03
196
+        , 1.1737980889093292e+03,-1.3827679492110470e-05, 1.5843226896713463e-03
197
+        , 1.3287580659938624e+03, 1.2195005442258958e-05,-1.3949288614414647e-03
198
+        , 1.5041752194232211e+03,-1.0760110818279243e-05, 1.2281869708886250e-03
199
+        , 1.7027502211507524e+03, 9.4974857670959145e-06,-1.0813786997088304e-03
200
+        , 1.9275402746900081e+03,-8.3853711343938338e-06, 9.5211407460757294e-04
201
+        , 2.1820061829391980e+03, 7.4050612540713192e-06,-8.3829103020448140e-04
202
+        , 2.4700656297055034e+03,-6.5403682860228500e-06, 7.3806018220987763e-04
203
+        , 2.7961534952362003e+03, 5.7772102413267325e-06,-6.4979406671247244e-04
204
+        , 3.1652901343571971e+03,-5.1032933218796731e-06, 5.7206022901230412e-04
205
+        , 3.5831586684094545e+03, 4.5078641320869195e-06,-5.0359764543483573e-04
206
+        , 4.0561924809477755e+03,-3.9815111951817114e-06, 4.4329604122300101e-04
207
+        , 4.5916742642604040e+03, 3.5159993210292339e-06,-3.9017773206623073e-04
208
+        , 5.1978481416012310e+03,-3.1041249680128287e-06, 3.4338166974098888e-04
209
+        , 5.8840465913361650e+03, 2.7395854235553632e-06,-3.0214941633163506e-04
210
+        , 6.6608341270911405e+03,-2.4168587823583312e-06, 2.6581280850704716e-04
211
+        , 7.5401699459601114e+03, 2.1310948134441218e-06,-2.3378310479588391e-04
212
+        , 8.5355920488578286e+03,-1.8780185742021288e-06, 2.0554143583887405e-04
213
+        , 9.6624256676814348e+03, 1.6538488252707735e-06,-1.8063040107732216e-04
214
+        , 1.0938019208165191e+04,-1.4552318768651144e-06, 1.5864667598176302e-04
215
+        , 1.2382011340936813e+04, 1.2791890865306748e-06,-1.3923451235168759e-04
216
+        , 1.4016633352832258e+04,-1.1230741959148155e-06, 1.2208003098625932e-04
217
+        , 1.5867051413382505e+04, 9.8453630538596172e-07,-1.0690622166177854e-04
218
+        , 1.7961754025908867e+04,-8.6148574493190796e-07, 9.3468580362568137e-05
219
+        , 2.0332990628312182e+04, 7.5206242699701732e-07,-8.1551328581234316e-05
220
+        , 2.3017268096126892e+04,-6.5460810334682633e-07, 7.0964174631531072e-05
221
+        , 2.6055912791858576e+04, 5.6764451596029765e-07,-6.1539592468666665e-05
222
+        , 2.9495706813754354e+04,-4.8985884555184997e-07, 5.3130609116145443e-05
223
+        , 3.3389608239508460e+04, 4.2009674106879252e-07,-4.5609105983126460e-05
224
+        , 3.7797566453568354e+04,-3.5736212641225517e-07, 3.8864648584181207e-05
225
+        , 4.2787445110585410e+04, 3.0082215969939671e-07,-3.2803856352344075e-05
226
+        , 4.8436066944688770e+04,-2.4981510481639669e-07, 2.7350296775876261e-05
227
+        , 5.4830396510166145e+04, 2.0385823466866512e-07,-2.2444816150805301e-05
228
+        , 6.2068879062685897e+04,-1.6265189071584773e-07, 1.8046076281584239e-05
229
+        , 7.0262956194088882e+04, 1.2607416700611311e-07,-1.4130826937491561e-05
230
+        , 7.9538781555028458e+04,-9.4158417913450858e-08, 1.0693106849359383e-05
231
+        , 9.0039163080228551e+04, 6.7043911217063425e-08,-7.7412053314530284e-06
232
+        , 1.0192576161830177e+05,-4.4891090827293947e-08, 5.2910576443698300e-06
233
+        , 1.1538157981559623e+05, 2.7761325666544702e-08,-3.3552268362550323e-06
234
+        , 1.3061377957221285e+05,-1.5480404355710375e-08, 1.9282956206367452e-06
235
+        , 1.4785687144693290e+05, 7.5327300141098751e-09,-9.7253712572058755e-07
236
+        , 1.6737632511421290e+05,-3.0524770418657847e-09, 4.1100807632959352e-07
237
+        , 1.8947265645880660e+05, 9.5877856096830783e-10,-1.3553176263207053e-07
238
+        , 2.1448605423174356e+05,-2.0575286298055636e-10, 3.0748587523233524e-08
239
+        , 2.4280161749832361e+05, 2.2414416956474645e-11,-3.5668195345476294e-09 ).finished();
240
+
241
+    // ====================  LIFECYCLE     =======================
242
+
243
+    //--------------------------------------------------------------------------------------
244
+    //       Class:  FHTKey
245
+    //      Method:  FHTKey
246
+    // Description:  constructor (protected)
247
+    //--------------------------------------------------------------------------------------
248
+    FHTKey::FHTKey (const std::string& name) : HankelTransform(name) {
249
+
250
+    }  // -----  end of method FHTKey::FHTKey  (constructor)  -----
251
+
252
+
253
+    //--------------------------------------------------------------------------------------
254
+    //       Class:  FHTKey
255
+    //      Method:  New()
256
+    // Description:  public constructor
257
+    //--------------------------------------------------------------------------------------
258
+    FHTKey* FHTKey::New() {
259
+        FHTKey*  Obj = new FHTKey("FHTKey");
260
+        Obj->AttachTo(Obj);
261
+        return Obj;
262
+    }
263
+
264
+    //--------------------------------------------------------------------------------------
265
+    //       Class:  FHTKey
266
+    //      Method:  ~FHTKey
267
+    // Description:  destructor (protected)
268
+    //--------------------------------------------------------------------------------------
269
+    FHTKey::~FHTKey () {
270
+
271
+    }  // -----  end of method FHTKey::~FHTKey  (destructor)  -----
272
+
273
+    //--------------------------------------------------------------------------------------
274
+    //       Class:  FHTKey
275
+    //      Method:  Delete
276
+    // Description:  public destructor
277
+    //--------------------------------------------------------------------------------------
278
+    void FHTKey::Delete() {
279
+        this->DetachFrom(this);
280
+    }
281
+
282
+    //--------------------------------------------------------------------------------------
283
+    //       Class:  FHTKey
284
+    //      Method:  Release
285
+    // Description:  destructor (protected)
286
+    //--------------------------------------------------------------------------------------
287
+    void FHTKey::Release() {
288
+        delete this;
289
+    }
290
+
291
+
292
+    //--------------------------------------------------------------------------------------
293
+    //       Class:  FHTKey
294
+    //      Method:  Zgauss
295
+    //--------------------------------------------------------------------------------------
296
+    Complex FHTKey::Zgauss ( const int &ikk, const EMMODE &imode,
297
+                            const int &itype, const Real &rho,
298
+                            const Real &wavef, KernelEm1DBase *Kernel ) {
299
+ 		return Zans(0, Kernel->GetManagerIndex());
300
+    }		// -----  end of method FHTKey::ComputeRelated  -----
301
+
302
+
303
+    //--------------------------------------------------------------------------------------
304
+    //       Class:  FHTKey
305
+    //      Method:  ComputeRelated
306
+    //--------------------------------------------------------------------------------------
307
+    void FHTKey::ComputeRelated ( const Real& rho, KernelEm1DBase* Kernel ) {
308
+        return ;
309
+    }		// -----  end of method FHTKey::ComputeRelated  -----
310
+
311
+    //--------------------------------------------------------------------------------------
312
+    //       Class:  FHTKey
313
+    //      Method:  ComputeRelated
314
+    //--------------------------------------------------------------------------------------
315
+    void FHTKey::ComputeRelated ( const Real& rho, std::vector< KernelEm1DBase* > KernelVec ) {
316
+        return ;
317
+    }		// -----  end of method FHTKey::ComputeRelated  -----
318
+
319
+    //--------------------------------------------------------------------------------------
320
+    //       Class:  FHTKey
321
+    //      Method:  ComputeRelated
322
+    //--------------------------------------------------------------------------------------
323
+    void FHTKey::ComputeRelated ( const Real& rho, KernelEM1DManager* KernelManager ) {
324
+
325
+        //kernelVec = KernelManager->GetSTLVector();
326
+        int nrel = (int)(KernelManager->GetSTLVector().size());
327
+        Eigen::Matrix<Complex, 201, Eigen::Dynamic > Zwork;
328
+        // TODO, if we want to allow lagged, then 1 below should be nlag
329
+        Zans= Eigen::Matrix<Complex, Eigen::Dynamic, Eigen::Dynamic>::Zero(1, nrel);
330
+        Zwork.resize(201, nrel);
331
+        VectorXr lambda = WT201.col(0).array()/rho;
332
+        int NumFun = 0;
333
+        int idx = 0;
334
+
335
+        // Get Kernel values
336
+        for (int ir=0; ir<lambda.size(); ++ir) {
337
+            // irelated loop
338
+            ++NumFun;
339
+            KernelManager->ComputeReflectionCoeffs(lambda(ir), idx, rho);
340
+            for (int ir2=0; ir2<nrel; ++ir2) {
341
+                // Zwork* needed due to sign convention of filter weights
342
+ 			    Zwork(ir, ir2) = std::conj(KernelManager->GetSTLVector()[ir2]->RelBesselArg(lambda(ir)));
343
+            }
344
+
345
+        }
346
+
347
+        // We diverge slightly from Key here, each kernel is evaluated seperately, whereby instead
348
+        // they prefer to sum them. The reason is that all those terms have been removed from the kernels
349
+        // in the interests of making them as generic and reusable as possible. This approach requires slightly
350
+        // more multiplies, but the same number of kernel evaluations, which is the expensive part.
351
+        // Inner product and scale
352
+        for (int ir2=0; ir2<nrel; ++ir2) {
353
+            Zans(0, ir2) = Zwork.col(ir2).dot(WT201.col(KernelManager->GetSTLVector()[ir2]->GetBesselOrder() + 1))/rho;
354
+        }
355
+
356
+        return ;
357
+    }		// -----  end of method FHTKey::ComputeRelated  -----
358
+
359
+}		// -----  end of Lemma  name  -----

+ 259
- 0
LemmaCore/src/FHTKey101.cpp View File

@@ -0,0 +1,259 @@
1
+/* This file is part of Lemma, a geophysical modelling and inversion API.
2
+ * More information is available at http://lemmasoftware.org
3
+ */
4
+
5
+/* This Source Code Form is subject to the terms of the Mozilla Public
6
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
7
+ * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ */
9
+
10
+/**
11
+ * @file
12
+ * @date      02/11/2014 03:42:53 PM
13
+ * @version   $Id$
14
+ * @author    Trevor Irons (ti)
15
+ * @email     Trevor.Irons@xri-geo.com
16
+ * @copyright Copyright (c) 2014, XRI Geophysics, LLC
17
+ * @copyright Copyright (c) 2014, Trevor Irons
18
+ */
19
+
20
+#include "FHTKey101.h"
21
+
22
+namespace Lemma {
23
+
24
+    // ====================  FRIEND METHODS  =====================
25
+
26
+    std::ostream &operator<<(std::ostream &stream, const FHTKey101 &ob) {
27
+
28
+        stream << *(HankelTransform*)(&ob);
29
+
30
+        return stream;
31
+    }
32
+
33
+
34
+    // ====================  STATIC CONST MEMBERS     ============
35
+
36
+    const Eigen::Matrix<Real, 101, 3>  FHTKey101::WT101 =
37
+        ( Eigen::Matrix<Real, 101, 3>()   <<
38
+       // Base                   J0                      J1
39
+       5.5308437014783363e-04,   5.1818808036862153e-02,   4.1746363961646286e-06,
40
+       6.4259236035555788e-04,  -2.9258492652779172e-01,  -2.5993370843637242e-05,
41
+       7.4658580837667996e-04,   8.7289913080159265e-01,   9.2506838353721647e-05,
42
+       8.6740895730700251e-04,  -1.8525183961240297e+00,  -2.4318740269846489e-04,
43
+       1.0077854290485113e-03,   3.2096055660873608e+00,   5.2276050788732404e-04,
44
+       1.1708796207911744e-03,  -4.9248158048315069e+00,  -9.5803859755432658e-04,
45
+       1.3603680375478939e-03,   7.0219167445719828e+00,   1.5308357107396591e-03,
46
+       1.5805221687362171e-03,  -9.4781099645811544e+00,  -2.1584605764249656e-03,
47
+       1.8363047770289071e-03,   1.2098564895534539e+01,   2.7161344302423967e-03,
48
+       2.1334817700377098e-03,  -1.4476661837664896e+01,  -3.0845361397036195e-03,
49
+       2.4787521766663585e-03,   1.6146079632847474e+01,   3.2133980102756368e-03,
50
+       2.8798991580882430e-03,  -1.6810370923047440e+01,  -3.1305779240645847e-03,
51
+       3.3459654574712720e-03,   1.6506202923977266e+01,   2.9239120736637542e-03,
52
+       3.8874572434761303e-03,  -1.5534747212675301e+01,  -2.6680602560576316e-03,
53
+       4.5165809426126703e-03,   1.4267433361428399e+01,   2.4131379039476304e-03,
54
+       5.2475183991813838e-03,  -1.2939053370802849e+01,  -2.1549566068119440e-03,
55
+       6.0967465655156379e-03,   1.1628520257389562e+01,   1.9058200916563901e-03,
56
+       7.0834089290521185e-03,  -1.0325503688577493e+01,  -1.6533122444456158e-03,
57
+       8.2297470490200302e-03,   9.0574401975545840e+00,   1.4391633836110848e-03,
58
+       9.5616019305435132e-03,  -7.8759096646654951e+00,  -1.2363666069459527e-03,
59
+       1.1108996538242306e-02,   6.8446506699312666e+00,   1.0907227256323094e-03,
60
+       1.2906812580479873e-02,  -5.9542991234257840e+00,  -9.2712769282234358e-04,
61
+       1.4995576820477703e-02,   5.1830565431894602e+00,   8.2888526218099687e-04,
62
+       1.7422374639493515e-02,  -4.4805481279340267e+00,  -6.7675613963809832e-04,
63
+       2.0241911445804391e-02,   3.8608298760715378e+00,   6.3558641899842260e-04,
64
+       2.3517745856009110e-02,  -3.3125736597743227e+00,  -4.8591507683128695e-04,
65
+       2.7323722447292573e-02,   2.8648088091590589e+00,   5.1892328126100203e-04,
66
+       3.1745636378067953e-02,  -2.4710577422247479e+00,  -3.3190335155472070e-04,
67
+       3.6883167401240015e-02,   2.1450315408533416e+00,   4.6189809360776176e-04,
68
+       4.2852126867040180e-02,  -1.8334353019592327e+00,  -1.8326476919948130e-04,
69
+       4.9787068367863944e-02,   1.5850020809005190e+00,   4.7669939315323097e-04,
70
+       5.7844320874838456e-02,  -1.3468969891769780e+00,  -1.7380345519175726e-05,
71
+       6.7205512739749784e-02,   1.1802299801807625e+00,   5.9009214750893949e-04,
72
+       7.8081666001153169e-02,  -9.9988174688478793e-01,   2.1645139320505843e-04,
73
+       9.0717953289412512e-02,   8.8503813256539254e-01,   8.5203135609860704e-04,
74
+       1.0539922456186433e-01,  -7.3165077099639619e-01,   5.9560990889710838e-04,
75
+       1.2245642825298191e-01,   6.5909386165012596e-01,   1.3651107378683781e-03,
76
+       1.4227407158651359e-01,  -5.3038429622108840e-01,   1.2606987195022564e-03,
77
+       1.6529888822158656e-01,   5.0119791866928076e-01,   2.3131990435032663e-03,
78
+       1.9204990862075413e-01,  -3.8269840749371159e-01,   2.4572002938857678e-03,
79
+       2.2313016014842982e-01,   3.8622329595139565e-01,   4.0408430887840449e-03,
80
+       2.5924026064589156e-01,  -2.6413330193320073e-01,   4.6278078809669602e-03,
81
+       3.0119421191220208e-01,   3.0353632730294311e-01,   7.1437051276295131e-03,
82
+       3.4993774911115533e-01,  -1.7255655176111537e-01,   8.5723466849983495e-03,
83
+       4.0656965974059917e-01,   2.5119774955173280e-01,   1.2684763573137947e-02,
84
+       4.7236655274101469e-01,  -9.8536724013140092e-02,   1.5643387012124067e-02,
85
+       5.4881163609402650e-01,   2.1755876398162183e-01,   2.2480928663078600e-02,
86
+       6.3762815162177333e-01,  -3.4268716744688760e-02,   2.8124131719595692e-02,
87
+       7.4081822068171788e-01,   1.9925218957836366e-01,   3.9373999883133115e-02,
88
+       8.6070797642505781e-01,   1.8319735495994052e-02,   4.9445586323210833e-02,
89
+       1.0000000000000000e+00,   1.8963099219918259e-01,   6.7326587032714463e-02,
90
+       1.1618342427282831e+00,   5.7228135568732394e-02,   8.3541701874077570e-02,
91
+       1.3498588075760032e+00,   1.7266316834158107e-01,   1.0961776964853986e-01,
92
+       1.5683121854901687e+00,   6.8141322181604499e-02,   1.3118216481048459e-01,
93
+       1.8221188003905089e+00,   1.2468074033081850e-01,   1.6144181878027153e-01,
94
+       2.1170000166126748e+00,   2.1678852838804014e-02,   1.7704476632134886e-01,
95
+       2.4596031111569494e+00,   1.1114005126278175e-02,   1.9032654055463888e-01,
96
+       2.8576511180631639e+00,  -1.0424806190544497e-01,   1.6333927603825021e-01,
97
+       3.3201169227365472e+00,  -1.6473681128667569e-01,   1.1034442879456068e-01,
98
+       3.8574255306969740e+00,  -2.3603153458714107e-01,  -1.1282682226217962e-02,
99
+       4.4816890703380645e+00,  -2.2093965064386309e-01,  -1.4579378661401318e-01,
100
+       5.2069798271798486e+00,  -7.5633542915308175e-02,  -2.7560051939484942e-01,
101
+       6.0496474644129448e+00,   1.3358180223826097e-01,  -2.3333751023296440e-01,
102
+       7.0286875805892928e+00,   3.3949946683489907e-01,  -5.9615109981928909e-03,
103
+       8.1661699125676499e+00,   1.2815187347111337e-01,   3.2380356528743487e-01,
104
+       9.4877358363585262e+00,  -2.2988301163130145e-01,   2.1970582679149839e-01,
105
+       1.1023176380641601e+01,  -3.3425750283830036e-01,  -2.8302631898505476e-01,
106
+       1.2807103782663029e+01,   4.4350537603751145e-01,  -2.2706962776315812e-01,
107
+       1.4879731724872830e+01,  -8.8943820418669634e-02,   4.7351258711649669e-01,
108
+       1.7287781840567639e+01,  -1.8646079800862164e-01,  -3.5417866045339608e-01,
109
+       2.0085536923187668e+01,   2.4494657419883456e-01,   1.6582378621661517e-01,
110
+       2.3336064580942711e+01,  -2.0169045144304532e-01,  -5.1221107687420810e-02,
111
+       2.7112638920657883e+01,   1.4661206655803793e-01,   3.5484710794282063e-03,
112
+       3.1500392308747923e+01,  -1.0564640256629308e-01,   1.1614894738175324e-02,
113
+       3.6598234443677974e+01,   7.8487036158411266e-02,  -1.4776256489774963e-02,
114
+       4.2521082000062783e+01,  -6.0533748554794195e-02,   1.4194293010344678e-02,
115
+       4.9402449105530167e+01,   4.8243702864613026e-02,  -1.2609914713728791e-02,
116
+       5.7397457045446188e+01,  -3.9347085461672239e-02,   1.0854082569077052e-02,
117
+       6.6686331040925154e+01,   3.2489421068688185e-02,  -9.2082270347668624e-03,
118
+       7.7478462925260828e+01,  -2.6982535264609676e-02,   7.7880648968821110e-03,
119
+       9.0017131300521811e+01,   2.2530196869950080e-02,  -6.6089268276601255e-03,
120
+       1.0458498557711414e+02,  -1.8947601435977172e-02,   5.6159700146012417e-03,
121
+       1.2151041751873485e+02,   1.6017457455233256e-02,  -4.7432063636330263e-03,
122
+       1.4117496392147686e+02,  -1.3519422964231352e-02,   3.9609893136500528e-03,
123
+       1.6402190729990167e+02,   1.1318328695851308e-02,  -3.2753768787828126e-03,
124
+       1.9056626845862999e+02,  -9.3839154851987506e-03,   2.6945716306237466e-03,
125
+       2.2140641620418697e+02,   7.7256174599644543e-03,  -2.2042319512562145e-03,
126
+       2.5723755590577474e+02,  -6.3199190181430056e-03,   1.7733135127602079e-03,
127
+       2.9886740096706029e+02,   5.0986473606509210e-03,  -1.3773733375919272e-03,
128
+       3.4723438047873447e+02,  -3.9929354358609528e-03,   1.0137885881408651e-03,
129
+       4.0342879349273511e+02,   2.9783618569305080e-03,  -6.9751488719640639e-04,
130
+       4.6871738678241655e+02,  -2.0802747552777045e-03,   4.4545125438205673e-04,
131
+       5.4457191012592898e+02,   1.3429398653973710e-03,  -2.6373575275283686e-04,
132
+       6.3270229281225352e+02,  -7.9345560431147465e-04,   1.4519595835116970e-04,
133
+       7.3509518924197266e+02,   4.2530878973518046e-04,  -7.4640168948626184e-05,
134
+       8.5405876252615155e+02,  -2.0457624610548748e-04,   3.5826939350044606e-05,
135
+       9.9227471560502534e+02,   8.6750842046621606e-05,  -1.5854604622793124e-05,
136
+       1.1528587427833875e+03,  -3.1406113278782205e-05,   6.2412989356183992e-06,
137
+       1.3394307643944169e+03,   9.1385289919391839e-06,  -2.0349222128793154e-06,
138
+       1.5561965278371533e+03,  -1.8949818224609619e-06,   4.8072849734177625e-07,
139
+       1.8080424144560632e+03,   2.0794387557779629e-07,  -6.0462736574031818e-08).finished();
140
+
141
+    // ====================  LIFECYCLE     =======================
142
+
143
+    //--------------------------------------------------------------------------------------
144
+    //       Class:  FHTKey101
145
+    //      Method:  FHTKey101
146
+    // Description:  constructor (protected)
147
+    //--------------------------------------------------------------------------------------
148
+    FHTKey101::FHTKey101 (const std::string& name) : HankelTransform(name) {
149
+
150
+    }  // -----  end of method FHTKey101::FHTKey101  (constructor)  -----
151
+
152
+
153
+    //--------------------------------------------------------------------------------------
154
+    //       Class:  FHTKey101
155
+    //      Method:  New()
156
+    // Description:  public constructor
157
+    //--------------------------------------------------------------------------------------
158
+    FHTKey101* FHTKey101::New() {
159
+        FHTKey101*  Obj = new FHTKey101("FHTKey101");
160
+        Obj->AttachTo(Obj);
161
+        return Obj;
162
+    }
163
+
164
+    //--------------------------------------------------------------------------------------
165
+    //       Class:  FHTKey101
166
+    //      Method:  ~FHTKey101
167
+    // Description:  destructor (protected)
168
+    //--------------------------------------------------------------------------------------
169
+    FHTKey101::~FHTKey101 () {
170
+
171
+    }  // -----  end of method FHTKey101::~FHTKey101  (destructor)  -----
172
+
173
+    //--------------------------------------------------------------------------------------
174
+    //       Class:  FHTKey101
175
+    //      Method:  Delete
176
+    // Description:  public destructor
177
+    //--------------------------------------------------------------------------------------
178
+    void FHTKey101::Delete() {
179
+        this->DetachFrom(this);
180
+    }
181
+
182
+    //--------------------------------------------------------------------------------------
183
+    //       Class:  FHTKey101
184
+    //      Method:  Release
185
+    // Description:  destructor (protected)
186
+    //--------------------------------------------------------------------------------------
187
+    void FHTKey101::Release() {
188
+        delete this;
189
+    }
190
+
191
+
192
+    //--------------------------------------------------------------------------------------
193
+    //       Class:  FHTKey101
194
+    //      Method:  Zgauss
195
+    //--------------------------------------------------------------------------------------
196
+    Complex FHTKey101::Zgauss ( const int &ikk, const EMMODE &imode,
197
+                            const int &itype, const Real &rho,
198
+                            const Real &wavef, KernelEm1DBase *Kernel ) {
199
+ 		return Zans(0, Kernel->GetManagerIndex());
200
+    }		// -----  end of method FHTKey101::ComputeRelated  -----
201
+
202
+
203
+    //--------------------------------------------------------------------------------------
204
+    //       Class:  FHTKey101
205
+    //      Method:  ComputeRelated
206
+    //--------------------------------------------------------------------------------------
207
+    void FHTKey101::ComputeRelated ( const Real& rho, KernelEm1DBase* Kernel ) {
208
+        return ;
209
+    }		// -----  end of method FHTKey101::ComputeRelated  -----
210
+
211
+    //--------------------------------------------------------------------------------------
212
+    //       Class:  FHTKey101
213
+    //      Method:  ComputeRelated
214
+    //--------------------------------------------------------------------------------------
215
+    void FHTKey101::ComputeRelated ( const Real& rho, std::vector< KernelEm1DBase* > KernelVec ) {
216
+        return ;
217
+    }		// -----  end of method FHTKey101::ComputeRelated  -----
218
+
219
+    //--------------------------------------------------------------------------------------
220
+    //       Class:  FHTKey101
221
+    //      Method:  ComputeRelated
222
+    //--------------------------------------------------------------------------------------
223
+    void FHTKey101::ComputeRelated ( const Real& rho, KernelEM1DManager* KernelManager ) {
224
+
225
+        //kernelVec = KernelManager->GetSTLVector();
226
+        int nrel = (int)(KernelManager->GetSTLVector().size());
227
+        Eigen::Matrix<Complex, 101, Eigen::Dynamic > Zwork;
228
+        // TODO, if we want to allow lagged, then 1 below should be nlag
229
+        Zans= Eigen::Matrix<Complex, Eigen::Dynamic, Eigen::Dynamic>::Zero(1, nrel);
230
+        Zwork.resize(101, nrel);
231
+        VectorXr lambda = WT101.col(0).array()/rho;
232
+        int NumFun = 0;
233
+        int idx = 0;
234
+
235
+        // Get Kernel values
236
+        for (int ir=0; ir<lambda.size(); ++ir) {
237
+            // irelated loop
238
+            ++NumFun;
239
+            KernelManager->ComputeReflectionCoeffs(lambda(ir), idx, rho);
240
+            for (int ir2=0; ir2<nrel; ++ir2) {
241
+                // Zwork* needed due to sign convention of filter weights
242
+ 			    Zwork(ir, ir2) = std::conj(KernelManager->GetSTLVector()[ir2]->RelBesselArg(lambda(ir)));
243
+            }
244
+
245
+        }
246
+
247
+        // We diverge slightly from Key here, each kernel is evaluated seperately, whereby instead
248
+        // they prefer to sum them. The reason is that all those terms have been removed from the kernels
249
+        // in the interests of making them as generic and reusable as possible. This approach requires slightly
250
+        // more multiplies, but the same number of kernel evaluations, which is the expensive part.
251
+        // Inner product and scale
252
+        for (int ir2=0; ir2<nrel; ++ir2) {
253
+            Zans(0, ir2) = Zwork.col(ir2).dot(WT101.col(KernelManager->GetSTLVector()[ir2]->GetBesselOrder() + 1))/rho;
254
+        }
255
+
256
+        return ;
257
+    }		// -----  end of method FHTKey101::ComputeRelated  -----
258
+
259
+}		// -----  end of Lemma  name  -----

+ 0
- 0
LemmaCore/src/FHTKey51.cpp View File


Some files were not shown because too many files changed in this diff

Loading…
Cancel
Save