Lemma is an Electromagnetics API
Vous ne pouvez pas sélectionner plus de 25 sujets Les noms de sujets doivent commencer par une lettre ou un nombre, peuvent contenir des tirets ('-') et peuvent comporter jusqu'à 35 caractères.

utTEMSurvey.cpp 9.9KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197
  1. /* This file is part of Lemma, a geophysical modelling and inversion API.
  2. * More information is available at http://lemmasoftware.org
  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. * @date 10/06/2014 10:37:30 AM
  11. * @version $Id$
  12. * @author Trevor Irons (ti)
  13. * @email Trevor.Irons@xri-geo.com
  14. * @copyright Copyright (c) 2014, XRI Geophysics, LLC
  15. * @copyright Copyright (c) 2014, Trevor Irons
  16. */
  17. #include "Lemma"
  18. using namespace Lemma;
  19. int main() {
  20. // Each pulse sequence functions as an autonomous transmitter. A record may contain multiple transmitters (moments).
  21. // There is some small overhead for wire loop locations, but generality is retained doing this, as well as monitoring of
  22. // slight changes in geometry for both pulses.
  23. TEMTransmitter* TxHM = TEMTransmitter::New();
  24. TxHM->SetRepFrequency( 20, KHZ );
  25. VectorXr Times (18);
  26. VectorXr Amps (18);
  27. Times << 0.0, 0.03051, 0.10267, 0.19408, 0.19889, 0.21332, 0.74249, 1.3775, 1.83452, 2.52245, \
  28. 3.191132, 3.9031135, 4.0, 4.00484486, 4.123904, 4.200182, 4.20732, 4.212946;
  29. Amps << 0.0, 14.71872, 62.34372, 114.84372, 117.84372, 118.96872, 118.96872, 118.96872, 118.96872,\
  30. 118.59372, 119.34372, 120.0, 120.0, 117.94176, 47.60364, 0.8905848, 0.1203888, 0.0;
  31. TxHM->SetWaveform( Times, Amps, MILLISEC );
  32. // Define wire loop
  33. TxHM->SetNumberOfPoints(8);
  34. TxHM->SetPoint(0, Vector3r( -16.10, 2.13, -34));
  35. TxHM->SetPoint(1, Vector3r( -7.51, 10.72, -34));
  36. TxHM->SetPoint(2, Vector3r( 7.51, 10.72, -34));
  37. TxHM->SetPoint(3, Vector3r( 14.92, 3.31, -34));
  38. TxHM->SetPoint(4, Vector3r( 14.92, -3.31, -34));
  39. TxHM->SetPoint(5, Vector3r( 7.51, -10.72, -34));
  40. TxHM->SetPoint(6, Vector3r( -7.51, -10.72, -34));
  41. TxHM->SetPoint(7, Vector3r( -16.10, -2.13, -34));
  42. TxHM->SetNumberOfTurns(8);
  43. // Each Transmitter needs its own `Receiver(s)', the only difference may be the time gates, but that's OK.
  44. // It's a minor amount of overhead for greatly improved genearality. As sometimes different gates are
  45. // masked.
  46. TEMInductiveReceiver* RxHM = TEMInductiveReceiver::New();
  47. RxHM->SetComponent( ZCOMPONENT ); // What about Overloaded to take (X), (X,Y), or (X,Y,Z) or what about tilt?
  48. RxHM->SetMoment( 1 ); // Normalized
  49. RxHM->SetReferenceTime( 4., MILLISEC );
  50. RxHM->SetRxLocation( (Vector3r() << -16.80, 0, -36.00).finished() );
  51. // Gate Centres ms
  52. VectorXr centres (37);
  53. centres << 7.15000000e-04, 2.21500000e-03, 4.21500000e-03, 6.21500000e-03,
  54. 8.21500000e-03, 1.02150000e-02, 1.22150000e-02, 1.47150000e-02,
  55. 1.82150000e-02, 2.27150000e-02, 2.82150000e-02, 3.52150000e-02,
  56. 4.42150000e-02, 5.57150000e-02, 7.02150000e-02, 8.82150000e-02,
  57. 1.10715000e-01, 1.38715000e-01, 1.74215000e-01, 2.19715000e-01,
  58. 2.76715000e-01, 3.48715000e-01, 4.39715000e-01, 5.53715000e-01,
  59. 6.97715000e-01, 8.79215000e-01, 1.10771500e+00, 1.39621500e+00,
  60. 1.76021500e+00, 2.21871500e+00, 2.79671500e+00, 3.52571500e+00,
  61. 4.44471500e+00, 5.60321500e+00, 7.06321500e+00, 8.90421500e+00,
  62. 1.10667200e+01;
  63. //centres.array() += 4.;
  64. // Gate Widths ms
  65. VectorXr widths (37);
  66. widths << 4.30000000e-04, 1.43000000e-03, 3.43000000e-03, 5.43000000e-03,
  67. 7.43000000e-03, 9.43000000e-03, 1.14300000e-02, 1.34300000e-02,
  68. 1.64300000e-02, 2.04300000e-02, 2.54300000e-02, 3.14300000e-02,
  69. 3.94300000e-02, 4.94300000e-02, 6.24300000e-02, 7.84300000e-02,
  70. 9.84300000e-02, 1.23430000e-01, 1.54430000e-01, 1.94430000e-01,
  71. 2.45430000e-01, 3.08430000e-01, 3.89430000e-01, 4.90430000e-01,
  72. 6.17430000e-01, 7.78430000e-01, 9.80430000e-01, 1.23543000e+00,
  73. 1.55743000e+00, 1.96343000e+00, 2.47443000e+00, 3.11943000e+00,
  74. 3.93243000e+00, 4.95743000e+00, 6.24943000e+00, 7.87743000e+00,
  75. 9.93143000e+00;
  76. RxHM->SetWindows(centres, widths, MILLISEC);
  77. TEMTransmitter* TxLM = TEMTransmitter::New();
  78. TxLM->SetRepFrequency( 20, KHZ );
  79. VectorXr TimesLM (18);
  80. VectorXr AmpsLM (18);
  81. TimesLM << -8.00000E-004, -7.86965E-004, -7.66493E-004, -7.23688E-004,
  82. -6.39938E-004, -5.16174E-004, -3.93340E-004, -2.63993E-004,
  83. -1.43952E-004, -7.15990E-006, -2.50712E-006, 0.00000E+000,
  84. 2.19597E-007, 1.47193E-006, 3.34398E-006, 4.68669E-006,
  85. 5.96484E-006, 7.04934E-006;
  86. TimesLM.array() = TimesLM.array() + 8e-4; // Valgrind Hack += yields error. Correct for SkyTEM convention
  87. AmpsLM << 0.00000E+000, 3.67188E-002, 6.17188E-002, 1.17969E-001,
  88. 2.14844E-001, 3.28906E-001, 4.75781E-001, 6.30469E-001,
  89. 7.82031E-001, 9.92969E-001, 1.00000E+000, 1.00000E+000,
  90. 9.63459E-001, 6.01030E-001, 2.29652E-001, 8.64702E-002,
  91. 2.53196E-002, 0.00000E+000;
  92. AmpsLM.array() = AmpsLM.array() * 8.; // Also correct for SkyTEM convention in .geo file
  93. TxLM->SetWaveform( TimesLM, AmpsLM, SEC );
  94. // Define wire loop
  95. TxLM->SetNumberOfPoints(8);
  96. TxLM->SetPoint(0, Vector3r( -16.10, 2.13, -34));
  97. TxLM->SetPoint(1, Vector3r( -7.51, 10.72, -34));
  98. TxLM->SetPoint(2, Vector3r( 7.51, 10.72, -34));
  99. TxLM->SetPoint(3, Vector3r( 14.92, 3.31, -34));
  100. TxLM->SetPoint(4, Vector3r( 14.92, -3.31, -34));
  101. TxLM->SetPoint(5, Vector3r( 7.51, -10.72, -34));
  102. TxLM->SetPoint(6, Vector3r( -7.51, -10.72, -34));
  103. TxLM->SetPoint(7, Vector3r( -16.10, -2.13, -34));
  104. TxLM->SetNumberOfTurns(8);
  105. TEMInductiveReceiver* RxLM = TEMInductiveReceiver::New();
  106. RxLM->SetComponent( ZCOMPONENT ); // What about Overloaded to take (X), (X,Y), or (X,Y,Z) or what about tilt?
  107. RxLM->SetMoment( 1 ); // Normalized
  108. RxLM->SetReferenceTime( 8e-4, SEC );
  109. RxLM->SetRxLocation( (Vector3r() << -16.80, 0, -36.00).finished() );
  110. // Gate Centres ms
  111. VectorXr centresLM (26);
  112. centresLM << 7.150000E-07, 2.215000E-06, 4.215000E-06, 6.215000E-06, 8.215000E-06,
  113. 1.021500E-05, 1.221500E-05, 1.471500E-05, 1.821500E-05, 2.271500E-05,
  114. 2.821500E-05, 3.521500E-05, 4.421500E-05, 5.571500E-05, 7.021500E-05,
  115. 8.821500E-05, 1.107150E-04, 1.387150E-04, 1.742150E-04, 2.197150E-04,
  116. 2.767150E-04, 3.487150E-04, 4.397150E-04, 5.537150E-04, 6.977150E-04,
  117. 8.792150E-04;
  118. VectorXr widthsLM (26);
  119. widthsLM << 5.700000E-07, 1.570000E-06, 1.570000E-06, 1.570000E-06, 1.570000E-06,
  120. 1.570000E-06, 1.570000E-06, 2.570000E-06, 3.570000E-06, 4.570000E-06,
  121. 5.570000E-06, 7.570000E-06, 9.570000E-06, 1.257000E-05, 1.557000E-05,
  122. 1.957000E-05, 2.457000E-05, 3.057000E-05, 3.957000E-05, 5.057000E-05,
  123. 6.257000E-05, 8.057000E-05, 1.005700E-04, 1.265700E-04, 1.605700E-04,
  124. 2.015700E-04;
  125. RxLM->SetWindows(centresLM, widthsLM, SEC);
  126. // Specifies survey, this is the Glue Class, the top of the structure, etc.
  127. TEMSurvey* Survey = TEMSurvey::New();
  128. Survey->SetNumberOfLines(1); // Flight lines or
  129. // Internally each line is a class? But that's sort of hidden to the
  130. // end user. Having each line seperate is nice for constrained inversion, where
  131. // each line is a nice thing to deal with.
  132. Survey->GetLine(0)->SetNumberOfRecords(1); // Each Record then contains everything needed for modelling response curve(s)
  133. Survey->GetLine(0)->GetRecord(0)->SetNumberOfPulseSequences( 1 );
  134. Survey->GetLine(0)->GetRecord(0)->SetTransmitterReceiverPair( 0, TxHM, RxHM );
  135. //Survey->GetLine(0)->GetRecord(0)->SetTransmitterReceiverPair( 1, TxHM, RxHM );
  136. LayeredEarthEM* Earth = LayeredEarthEM::New();
  137. Earth->SetNumberOfLayers(31);
  138. Earth->SetLayerThickness( (VectorXr(29) << 5.00E+00, 5.40E+00,
  139. 5.80E+00, 6.30E+00, 6.80E+00, 7.30E+00, 7.80E+00, 8.50E+00,
  140. 9.10E+00, 9.80E+00, 1.06E+01, 1.14E+01, 1.23E+01, 1.33E+01,
  141. 1.43E+01, 1.54E+01, 1.66E+01, 1.79E+01, 1.93E+01, 2.08E+01,
  142. 2.25E+01, 2.42E+01, 2.61E+01, 2.81E+01, 3.03E+01, 3.27E+01,
  143. 3.52E+01, 3.80E+01, 4.10E+01).finished() );
  144. VectorXcr rho = ( (VectorXcr(31) << 0, 1.54E+01, 4.21E+01,
  145. 9.25E+01, 1.26E+02, 1.17E+02, 7.57E+01, 3.21E+01, 1.40E+01, 1.96E+01,
  146. 2.67E+01, 2.56E+01, 2.00E+01, 1.86E+01, 2.31E+01, 2.97E+01, 3.50E+01,
  147. 3.79E+01, 3.75E+01, 3.32E+01, 2.52E+01, 1.57E+01, 8.38E+00, 5.38E+00,
  148. 5.49E+00, 6.34E+00, 7.07E+00, 7.81E+00, 8.67E+00, 9.59E+00, 1.05E+01
  149. ).finished() ); // 200 Ohm-m half space
  150. Earth->SetLayerConductivity( 1./rho.array() );
  151. // ALL SET UP
  152. std::cout << *Survey << std::endl;
  153. // OK do your thinc
  154. //DataTEM* data =
  155. Survey->ForwardModel( Earth );
  156. // Clean up
  157. // //Survey->Delete();
  158. // Earth->Delete();
  159. //
  160. // TxHM->Delete();
  161. // RxHM->Delete();
  162. // TxLM->Delete();
  163. // RxLM->Delete();
  164. }