Geophysical Inversion and Modelling Library v1.5.4
Loading...
Searching...
No Matches
trans.h
1/******************************************************************************
2 * Copyright (C) 2006-2024 by the GIMLi development team *
3 * Thomas Günther thomas@resistivity.net *
4 * Carsten Rücker carsten@resistivity.net *
5 * *
6 * Licensed under the Apache License, Version 2.0 (the "License"); *
7 * you may not use this file except in compliance with the License. *
8 * You may obtain a copy of the License at *
9 * *
10 * http://www.apache.org/licenses/LICENSE-2.0 *
11 * *
12 * Unless required by applicable law or agreed to in writing, software *
13 * distributed under the License is distributed on an "AS IS" BASIS, *
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. *
15 * See the License for the specific language governing permissions and *
16 * limitations under the License. *
17 * *
18 ******************************************************************************/
19
20#ifndef _GIMLI_TRANS__H
21#define _GIMLI_TRANS__H
22
23#include "gimli.h"
24#include "vector.h"
25#include "numericbase.h"
26
27#define TRANSTOL 1e-8
28
29namespace GIMLI{
30
33template< class Vec > class Trans {
34public:
35//
37 Trans() { }
38
40 virtual ~Trans() { }
41
43 virtual Vec operator()(const Vec & a) const { return trans(a); }
44
46 virtual double operator()(double x) const { return trans(x); }
47
49 inline Vec fwd(const Vec & f) const { return this->trans(f); }
50
52 inline double fwd(double f) const { return this->trans(f); }
53
55 inline Vec inv(const Vec & f) const { return this->invTrans(f); }
56
58 inline double inv(double f) const { return this->inv(Vec(1, f))[0]; }
59
60
62 virtual double trans(double x) const { return this->trans(Vec(1, x))[0]; }
63
65 virtual Vec trans(const Vec & x) const { return x; }
66
68 virtual Vec invTrans(const Vec & f) const { return f; }
69
71 virtual double invTrans(double f) const { return this->invTrans(Vec(1, f))[0]; }
72
74 virtual Vec deriv(const Vec & x) const { return Vec(x.size(), 1.0); }
75
78 Vec update(const Vec & a, const Vec & b) const {
79 return (invTrans(trans(a) + b));
80 }
81
84 Vec error(const Vec & a, const Vec & daBya) const {
85 if (daBya == Vec(a.size(), 0.0)) return Vec(a.size(), 1.0);
86 return abs(Vec(a * daBya * deriv(a)));
87 }
88
91 Vec error_brute(const Vec & a, const Vec & daBya) const {
92 return abs(trans(a * (daBya + 1.0)) - trans(a));
93 }
94};
95
98template< class Vec > class TransNewton : public Trans < Vec >{
99public:
100 TransNewton(const int maxiter=10)
101 : maxiter_(maxiter) { }
102
103 virtual ~TransNewton(){ }
104
105 virtual Vec trans(const Vec & a) const { }
106
107 virtual Vec deriv(const Vec & a) const { }
108
109 virtual Vec invTrans(const Vec & a) const {
110 Vec p(Vec(a.size(), 0.01)); // guess vector
111 Vec dm(trans(p) - a); // function to be nulled
112 //std::cout << "Newton iter norm:";
113 for(size_t i = 0; i < 10; i++) {
114 p = p - dm / deriv(p); // Newton method
115 dm = trans(p) - a;
116 //std::cout << " " << norml2(dm);
117 }
118 //std::cout << std::endl;
119 return p;
120 }
121protected:
122 int maxiter_;
123};
124
125//** Fundamental transformation operations: linear, inverse, log, power, exp:
126
129template< class Vec > class TransLinear : public Trans < Vec > {
130public:
131 TransLinear(const Vec & factor, double offset=0.0)
132 : factor_(factor), offset_(Vec(factor.size(), offset)) {}
133
134 virtual ~TransLinear() { }
135
137 virtual Vec trans(const Vec & x) const {
138// std::cout << a.size() << " " << factor_.size() << " "
139// << offset_.size()<< std::endl;
140 return x * factor_ + offset_;
141 }
142
144 virtual Vec invTrans(const Vec & f) const { return (f - offset_) / factor_;}
145
147 virtual Vec deriv(const Vec & x) const { return factor_; }
148
149protected:
150 Vec factor_;
151 Vec offset_;
152};
153
156template< class Vec > class TransLin : public Trans < Vec > {
157public:
158 TransLin(double factor=1.0, double offset=0.0)
159 : factor_(factor), offset_(offset) {}
160
161 virtual ~TransLin() { }
162
163 virtual Vec trans(const Vec & a) const { return a * factor_ + offset_; }
164
165 virtual Vec invTrans(const Vec & a) const { return (a - offset_) / factor_;}
166
167 virtual Vec deriv(const Vec & a) const { return Vec(a.size(), factor_); }
168
169protected:
170 double factor_;
171 double offset_;
172};
173
175template< class Vec > class TransPower : public Trans < Vec > {
176public:
177 TransPower(double npower=-1.0, double a0=1.0)
178 : npower_(npower), a0_(a0) {}
179 virtual ~TransPower() { }
180
182 virtual Vec trans(const Vec & x) const {
183 return pow(x / a0_, npower_);}
184
186 virtual Vec invTrans(const Vec & f) const {
187 return pow(f, 1.0 / npower_) * a0_;}
188
190 virtual Vec deriv(const Vec & a) const {
191 return pow(a / a0_, npower_ - 1.0) * npower_ / a0_;}
192protected:
193 double npower_;
194 double a0_;
195};
196
198template< class Vec > class TransExp : public Trans < Vec > {
199public:
200
201 TransExp(double a0=1.0, double f0=1.0)
202 : a0_(a0), f0_(f0) {}
203
204
205 virtual ~TransExp() {}
206
207
208 virtual Vec trans(const Vec & a) const {
209 return exp(a / a0_ * (-1.0)) * f0_; }
210
211
212 virtual Vec invTrans(const Vec & f) const {
213 return log(f / f0_) * a0_ * (-1.0); }
214
216 virtual Vec deriv(const Vec & a) const {
217 return trans(a) / a0_ * (-1.0); }
218protected:
219 double a0_;
220 double f0_;
221};
222
224template< class Vec > class TransInv : public Trans < Vec > {
225public:
226 TransInv() { }
227 virtual ~TransInv() { }
228
229 virtual Vec trans(const Vec & a) const { return 1.0 / a; }
230 virtual Vec invTrans(const Vec & f) const { return 1.0 / f; }
231 virtual Vec deriv(const Vec & a) const { return -1.0 / a / a; }
232
233};
234
236template< class Vec > class TransLog : public Trans < Vec > {
237public:
238 TransLog(double lowerbound=0.0) : lowerbound_(lowerbound) { }
239 virtual ~TransLog() { }
240
241 virtual Vec trans(const Vec & a) const {
242 double lb1 = lowerbound_ * (1.0 + TRANSTOL);
243 if (min(a) < lb1) {
244 std::cerr << WHERE_AM_I << " Warning! " << min(a)
245 << " <=" << lowerbound_ << " lowerbound" << std::endl;
246 Vec tmp(a);
247 for (uint i = 0; i < a.size(); i ++){
248 tmp[i] = max(a[i], lb1 );
249 }
250 return log(tmp - lowerbound_);
251 }
252 return log(a - lowerbound_);
253 }
254
255 virtual Vec invTrans(const Vec & f) const { return exp(f) + lowerbound_; }
256
257 virtual Vec deriv(const Vec & a) const {
258 double lb1 = lowerbound_ * (1.0 + TRANSTOL);
259 if (min(a) < lb1) {
260 std::cerr << WHERE_AM_I << " Warning! " << min(a)
261 << " <=" << lowerbound_ << " lowerbound" << std::endl;
262 Vec tmp(a);
263 for (uint i = 0; i < a.size(); i ++){
264 tmp[i] = max(a[i], lb1 );
265 }
266 return 1.0 / (tmp - lowerbound_);
267 }
268 return 1.0 / (a - lowerbound_);
269 }
270
271 //** suggested by Friedel(2003), but deactivated since inherited by transLogLU
272// virtual Vec error(const Vec & a, const Vec & daBya) const { return log(1.0 + daBya); }
273
274 inline void setLowerBound(double lb) { lowerbound_ = lb; }
275
276 inline double lowerBound() const { return lowerbound_; }
277
278protected:
279 double lowerbound_;
280};
281
282
285template< class Vec > class TransLogLU : public TransLog < Vec > {
286public:
287 TransLogLU(double lowerbound=0.0, double upperbound=0.0)
288 : TransLog< Vec >(lowerbound), upperbound_(upperbound) { }
289 virtual ~TransLogLU() { }
290
292 Vec rangify(const Vec & a) const;
293
294 virtual Vec trans(const Vec & a) const;
295
296 virtual Vec invTrans(const Vec & a) const;
297
298 virtual Vec deriv(const Vec & a) const;
299
300 inline void setUpperBound(double ub) { upperbound_ = ub; }
301
302 inline double upperBound() const { return upperbound_; }
303
304protected:
305 double upperbound_;
306};
307
309template <> DLLEXPORT RVector TransLogLU<RVector>::rangify(const RVector & a) const;
310template <> DLLEXPORT RVector TransLogLU<RVector>::trans(const RVector & a) const;
311template <> DLLEXPORT RVector TransLogLU<RVector>::invTrans(const RVector & a) const;
312template <> DLLEXPORT RVector TransLogLU<RVector>::deriv(const RVector & a) const;
313
314
316template< class Vec > class TransCotLU : public Trans < Vec > {
317public:
318
319 TransCotLU(double lowerbound=0.0, double upperbound=0.0)
320 : lowerbound_(lowerbound), upperbound_(upperbound) { }
321
322 virtual ~TransCotLU() { }
323
324 virtual Vec trans(const Vec & a) const {
325 Vec tmp(a);
326 double fak = 1.00001;
327 if (min(a) <= lowerbound_ ){
328 std::cerr << WHERE_AM_I << " Warning! " << min(a) << " < " << lowerbound_ << " = lowerbound" << std::endl;
329 for (uint i = 0; i < a.size(); i ++){
330 tmp[i] = max(a[i], lowerbound_ * fak);
331 }
332 }
333 if (max(a) >= upperbound_ ){
334 std::cerr << WHERE_AM_I << " Warning! " << max(a) << " > " << upperbound_ << " = upperbound" << std::endl;
335 for (uint i = 0; i < a.size(); i ++){
336 tmp[i] = min(a[i], upperbound_ / fak);
337 }
338 }
339 return cot((tmp - lowerbound_) / (upperbound_ - lowerbound_) * PI) * (-1.0);
340 }
341
342 virtual Vec invTrans(const Vec & a) const {
343// return acot(a * (-1.0)) * (upperbound_ - lowerbound_) / PI + lowerbound_;
344 return atan(a) * (upperbound_ - lowerbound_) / PI + (lowerbound_ + upperbound_) / 2;
345 }
346
347 virtual Vec deriv(const Vec & a) const {
348 return ((trans(a) * trans(a) + 1.0) * PI / (upperbound_ - lowerbound_));
349 }
350
351protected:
352 double lowerbound_;
353 double upperbound_;
354};
355
358template< class Vec > class TransNest : public Trans < Vec >{
359public:
360 TransNest(Trans< Vec > & T1, Trans< Vec > & T2) : T1_(&T1), T2_(&T2){
361 }
362 virtual ~TransNest(){ }
363
364 virtual Vec trans(const Vec & a) const {
365 return T1_->trans(T2_->trans(a));
366 }
367
368 virtual Vec invTrans(const Vec & a) const {
369 return T2_->invTrans(T1_->invTrans(a));
370 }
371
372 virtual Vec deriv(const Vec & a) const {
373 return T1_->deriv(T2_->trans(a)) * T2_->deriv(a);
374 }
375
376protected:
377 Trans< Vec > * T1_;
378 Trans< Vec > * T2_;
379};
380
382template< class Vec > class TransAdd : public TransNewton < Vec >{
383public:
384 TransAdd(Trans< Vec > & T1, Trans< Vec > & T2) : T1_(&T1), T2_(&T2){ }
385 virtual ~TransAdd(){ }
386
387 virtual Vec trans(const Vec & a) const {
388 return T1_->trans(a) + T2_->trans(a);
389 }
390
391 virtual Vec deriv(const Vec & a) const {
392 return T1_->deriv(a) + T2_->deriv(a);
393 }
394
395protected:
396 Trans< Vec > * T1_;
397 Trans< Vec > * T2_;
398};
399
401template< class Vec > class TransMult : public TransNewton < Vec >{
402public:
403 TransMult(Trans< Vec > & T1, Trans< Vec > & T2) : T1_(&T1), T2_(&T2){ }
404 virtual ~TransMult(){ }
405
406 virtual Vec trans(const Vec & a) const {
407 return T1_->trans(a) * T2_->trans(a);
408 }
409
410 virtual Vec deriv(const Vec & a) const {
411 return T1_->deriv(a) * T2_->trans(a) + T2_->deriv(a) * T1_->trans(a);
412 }
413
414protected:
415 Trans< Vec > * T1_;
416 Trans< Vec > * T2_;
417};
418
421template< class Vec > class TransCRIM : public TransLinear < Vec > {
422public:
424 TransCRIM(const Vec & phi, double ematrix = 5.0, double ewater = 81.0)
425 : TransLinear< Vec >(1.0 / phi / 2.99e8 / (std::sqrt(ewater) - 1.0),
426 (phi + (phi - 1.0) * std::sqrt(ematrix)) / (phi * (std::sqrt(ewater) - 1.0))){
427 }
428 virtual ~TransCRIM() { }
429};
430
432template< class Vec > class TransArchie : public TransPower < Vec > {
433public:
435 TransArchie(double resfluid, double mexp = 2.0)
436 :TransPower< Vec >(resfluid, 1 / mexp){
437 }
438
439 virtual ~TransArchie() { }
440};
441
444template< class Vec > class TransQuadrat : public TransNewton < Vec >{
445public:
446 TransQuadrat(const int maxiter = 10) : TransNewton< Vec >(maxiter){ }
447 virtual ~TransQuadrat(){ }
448 virtual Vec trans(const Vec & a) const { return a * a; }
449 virtual Vec deriv(const Vec & a) const { return a * 2.0; }
450};
451
453template< class Vec > class TransLogMult : public TransLog < Vec > {
454public:
455 TransLogMult(const Vec & factor, double lowerbound = 0.0)
456 : TransLog< Vec >(lowerbound), factor_(factor) { }
457 virtual ~TransLogMult() { }
458
459 virtual Vec trans(const Vec & a) const { return TransLog< Vec >::trans(a * factor_); }
460 virtual Vec invTrans(const Vec & a) const { return TransLog< Vec >::invTrans(a) / factor_; }
461 virtual Vec deriv(const Vec & a) const { return TransLog< Vec >::deriv(a * factor_) * factor_; }
462
463protected:
464 Vec factor_;
465};
466
468template< class Vec > class TransTanLU : public Trans < Vec > {
469public:
470 TransTanLU(double lowerbound=0.0, double upperbound=0.0)
471 : lowerbound_(lowerbound), upperbound_(upperbound) {
472 }
473 virtual ~TransTanLU() { }
474
475 virtual Vec trans(const Vec & a) const {
476 Vec tmp(a);
477 double tol = 1e-5;
478 if (a.min() < lowerbound_ ){
479 std::cerr << WHERE_AM_I << " Warning! " << a.min() << " < " << lowerbound_ << " lowerbound" << std::endl;
480 for (int i = 0; i < a.size(); i ++){
481 tmp[i] = max(a[i], lowerbound_) + tol;
482 }
483 }
484 if (a.max() > upperbound_ ){
485 std::cerr << WHERE_AM_I << " Warning! " << a.max() << " > " << upperbound_ << " lowerbound" << std::endl;
486 Vec tmp(a);
487 for (int i = 0; i < a.size(); i ++){
488 tmp[i] = min(a[i], upperbound_) - tol;
489 }
490 }
491 return tan(((a - lowerbound_) / (upperbound_ - lowerbound_) - 0.5) * PI);
492 }
493
494 virtual Vec invTrans(const Vec & a) const {
495 return atan(a) / PI * (upperbound_ - lowerbound_) + (lowerbound_ + upperbound_) / 2;
496 }
497
498 virtual Vec deriv(const Vec & a) const {
499 return (pow(trans(a), 2.0) + 1.0);
500 }
501
502protected:
503 double lowerbound_;
504 double upperbound_;
505};
506
508template< class Vec > class TransLogLUMult : public TransLogLU < Vec > {
509public:
510 TransLogLUMult(const Vec & factor,
511 double lowerbound=0.0,
512 double upperbound=0.0)
513 : TransLogLU< Vec >(lowerbound, upperbound), factor_(factor){ }
514
515 virtual ~TransLogLUMult() { }
516
517 virtual Vec trans(const Vec & a) const {
518 return TransLogLU< Vec >::trans(a * factor_);
519 }
520
521 virtual Vec invTrans(const Vec & a) const {
522 return TransLogLU< Vec >::invTrans(a) / factor_ ;
523 }
524
525 virtual Vec deriv(const Vec & a) const {
526 return TransLogLU< Vec >::deriv(a * factor_) * factor_;
527 }
528
529protected:
530 Vec factor_;
531};
532
535template< class Vec > class TransCumulative : public Trans < Vec >{
536public:
537 TransCumulative() { }
538
539 virtual ~TransCumulative() { }
540
541 virtual Vec trans(const Vec & a) const;
542
543 virtual Vec invTrans(const Vec & a) const;
544
545 virtual Vec deriv(const Vec & a) const;
546
547 Index size() const { return transVec_.size(); }
548
549 void clear() {
550 transVec_.clear();
551 slice_.clear();
552 indices_.clear();
553 }
554
555 void add(Trans< Vec > & trans, Index size);
556
557 void add(Trans< Vec > & trans, Index start, Index end);
558
559 void add(Trans< Vec > & trans, const IVector & indices);
560
562 Trans < Vec > & at(Index i) { return *transVec_.at(i);}
563
564 const std::pair< Index, Index> & slice(Index i) const { return slice_.at(i);}
565
566 const IVector & indices(Index i) const { return indices_.at(i);}
567
568protected:
569 std::vector < Trans< Vec > * > transVec_;
570 std::vector < std::pair< Index, Index> > slice_;
571 std::vector < IVector > indices_;
572};
573
574template <> DLLEXPORT RVector TransCumulative < RVector >::trans(const RVector & a) const;
575template <> DLLEXPORT RVector TransCumulative < RVector >::invTrans(const RVector & a) const;
576template <> DLLEXPORT RVector TransCumulative < RVector >::deriv(const RVector & a) const;
577
578template <> DLLEXPORT void TransCumulative < RVector >::add(Trans< RVector > & trans, Index size);
579template <> DLLEXPORT void TransCumulative < RVector >::add(Trans< RVector > & trans, Index start, Index end);
580template <> DLLEXPORT void TransCumulative < RVector >::add(Trans< RVector > & trans, const IVector & indices);
581
582typedef Trans < RVector > RTrans;
583typedef TransLinear < RVector > RTransLinear;
584typedef TransLin < RVector > RTransLin;
585typedef TransPower < RVector > RTransPower;
586typedef TransLog < RVector > RTransLog;
587typedef TransLogLU < RVector > RTransLogLU;
588typedef TransCotLU < RVector > RTransCotLU;
589typedef TransCumulative< RVector > RTransCumulative;
590
591
592} // namespace GIMLI
593
594
595#endif // _GIMLI_TRANS__H
596
virtual Vec trans(const Vec &a) const
Definition trans.h:387
virtual Vec deriv(const Vec &a) const
Definition trans.h:391
Definition trans.h:432
TransArchie(double resfluid, double mexp=2.0)
Definition trans.h:435
Definition trans.h:421
TransCRIM(const Vec &phi, double ematrix=5.0, double ewater=81.0)
Definition trans.h:424
virtual Vec trans(const Vec &a) const
Definition trans.h:324
virtual Vec deriv(const Vec &a) const
Definition trans.h:347
virtual Vec invTrans(const Vec &a) const
Definition trans.h:342
Trans< Vec > & at(Index i)
Definition trans.h:562
virtual Vec trans(const Vec &a) const
virtual Vec invTrans(const Vec &a) const
virtual Vec deriv(const Vec &a) const
virtual Vec trans(const Vec &a) const
Definition trans.h:208
virtual Vec invTrans(const Vec &f) const
Definition trans.h:212
virtual Vec deriv(const Vec &a) const
Definition trans.h:216
virtual Vec invTrans(const Vec &f) const
Definition trans.h:230
virtual Vec deriv(const Vec &a) const
Definition trans.h:231
virtual Vec trans(const Vec &a) const
Definition trans.h:229
virtual Vec trans(const Vec &a) const
Definition trans.h:163
virtual Vec invTrans(const Vec &a) const
Definition trans.h:165
virtual Vec deriv(const Vec &a) const
Definition trans.h:167
virtual Vec deriv(const Vec &x) const
Definition trans.h:147
virtual Vec invTrans(const Vec &f) const
Definition trans.h:144
virtual Vec trans(const Vec &x) const
Definition trans.h:137
virtual Vec deriv(const Vec &a) const
Definition trans.h:525
virtual Vec invTrans(const Vec &a) const
Definition trans.h:521
virtual Vec trans(const Vec &a) const
Definition trans.h:517
virtual Vec trans(const Vec &a) const
Vec rangify(const Vec &a) const
virtual Vec deriv(const Vec &a) const
virtual Vec invTrans(const Vec &a) const
virtual Vec deriv(const Vec &a) const
Definition trans.h:461
virtual Vec invTrans(const Vec &a) const
Definition trans.h:460
virtual Vec trans(const Vec &a) const
Definition trans.h:459
virtual Vec deriv(const Vec &a) const
Definition trans.h:257
virtual Vec invTrans(const Vec &f) const
Definition trans.h:255
virtual Vec trans(const Vec &a) const
Definition trans.h:241
virtual Vec deriv(const Vec &a) const
Definition trans.h:410
virtual Vec trans(const Vec &a) const
Definition trans.h:406
virtual Vec deriv(const Vec &a) const
Definition trans.h:372
virtual Vec trans(const Vec &a) const
Definition trans.h:364
virtual Vec invTrans(const Vec &a) const
Definition trans.h:368
virtual Vec trans(const Vec &a) const
Definition trans.h:105
virtual Vec deriv(const Vec &a) const
Definition trans.h:107
virtual Vec invTrans(const Vec &a) const
Definition trans.h:109
virtual Vec deriv(const Vec &a) const
Definition trans.h:190
virtual Vec invTrans(const Vec &f) const
Definition trans.h:186
virtual Vec trans(const Vec &x) const
Definition trans.h:182
virtual Vec trans(const Vec &a) const
Definition trans.h:448
virtual Vec deriv(const Vec &a) const
Definition trans.h:449
virtual Vec invTrans(const Vec &a) const
Definition trans.h:494
virtual Vec deriv(const Vec &a) const
Definition trans.h:498
virtual Vec trans(const Vec &a) const
Definition trans.h:475
Definition trans.h:33
virtual ~Trans()
Definition trans.h:40
virtual Vec operator()(const Vec &a) const
Definition trans.h:43
Vec inv(const Vec &f) const
Definition trans.h:55
virtual Vec invTrans(const Vec &f) const
Definition trans.h:68
virtual Vec trans(const Vec &x) const
Definition trans.h:65
virtual double trans(double x) const
Definition trans.h:62
double inv(double f) const
Definition trans.h:58
Vec error_brute(const Vec &a, const Vec &daBya) const
Definition trans.h:91
Trans()
Definition trans.h:37
virtual Vec deriv(const Vec &x) const
Definition trans.h:74
double fwd(double f) const
Definition trans.h:52
Vec fwd(const Vec &f) const
Definition trans.h:49
virtual double invTrans(double f) const
Definition trans.h:71
Vec error(const Vec &a, const Vec &daBya) const
Definition trans.h:84
virtual double operator()(double x) const
Definition trans.h:46
Vec update(const Vec &a, const Vec &b) const
Definition trans.h:78
GIMLi main namespace for the Geophyiscal Inversion and Modelling Library.
Definition baseentity.h:24
RVector x(const R3Vector &rv)
Definition pos.cpp:107