Geophysical Inversion and Modelling Library v1.5.4
Loading...
Searching...
No Matches
vectortemplates.h
1/******************************************************************************
2 * Copyright (C) 2006-2024 by the GIMLi development team *
3 * Carsten Rücker carsten@resistivity.net *
4 * *
5 * Licensed under the Apache License, Version 2.0 (the "License"); *
6 * you may not use this file except in compliance with the License. *
7 * You may obtain a copy of the License at *
8 * *
9 * http://www.apache.org/licenses/LICENSE-2.0 *
10 * *
11 * Unless required by applicable law or agreed to in writing, software *
12 * distributed under the License is distributed on an "AS IS" BASIS, *
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. *
14 * See the License for the specific language governing permissions and *
15 * limitations under the License. *
16 * *
17 ******************************************************************************/
18
19#ifndef _GIMLI_VECTORTEMPLATES__H
20#define _GIMLI_VECTORTEMPLATES__H
21
22#include "gimli.h"
23#include <cmath>
24#include <cstdlib>
25#include <cerrno>
26#include <cstring>
27#include <string>
28#include <vector>
29#include <fstream>
30#include <algorithm>
31#include <numeric>
32
33namespace GIMLI{
34
35template < typename T, class Iter, template < typename, class > class Vec >
36// template < typename T, template < typename, class > class Vec >
37IndexArray ids(const Vec < T, Iter > & e){
38 IndexArray id(e.size());
39 for (Index i = 0; i < e.size(); i ++ ) id[i] = e[i]->id();
40 return id;
41}
42
43template < class ValueType > bool save(std::vector < ValueType > & a, const std::string & filename, IOFormat format = Ascii){
44 return saveVec(a, filename, format);
45}
46
47template < class ValueType > bool load(std::vector < ValueType > & a, const std::string & filename, IOFormat format = Ascii,
48 bool verbose = true){
49 return loadVec(a, filename, format, verbose);
50}
51
52template < class Vec > bool saveVec(const Vec & a, const std::string & filename,
53 IOFormat format, bool verbose = true){
54
55 if (filename.rfind(VECTORASCSUFFIX) != std::string::npos) format = Ascii;
56 else if (filename.rfind(VECTORBINSUFFIX) != std::string::npos) format = Binary;
57 std::string fname(filename);
58
59 if (format == Ascii){
60 if (fname.rfind(".") == std::string::npos) fname += VECTORASCSUFFIX;
61
62 std::ofstream file; file.open(fname.c_str());
63 if (!file) {
64 std::cerr << filename << ": " << strerror(errno) << " " << errno << std::endl;
65 return false;
66 }
67
68 file.setf(std::ios::scientific, std::ios::floatfield);
69 file.precision(14);
70
71 for (uint i = 0, imax = a.size(); i < imax; i ++) file << a[i] << std::endl;
72 file.close();
73 } else {
74 if (fname.rfind(".") == std::string::npos) fname += VECTORBINSUFFIX;
75 // so haett ich das gern //
76// std::ofstream file(filename.c_str(), std::ofstream::binary);
77// std::copy(&a[0], &a[a.size()-1], ostream_iterator< double >(&file));
78// file.close();
79 FILE *file; file = fopen(fname.c_str(), "w+b");
80 if (!file) {
81 if (verbose) std::cerr << filename << ": " << strerror(errno) << " " << errno << std::endl;
82 return false;
83 }
84
85 int count = a.size();
86 uint ret = 0; ret = fwrite((char*)&count, sizeof(int), 1, file);
87 if (ret){
88 for (uint i = 0; i < a.size(); i++) ret = fwrite((char*)&a[i], sizeof(double), 1, file);
89 }
90 fclose(file);
91 }
92 return true;
93}
94
95template < class Vec > bool loadVec(Vec & a, const std::string & filename,
96 IOFormat format, bool verbose = true){
97
98 if (filename.rfind(VECTORASCSUFFIX) != std::string::npos) format = Ascii;
99 else if (filename.rfind(VECTORBINSUFFIX) != std::string::npos) format = Binary;
100
101 if (!fileExist(filename)){
102 if (fileExist(filename + VECTORBINSUFFIX))
103 return loadVec(a, filename + VECTORBINSUFFIX, Binary);
104 if (fileExist(filename + VECTORASCSUFFIX))
105 return loadVec(a, filename + VECTORASCSUFFIX, Ascii);
106 }
107
108 if (format == Ascii){
109
110 a.clear();
111 std::fstream file; openInFile(filename.c_str(), &file);
112 double val; while(file >> val) a.push_back(val);
113
114 //so haett ich das gern
115// std::ifstream file(filename.c_str());
116// std::copy( std::istream_iterator<double>(file),
117// std::istream_iterator<double>(),
118// std::back_inserter(tmp));
119
120//std::back_inserter< double > (tmp));
121 //std::copy(file.begin(), file.end(), back_inserter< double >(& tmp[0]));
122
123// a.resize(tmp.size());
124// std::copy(tmp.begin(), tmp.end(), &a[0]);
125 file.close();
126
127 } else {
128 FILE *file;
129 file = fopen(filename.c_str(), "r+b");
130 if (!file) {
131 if (verbose) std::cerr << filename << ": " << strerror(errno) << " " << errno << std::endl;
132 return false;
133 }
134 uint ret = 0;
135 int size; ret = fread(&size, sizeof(int), 1, file);
136 if (ret){
137 a.resize(size);
138 ret = fread(&a[0], sizeof(double), size, file);
139 }else {
140
141 }
142 fclose(file);
143 }
144 return true;
145}
146
147
148//** START std::vector shortcuts
149template < class T > std::vector< T > sort(const std::vector < T > & a){
150 std::vector < T > t(a);
151 sort(t.begin(), t.end());
152 return t;
153}
154
155template < class T > std::vector< T > unique(const std::vector < T > & a){
156 std::vector < T > t;
157 std::unique_copy(a.begin(), a.end(), back_inserter(t));
158 return t;
159}
160
161//** END std::vector shortcuts
162
163// template < class Vec > Vec abs(const Vec & v) {
164// Vec tmp(v.size());
165// for (uint i = 0; i < v.size(); i ++) tmp[i] = abs(v[i]);
166// return tmp;
167// }
168
169template < class Vec > void clear(Vec & a) {
170 for (int i = 0; i < (int)a.size(); i ++) a[i] = 0.0;
171}
172
173template < typename T, class Iter, template < typename, class > class Vec >
174T min(const Vec< T, Iter > & v){
175 return *std::min_element(&v[0], &v[0] + v.size());
176}
177
178template < typename T, class Iter, template < typename, class > class Vec >
179T max(const Vec< T, Iter > & v){
180 return *std::max_element(v.begin(), v.end());
181}
182//
183// template < class T, class Iter, template < class T, class Iter > class Vec > T sum(const Vec< T, Iter > & v){
184// return std::accumulate(v.begin(), v.end(), 0.0);
185// // T sum = 0.0;
186// // for (size_t i = v.size(); i--;) sum += v[i];
187// // return sum;
188// }
189//
190// template < class ValueType, template < class T > class Vec > T dot(const Vec< T > & a, const Vec < T > & b) {
191// return sum(a * b);
192// }
193
194template < class Vec > void echoMinMax(const Vec & vec, const std::string & name){
195 if (vec.size() > 0){
196 std::cout << "min " << name << " = " << min(vec)
197 << " max " << name << " = " << max(vec) << " (" << vec.size() << ")" << std::endl;
198 } else {
199 std::cout << "min " << name << " = ndef."
200 << " max " << name << " = ndef." << std::endl;
201 }
202}
203
204template < class Vec > double median(const Vec & a) {
205 Index dim = a.size();
206 if (dim == 1) return a[0];
207 if (dim > 1){
208 Vec tmp(sort(a));
209 if (std::fabs(dim / 2.0 - rint(dim / 2.0)) < 1e-12){ // even
210 return (tmp[dim / 2] + tmp[dim / 2 - 1]) / 2.0;
211 } else { // odd
212 return tmp[(dim - 1)/ 2];
213 }
214 }
215 return 0.0;
216}
217
218// template < class Vec > double mean(const Vec & a) { return sum(a) / a.size(); }
219
220// template < class Vec > double stdDev(const Vec & a) {
221// return std::sqrt(sum(square(a - mean(a))) / (a.size() - 1));
222// }
223
224template < class Vec > double arithmeticMean(const Vec & a) { return mean(a); }
225
226template < class Vec > double geometricMean(const Vec & a) {
227 int dim = a.size();
228 double result = 0.0;
229 for (int i = 0; i < dim; i ++) result += std::log(a[i]);
230 result /= (double)dim;
231 return std::exp(result);
232}
233
234template < class Vec > double harmonicMean(const Vec & a) {
235 int dim = a.size();
236 double result = 1.0 / a[0];
237
238 for (int i = 1; i < dim; i ++) result += 1.0 / a[i];
239 result /= dim;
240 return 1.0 / result;
241}
242
243template < class Vec > double rms(const Vec & a) { return std::sqrt(mean(square(a))); }
244
245template < class Vec > double rms(const Vec & a, const Vec & b) { return rms(a - b); }
246
247template < class Vec > double rrms(const Vec & a, const Vec & b) { return rms((a - b) / a); }
248
249template < class Vec > double normlp(const Vec & a, int p) {
250 return std::pow(sum(pow(abs(a), p)), 1.0/(double)p);
251}
252
253template < class Vec > double norml1(const Vec & a) {
254 //http://mathworld.wolfram.com/L1-Norm.html
255 return normlp(a, 1);
256}
257
258template < class Vec > double norml2(const Vec & a) {
259 // vector norm \ell^2 nicht L^2
260 return normlp(a, 2);
261}
262template < class Vec > double normlInfinity(const Vec & a) {
263 return max(abs(a));
264}
265template < class Vec > double euclideanNorm(const Vec & a) {
266 return norml2(a);
267}
268
269template < class Vec > double norm(const Vec & a) {
270 //** sqrt(a_0^2 + a_i^2 + a_n^2) ; 0 < i < a.size()
271 return norml2(a);
272}
273
274template < class Vec > double chiQuad(const Vec & a, const Vec & b, const Vec & err) {
275 Vec tmp((a - b) / err);
276 return dot(tmp, tmp) / a.size();
277}
278
279template < class Vec > double chiQuad(const Vec & a, const Vec & b, const Vec & err, bool isLog) {
280 double chiq = 0.0;
281
282 Vec tmp(a.size());
283
284 if (isLog){
285 tmp = ((log(b) - log(a)) / log(err + 1.0));
286 chiq = mean(tmp * tmp);
287 } else {
288 chiq = mean(((b / a - 1.0) * (b / a - 1.0)) / (err * err));
289 }
290 return chiq;
291}
292
293template < class ValueType >
294void rand(Vector < ValueType > & vec, ValueType min = 0.0, ValueType max = 1.0){
295 for (int i = 0, imax = vec.size(); i < imax; i ++){
296 vec[i] = (ValueType)std::rand() * ((max -min)/ RAND_MAX) + min;
297 }
298}
299
300template < class ValueType >
301void randn(Vector< ValueType > & vec){
302 // vec = sqrt(log(1.0 - vec) * -2.0) * cos(vec * 2.0 * PI_);
303 //** keine Ahnung was passiert aber es funktioniert. vgl. tests/vector/baseio.cpp
304 for (uint i = 0, imax = vec.size(); i < imax; i ++){
305 double sum = 0.0;
306 for (int j = 0; j < 16; j++) sum += std::rand() & 0xfff;
307 vec[i] = (sum - 0x8000) * (1.0 / 4729.7);
308 }
309}
310
312inline RVector randn(Index n){
313 RVector r(n);
314 randn(r);
315 return r;
316}
317
318
319// //*!Position of the minimum Value position as IndexArray */
320// template < class ValueType >
321// IndexArray minIdx(Vector< ValueType > & vec){
322// minId
323
324} // namespace GIMLI{
325
326#endif // _GIMLI_VECTORTEMPLATES__H
One dimensional array aka Vector of limited size.
Definition vector.h:186
GIMLi main namespace for the Geophyiscal Inversion and Modelling Library.
Definition baseentity.h:24
bool loadVec(Vector< ValueType > &a, const std::string &filename, IOFormat format=Ascii)
Definition vector.h:1925
Vector< T > unique(const Vector< T > &a)
Definition vector.h:1604
bool saveVec(const Vector< ValueType > &a, const std::string &filename, IOFormat format=Ascii)
Definition vector.h:1916
IOFormat
Definition gimli.h:289
bool load(Matrix< ValueType > &A, const std::string &filename)
Definition matrix.h:828