croposp.cc 5.06 KB
Newer Older
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
/*! \file croposp.cc
 * \brief Cross power spectral density
 * 
 * ----------------------------------------------------------------------------
 * 
 * \author Thomas Forbriger
 * \date 25/12/2018
 * 
 * Cross power spectral density
 * 
 * Copyright (c) 2018 by Thomas Forbriger (BFO Schiltach) 
 * 
 * REVISIONS and CHANGES 
 *  - 25/12/2018   V1.0   Thomas Forbriger
 * 
 * ============================================================================
 */
#define CROPOSP_VERSION \
  "CROPOSP   V1.0   Cross power spectral density"

#include <iostream>
#include <tfxx/commandline.h>
23
#include <tfxx/error.h>
24
#include <tsioxx/cmdlinefiles.h>
25
#include <tsxx/tscollection.h>
26
27
28
29
30

using std::cout;
using std::cerr;
using std::endl;

31
struct Options {
32
  bool verbose, trim;
33
  std::string inputformat;
34
  double datetolerance;
35
36
}; // struct Options

37
38
39
40
41
42
43
44
45
46
47
48
49
50
int main(int iargc, char* argv[])
{

  // define usage information
  char usage_text[]=
  {
    CROPOSP_VERSION "\n"
    "usage: croposp" "\n"
    "   or: croposp --help|-h" "\n"
  };

  // define full help text
  char help_text[]=
  {
51
52
53
54
55
56
    "-verbose           be verbose\n"
    "-itype f           set default input file format (this value can\n"
    "                   be overwritten by the format key at a file name)\n"
    "-trim              trim time series to identical begin and length\n"
    "-datetolerance t   set tolerance as a fraction of sampling interval\n"
    "                   when comparing time series header date values\n"
57
    "\n"
58
    "keys to be appended to file names if required:\n"
59
60
    "t:sel        trace selection\n"
    "f:format     file format\n"
61
62
63
64
65
66
67
68
69
  };

  // define commandline options
  using namespace tfxx::cmdline;
  static Declare options[]= 
  {
    // 0: print help
    {"help",arg_no,"-"},
    // 1: verbose mode
70
71
72
    {"verbose",arg_no,"-"},
    // 2: default input file format
    {"itype",arg_yes,"sff"},
73
74
75
76
    // 3: trim time series
    {"trim",arg_no,"-"},
    // 4: default input file format
    {"datetolerance",arg_yes,"0."},
77
78
79
80
81
    {NULL}
  };

  // define command line keys for input files
  static const char tracekey[]="t";
82
  static const char formatkey[]="f";
83
84

  // define commandline argument modifier keys
85
  static const char* cmdlinekeys[]={tracekey, formatkey, 0};
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103

  // no arguments? print usage...
  if (iargc<2) 
  {
    cerr << usage_text << endl;
    exit(0);
  }

  // collect options from commandline
  Commandline cmdline(iargc, argv, options);

  // help requested? print full help text...
  if (cmdline.optset(0))
  {
    cerr << usage_text << endl;
    cerr << help_text << endl;
    exit(0);
  }
104
105
106
107

  Options opt;
  opt.verbose=cmdline.optset(1);
  opt.inputformat=cmdline.string_arg(2);
108
109
  opt.trim=cmdline.optset(3);
  opt.datetolerance=cmdline.double_arg(4);
110
111
112

  TFXX_assert(((opt.datetolerance >= 0.) && (opt.datetolerance <=1.)),
              "datetolerance is out of accepted range");
113
114
115
116
117
  
  // extract commandline arguments
  TFXX_assert(cmdline.extra(), "missing input file");
  tfxx::cmdline::Tparsed arguments=parse_cmdline(cmdline, cmdlinekeys);

118
119
120
121
122
  // read data files
  if (opt.verbose) 
  {
    cout << "Read time series data" << endl;
  }
123
124
125
126
127
128
129
130
131
132
133
134
135
136
  ts::sff::TDFileList input_file_list;
  tfxx::cmdline::Tparsed::const_iterator file=arguments.begin();
  while (file != arguments.end())
  {
    std::string format=opt.inputformat;
    if (file->haskey(formatkey))
    {
      format=file->value(formatkey);
    }
    input_file_list.push_back(ts::sff::readDSFF(*file, opt.verbose, 
                                                tracekey, format));
    ++file;
  }

137
138
  // collect traces
  typedef ts::TimeSeriesCollection<double> TCollection;
139
  TCollection collection_of_series;
140
141
142
143
144
145
146
147
  typedef ts::sff::DFile::Tfile Tfile;
  typedef Tfile::Ttracevector Ttracevector;
  ts::sff::TDFileList::const_iterator i_file=input_file_list.begin();
  while (i_file != input_file_list.end())
  {
    Ttracevector::const_iterator i_trace=i_file->data.begin();
    while (i_trace != i_file->data.end())
    {
148
      collection_of_series.push_back(*i_trace);
149
150
151
152
153
154
155
156
157
      ++i_trace;
    }
    ++i_file;
  }

  // report traces
  if (opt.verbose)
  {
    cout << "Time series to be analyzed:" << endl;
158
159
    TCollection::const_iterator i_series=collection_of_series.begin();
    while (i_series != collection_of_series.end())
160
161
162
163
164
165
166
167
168
169
170
171
172
    {
      cout << "  "
        << i_series->header.station << " "
        << i_series->header.channel << " "
        << i_series->header.auxid << " "
        << "dt=" << i_series->header.dt << "s "
        << "begin: " << i_series->header.date.timestring() << " "
        << "n: " << i_series->header.nsamples 
        << endl;
      ++i_series;
    }
  }

173
174
175
  // trim time series
  if (opt.trim)
  {
176
177
    TFXX_assert(collection_of_series.overlap(),
                "time series do not overlap");
178
179
    collection_of_series.trim_to_date();
    collection_of_series.trim_to_nsamples();
180
181
182
183
184
185
186
187
  }

  // check consistency
  ::sff::WID2compare comparer(::sff::Fdt | ::sff::Fnsamples | ::sff::Fdate);
  comparer.setdatetolerance(opt.datetolerance);
  TFXX_assert(collection_of_series.are_consistent(comparer),
              "time series are inconsistent");

188
189
190
} // main()

/* ----- END OF croposp.cc ----- */