source: trunk/src/STFrequencies.cpp @ 806

Last change on this file since 806 was 806, checked in by mar637, 18 years ago

Frequency subtable for Scantable. Initial revision.

File size: 5.6 KB
Line 
1//
2// C++ Implementation: STFrequencies
3//
4// Description:
5//
6//
7// Author: Malte Marquarding <asap@atnf.csiro.au>, (C) 2006
8//
9// Copyright: See COPYING file that comes with this distribution
10//
11//
12#include <casa/iostream.h>
13#include <casa/iomanip.h>
14#include <casa/Exceptions/Error.h>
15#include <casa/Containers/RecordField.h>
16#include <casa/Arrays/IPosition.h>
17
18#include <tables/Tables/TableDesc.h>
19#include <tables/Tables/SetupNewTab.h>
20#include <tables/Tables/ScaColDesc.h>
21#include <tables/Tables/TableRecord.h>
22#include <tables/Tables/TableParse.h>
23#include <tables/Tables/TableRow.h>
24
25#include <coordinates/Coordinates/CoordinateSystem.h>
26#include <coordinates/Coordinates/CoordinateUtil.h>
27
28#include "STFrequencies.h"
29
30
31using namespace casa;
32
33namespace asap {
34
35const casa::String STFrequencies::name_ = "FREQUENCIES";
36
37STFrequencies::STFrequencies(casa::Table::TableType tt) :
38  STSubTable( name_, tt )
39{
40  setup();
41}
42
43
44STFrequencies::~STFrequencies()
45{
46}
47
48void STFrequencies::setup( )
49{
50  // add to base class table
51  table_.addColumn(ScalarColumnDesc<Double>("REFPIX"));
52  table_.addColumn(ScalarColumnDesc<Double>("REFVAL"));
53  table_.addColumn(ScalarColumnDesc<Double>("INCREMENT"));
54
55  table_.rwKeywordSet().define("REFFRAME", String("TOPO"));
56  table_.rwKeywordSet().define("EQUINOX",String( "J2000"));
57  table_.rwKeywordSet().define("UNIT", String("Hz"));
58  table_.rwKeywordSet().define("DOPPLER", String("RADIO"));
59
60  // new cached columns
61  refpixCol_.attach(table_,"REFPIX");
62  refvalCol_.attach(table_,"REFVAL");
63  incrCol_.attach(table_,"INCREMENT");
64}
65
66uInt STFrequencies::addEntry( Double refpix, Double refval, Double inc )
67{
68  // test if this already exists
69  Table result = table_( near(table_.col("REFVAL"), refval)
70                    && near(table_.col("REFPIX"), refpix)
71                    && near(table_.col("INCREMENT"), inc) );
72  uInt resultid = 0;
73  if ( result.nrow() > 0) {
74    ROScalarColumn<uInt> c(result, "ID");
75    c.get(0, resultid);
76
77  } else {
78    uInt rno = table_.nrow();
79    table_.addRow();
80    // get last assigned freq_id and increment
81    if ( rno > 0 ) {
82      idCol_.get(rno-1, resultid);
83      resultid++;
84    }
85    refpixCol_.put(rno, refpix);
86    refvalCol_.put(rno, refval);
87    incrCol_.put(rno, inc);
88    idCol_.put(rno, resultid);
89  }
90  return resultid;
91}
92
93
94SpectralCoordinate STFrequencies::getSpectralCoordinate( uInt freqID )
95{
96  Table t = table_(table_.col("ID") == Int(freqID) );
97
98  if (t.nrow() == 0 ) {
99    throw(AipsError("STFrequencies::getSpectralCoordinate - freqID out of range"));
100  }
101
102  // get the data
103  ROTableRow row(t);
104  // get first row - there should only be one matching id
105  const TableRecord& rec = row.get(0);
106
107  return SpectralCoordinate( getFrame(), rec.asDouble("REFVAL"),
108                             rec.asDouble("INCREMENT"),
109                             rec.asDouble("REFPIX"));
110}
111
112void STFrequencies::rescale( casa::Float factor, const std::string& mode )
113{
114  TableRow row(table_);
115  TableRecord& outrec = row.record();
116  RecordFieldPtr<Double> rv(outrec, "REFVAL");
117  RecordFieldPtr<Double> rp(outrec, "REFPIX");
118  RecordFieldPtr<Double> inc(outrec, "INCREMENT");
119  for (uInt i=0; i<table_.nrow(); ++i) {
120
121    const TableRecord& rec = row.get(i);
122
123    SpectralCoordinate sc ( getFrame(), rec.asDouble("REFVAL"),
124                            rec.asDouble("INCREMENT"), rec.asDouble("REFPIX") );
125
126    SpectralCoordinate scout;
127    if (mode == "BIN") {
128      scout = binCsys(sc, Int(factor));
129    } else if (mode == "RESAMPLE") {
130      scout = resampleCsys(sc, factor);
131    }
132    *rv = scout.referenceValue()[0];
133    *rp = scout.referencePixel()[0];
134    *inc = scout.increment()[0];
135    row.put(i);
136  }
137}
138
139SpectralCoordinate STFrequencies::binCsys(const SpectralCoordinate& sc,
140                                          Int factor)
141{
142  CoordinateSystem csys;
143  csys.addCoordinate(sc);
144  IPosition factors(1, factor);
145  CoordinateSystem binnedcs =
146    CoordinateUtil::makeBinnedCoordinateSystem(factors, csys, False);
147  return binnedcs.spectralCoordinate(0);
148}
149
150SpectralCoordinate STFrequencies::resampleCsys(const SpectralCoordinate& sc,
151                                               Float width)
152{
153  Vector<Float> offset(1,0.0);
154  Vector<Float> factors(1,1.0/width);
155  Vector<Int> newshape;
156  CoordinateSystem csys;
157  csys.addCoordinate(sc);
158  CoordinateSystem csys2 = csys.subImage(offset, factors, newshape);
159  return csys2.spectralCoordinate(0);
160}
161
162
163casa::MFrequency::Types STFrequencies::getFrame( ) const
164{
165  // get the ref frame
166  String rf;
167  table_.keywordSet().get("REFFRAME", rf);
168
169  // Create SpectralCoordinate (units Hz)
170  MFrequency::Types mft;
171  if (!MFrequency::getType(mft, rf)) {
172    ostringstream oss;
173    pushLog("WARNING: Frequency type unknown assuming TOPO");
174    mft = MFrequency::TOPO;
175  }
176
177  return mft;
178}
179
180std::string asap::STFrequencies::print( int id )
181{
182  Table t;
183  ostringstream oss;
184  if ( id < 0 ) t = table_;
185  else  t = table_(table_.col("ID") == Int(id) );
186  ROTableRow row(t);
187  for (uInt i=0; i<t.nrow(); ++i) {
188    const TableRecord& rec = row.get(i);
189    oss <<  setw(8)
190    << "frame" << setw(16) << setprecision(8)
191    << rec.asDouble("REFVAL") << setw(10)
192    << rec.asDouble("REFPIX") << setw(12)
193    << rec.asDouble("INCREMENT") << endl;
194  }
195  return String(oss);
196}
197
198float STFrequencies::getRefFreq( uInt id, uInt channel )
199{
200  Table t = table_(table_.col("ID") == Int(id) );
201  if ( t.nrow() == 0 ) throw(AipsError("Selected Illegal frequency id"));
202  ROTableRow row(t);
203  const TableRecord& rec = row.get(0);
204  return (Double(channel/2) - rec.asDouble("REFPIX"))
205          * rec.asDouble("INCREMENT") + rec.asDouble("REFVAL");
206}
207
208} // namespace
Note: See TracBrowser for help on using the repository browser.