source: trunk/external-alma/asdm2ASAP/ASDMFiller.cc@ 2219

Last change on this file since 2219 was 2218, checked in by Takeshi Nakazato, 14 years ago

New Development: No

JIRA Issue: Yes CAS-1913

Ready for Test: Yes

Interface Changes: No

What Interface Changed: Please list interface changes

Test Programs: List test programs

Put in Release Notes: Yes/No

Module(s): Module Names change impacts.

Description: Describe your changes here...

Get frequency reference frame from the data.


File size: 17.7 KB
RevLine 
[2197]1#include<iostream>
2
3#include <STHeader.h>
4
5#include <measures/Measures/MEpoch.h>
6#include <measures/Measures/MPosition.h>
7#include <measures/Measures/MDirection.h>
8#include <measures/Measures/MCDirection.h>
9#include <measures/Measures/MeasFrame.h>
10#include <measures/Measures/MeasConvert.h>
11#include <casa/Arrays/Vector.h>
12#include <casa/Arrays/Matrix.h>
13#include <casa/Quanta/MVTime.h>
[2208]14#include <casa/Logging/LogMessage.h>
[2197]15
16#include "ASDMFiller.h"
17
18using namespace std ;
19using namespace casa ;
20using namespace asap ;
21
22ASDMFiller::ASDMFiller( CountedPtr<Scantable> stable )
23 : FillerBase( stable ),
24 antennaId_( -1 ),
[2208]25 antennaName_( "" ),
26 className_("ASDMFiller")
[2197]27{
28 reader_ = new ASDMReader() ;
29}
30
31ASDMFiller::~ASDMFiller()
32{
[2208]33 // nothing to do?
34 logsink_ = 0 ;
[2197]35}
36
[2208]37void ASDMFiller::setLogger( CountedPtr<LogSinkInterface> &logsink )
38{
39 logsink_ = logsink ;
40 if ( !(reader_.null()) ) {
41 reader_->setLogger( logsink ) ;
42 }
43}
44
[2197]45bool ASDMFiller::open( const string &filename, const Record &rec )
46{
[2208]47 String funcName = "open" ;
[2197]48 bool status = reader_->open( filename, rec ) ;
49
50 antennaId_ = reader_->getAntennaId() ;
51 antennaName_ = reader_->getAntennaName() ;
52
[2208]53 //logsink->postLocally( LogMessage("antennaId_ = "+String::toString(antennaId_),LogOrigin(className_,funcName,WHERE)) ) ;
54 //logsink->postLocally( LogMessage("antennaName_ = "+antennaName_,LogOrigin(className_,funcName,WHERE)) ) ;
[2197]55
56 return status ;
57}
58
59void ASDMFiller::fill()
60{
[2208]61 String funcName = "fill" ;
62
[2197]63 // header
64 fillHeader() ;
[2218]65
66 // set Frame for FREQUENCIES table
67 string sFreqFrame = reader_->getFrame() ;
68 MFrequency::Types freqFrame = toFrameType( sFreqFrame ) ;
69 table_->frequencies().setFrame( freqFrame, false ) ;
70 table_->frequencies().setFrame( freqFrame, true ) ;
[2197]71
72 Vector<casa::Double> antpos = table_->getHeader().antennaposition ;
73
74 //STHeader hdr = table_->getHeader() ;
75
76 // data selection
77 reader_->select() ;
78
79 // pick up valid configDescriptionId
80 Vector<uInt> configDescIdList = reader_->getConfigDescriptionIdList() ;
81 uInt numConfigDescId = configDescIdList.size() ;
82
[2208]83 //logsink->postLocally( LogMessage("configDescIdList = "+String::toString(configDescIdList),LogOrigin(className_,funcName,WHERE)) ) ;
[2197]84
85 // get field list
86 Vector<uInt> fieldIdList = reader_->getFieldIdList() ;
87 uInt numFieldId = fieldIdList.size() ;
88
[2208]89 //logsink->postLocally( LogMessage("fieldIdList = "+String::toString(fieldIdList),LogOrigin(className_,funcName,WHERE)) ) ;
[2197]90
91 // BEAMNO is always 0 since ALMA antenna is single beam
92 uInt beamno = 0 ;
93
94 // REFBEAMNO is -1
95 setReferenceBeam() ;
96
97 // fill FOCUS_ID and add FOCUS row if necessary
98 setFocus() ;
99
100 for ( uInt icon = 0 ; icon < numConfigDescId ; icon++ ) {
101 for ( unsigned int ifield = 0 ; ifield < numFieldId ; ifield++ ) {
[2208]102 //logsink_->postLocally( LogMessage("start configDescId "+String::toString(configDescIdList[icon])+" fieldId "+String::toString(fieldIdList[ifield]),LogOrigin(className_,funcName,WHERE)) ) ;
[2197]103
104 //Bool status = reader_->setMainRow( configDescIdList[icon], fieldIdList[ifield] ) ;
105 if ( !(reader_->setMainRow( configDescIdList[icon], fieldIdList[ifield] )) ) {
[2208]106 //logsink_->postLocally( LogMessage("skip configDescId "+String::toString(configDescIdList[icon])+" fieldId "+String::toString(fieldIdList[ifield]),LogOrigin(className_,funcName,WHERE)) ) ;
[2197]107 continue ;
108 }
109
110 // number of rows
111 uInt nrow = reader_->getNumMainRow() ;
112
[2208]113 //logsink_->postLocally( LogMessage("There are "+String::toString(nrow)+" rows in Main table corresponding to configDescId "+String::toString(configDescIdList[icon]+" fieldId "+String::toString(fieldIdList[ifield]),LogOrigin(className_,funcName,WHERE)) ) ;
[2197]114
115 // CYCLENO
116 unsigned int cycleno = 0 ;
117
118 for ( uInt irow = 0 ; irow < nrow ; irow++ ) {
119
120 // set main row
121 if ( !(reader_->setMainRow( irow )) ) {
122 // skip row since the row doesn't have valid configDescId
[2208]123 //logsink_->postLocally( LogMessage("skip "+String::toString(irow),LogOrigin(className_,funcName,WHERE)) ) ;
[2197]124 continue ;
125 }
126
127 // scan and subscan
128 unsigned int scanno = reader_->getScanNo() ;
129 //uInt subscanno = reader_->getSubscanNo() ;
130
131 // set data
132 if ( !(reader_->setData()) ) {
[2208]133 // skip row since reader failed to retrieve data
134 //logsink_->postLocally( LogMessage("skip "+String::toString(irow),LogOrigin(className_,funcName,WHRER)) ) ;
135 continue ;
[2197]136 }
137
138 unsigned int numData = reader_->getNumData() ;
139 double refpix = 0.0 ;
140 double refval = 0.0 ;
141 double incr = 0.0 ;
142
143 for ( unsigned int idata = 0 ; idata < numData ; idata++ ) {
144
145 // subscan number
146 unsigned int subscanno = reader_->getSubscanNo( idata ) ;
147
148 // IFNO
149 uInt ifno = reader_->getIFNo( idata ) ;
150
151
152 // REFPIX, REFVAL, INCREMENT
153 String ifkey = getIFKey( ifno ) ;
154 if ( ifrec_.isDefined( ifkey ) ) {
155 getFrequencyRec( ifkey, refpix, refval, incr ) ;
156 }
157 else {
158 reader_->getFrequency( idata, refpix, refval, incr ) ;
159 setFrequencyRec( ifkey, refpix, refval, incr ) ;
160 }
161
162 // fill FREQ_ID and add FREQUENCIES row if necessary
163 setFrequency( (casa::Double)refpix, (casa::Double)refval, (casa::Double)incr ) ;
164
165
166 // rest frequency
167 vector<double> rf = reader_->getRestFrequency( idata ) ;
168
169 // fill MOLECULE_ID and add MOLECULES row if necessary
170 Vector<casa::Double> restFreqs( rf.size() ) ;
171 for ( uInt i = 0 ; i < rf.size() ; i++ )
172 restFreqs[i] = (casa::Double)(rf[i]) ;
173 setMolecule( restFreqs ) ;
174
175
176 // time and interval
177 casa::Double mjd = (casa::Double)(reader_->getTime( idata )) ;
178 casa::Double interval = (casa::Double)(reader_->getInterval( idata )) ;
179
180 // fill TIME and INTERVAL
181 setTime( mjd, interval ) ;
182
183
184 // source spec
185 string srcname = reader_->getSourceName( idata ) ;
186 string fieldname = reader_->getFieldName( idata ) ;
187 int srctype = reader_->getSrcType( scanno, subscanno ) ;
188 vector<double> srcDirection = reader_->getSourceDirection( idata ) ;
189 vector<double> srcProperMotion = reader_->getSourceProperMotion( idata ) ;
190 double sysVel = reader_->getSysVel( idata ) ;
191
192 // fill SRCNAME, SRCTYPE, FIELDNAME, SRCDIRECTION, SRCPROPERMOTION, and SRCVELOCITY
193 Vector<casa::Double> srcDir( 2 ) ;
194 srcDir[0] = (casa::Double)(srcDirection[0]) ;
195 srcDir[1] = (casa::Double)(srcDirection[1]) ;
196 Vector<casa::Double> srcPM( 2 ) ;
197 srcPM[0] = (casa::Double)(srcProperMotion[0]) ;
198 srcPM[1] = (casa::Double)(srcProperMotion[1]) ;
199 setSource( srcname, srctype, fieldname, srcDir, srcPM, (casa::Double)sysVel ) ;
200
201 // fill FLAGROW
202 unsigned int flagrow = reader_->getFlagRow( idata ) ;
203 setFlagrow( (uInt)flagrow ) ;
204
205 // fill WEATHER_ID and add WEATHER row if necessary
206 float temperature ;
207 float pressure ;
208 float humidity ;
209 float windspeed ;
210 float windaz ;
211 reader_->getWeatherInfo( idata,
212 temperature,
213 pressure,
214 humidity,
215 windspeed,
216 windaz ) ;
217 setWeather2( (casa::Float)temperature,
218 (casa::Float)pressure,
219 (casa::Float)humidity,
220 (casa::Float)windspeed,
221 (casa::Float)windaz ) ;
222
223 // fill AZIMUTH, ELEVATION, DIRECTION and SCANRATE
224 vector<double> dir ;
225 double az ;
226 double el ;
227 vector<double> srate ;
228 reader_->getPointingInfo( idata,
229 dir,
230 az,
231 el,
232 srate ) ;
233 Vector<casa::Double> scanRate( 2, 0.0 ) ;
234 Vector<casa::Double> direction( 2, 0.0 ) ;
235 if ( srate.size() > 0 ) {
236 scanRate[0] = (casa::Double)(srate[0]) ;
237 scanRate[1] = (casa::Double)(srate[1]) ;
238 }
239 setScanRate( scanRate ) ;
240 if ( dir.size() > 0 ) {
241 direction[0] = (casa::Double)(dir[0]) ;
242 direction[1] = (casa::Double)(dir[1]) ;
243 }
244 else {
245 toJ2000( direction, az, el, mjd, antpos ) ;
246 }
[2208]247 //logsink_->postLocally( LogMessage("direction = "+String::toString(direction),LogOrigin(className_,funcName,WHERE)) ) ;
[2197]248 setDirection( direction, (casa::Float)az, (casa::Float)el ) ;
249
250 // loop on polarization
251 vector<unsigned int> dataShape = reader_->getDataShape( idata ) ;
[2208]252// ostringstream oss ;
253// for ( unsigned int i = 0 ; i < dataShape.size() ; i++ ) {
254// if ( i == 0 )
255// oss << "dataShape=[" << dataShape[i] << ", " ;
256// else if ( i == dataShape.size()-1 )
257// oss << dataShape[i] << "]" ;
258// else
259// oss << dataShape[i] << ", " ;
260// }
261// logsink_->postLocally( LogMessage(oss.str(),LogOrigin(className_,funcName,WHERE)) ) ;
262
[2197]263 //int numPol = reader_->getNumPol( idata ) ;
264 unsigned int numPol = dataShape[0] ;
265 unsigned int numChan = dataShape[1] ;
266
[2208]267 //logsink_->postLocally( LogMessage("numPol = "+String::toString(numPol),LogOrigin(className_,funcName,WHERE)) ) ;
[2197]268
269 // OPACITY
270 vector<float> tau = reader_->getOpacity( idata ) ;
271 Vector<casa::Float> opacity = toVector( tau, numPol ) ;
272
273 // SPECTRA, FLAGTRA, TSYS, TCAL
274 float *sp = reader_->getSpectrum( idata ) ;
275 vector< vector<float> > ts = reader_->getTsys( idata ) ;
276 vector< vector<float> > tc = reader_->getTcal( idata ) ;
277 Matrix<casa::Float> spectra = toMatrix( sp, numPol, numChan ) ;
278 Vector<uChar> flagtra( numChan, 0 ) ;
279 Matrix<casa::Float> tsys = toMatrix( ts, numPol, numChan ) ;
280 Matrix<casa::Float> tcal = toMatrix( tc, numPol, numChan ) ;
281// String caltime = "" ;
282// if ( anyNE( tcal, (casa::Float)1.0 ) )
283// caltime = toTcalTime( mjd ) ;
284 String caltime = toTcalTime( mjd ) ;
285
286 for ( unsigned int ipol = 0 ; ipol < numPol ; ipol++ ) {
287
288 // fill SCANNO, CYCLENO, IFNO, POLNO, and BEAMNO
289 setIndex( (uInt)scanno-1, (uInt)cycleno, ifno, ipol, beamno ) ;
290
291 // fill SPECTRA, FLAGTRA, TSYS
292 setSpectrum( spectra.row(ipol), flagtra, tsys.row(ipol) ) ;
293
294 // fill TCAL_ID and add TCAL row if necessary
295 setTcal2( caltime, tcal.row(ipol) ) ;
296
297 // fill OPACITY
298 setOpacity( opacity[ipol] ) ;
299
300 // commit row
301 commitRow() ;
302 }
303
304 // increment CYCLENO
305 cycleno++ ;
306 }
307 }
308 }
309 }
310
311 return ;
312}
313
314void ASDMFiller::close()
315{
316 reader_->close() ;
317 reader_ = 0 ;
318
319 return ;
320}
321
322void ASDMFiller::fillHeader()
323{
324 STHeader hdr ;
325
326 reader_->fillHeader( hdr.nchan,
327 hdr.npol,
328 hdr.nif,
329 hdr.nbeam,
330 hdr.observer,
331 hdr.project,
332 hdr.obstype,
333 hdr.antennaname,
334 hdr.antennaposition,
335 hdr.equinox,
336 hdr.freqref,
337 hdr.reffreq,
338 hdr.bandwidth,
339 hdr.utc,
340 hdr.fluxunit,
341 hdr.epoch,
342 hdr.poltype ) ;
343
344 setHeader( hdr ) ;
345}
346
347String ASDMFiller::getIFKey( uInt ifno )
348{
349 return "IFNO"+String::toString( ifno ) ;
350}
351
352void ASDMFiller::getFrequencyRec( String key,
353 double &refpix,
354 double &refval,
355 double &incr )
356{
357 Record frec = ifrec_.asRecord( key ) ;
358 refpix = frec.asdouble( "REFPIX" ) ;
359 refval = frec.asdouble( "REFVAL" ) ;
360 incr = frec.asdouble( "INCREMENT" ) ;
361}
362
363void ASDMFiller::setFrequencyRec( String key,
364 double refpix,
365 double refval,
366 double incr )
367{
368 Record frec ;
369 frec.define( "REFPIX", refpix ) ;
370 frec.define( "REFVAL", refval ) ;
371 frec.define( "INCREMENT", incr ) ;
372 ifrec_.defineRecord( key, frec ) ;
373}
374
375Matrix<casa::Float> ASDMFiller::toMatrix( float *sp,
376 unsigned int npol,
377 unsigned int nchan )
378{
379 Matrix<casa::Float> mSp( npol, nchan ) ;
380 if ( npol <= 2 ) {
381 // 1 or 2 polarization case
382 for ( unsigned int ich = 0 ; ich < nchan ; ich++ ) {
383 for ( unsigned int ipol = 0 ; ipol < npol ; ipol++ ) {
384 mSp(ipol,ich) = (casa::Float)(sp[npol*ich+ipol]) ;
385 }
386 }
387 }
388 else {
389 // 4 polarization case
390 for ( unsigned int ich = 0 ; ich < nchan ; ich++ ) {
391 mSp(0,ich) = (casa::Float)(sp[4*ich]) ; // Re(XX)
392 mSp(1,ich) = (casa::Float)(sp[4*ich+4]) ; // Re(YY)
393 mSp(2,ich) = (casa::Float)(sp[4*ich+2]) ; // Re(XY)
394 mSp(3,ich) = (casa::Float)(sp[4*ich+3]) ; // Im(XY)
395 }
396 }
397 return mSp ;
398}
399
400Matrix<casa::Float> ASDMFiller::toMatrix( vector< vector<float> > &tsys,
401 unsigned int npol,
402 unsigned int nchan )
403{
404 unsigned int numRec = tsys.size() ;
405 unsigned int numChan = tsys[0].size() ;
406 Matrix<casa::Float> ret ;
407 if ( npol == numRec && nchan == numChan ) {
408 ret.resize( npol, nchan ) ;
409 for ( unsigned int ip = 0 ; ip < npol ; ip++ )
410 for ( unsigned int ic = 0 ; ic < nchan ; ic++ )
411 ret( ip, ic ) = (casa::Float)(tsys[ip][ic]) ;
412 }
413 else if ( npol == numRec && numChan == 1 ) {
414 ret.resize( npol, 1 ) ;
415 for ( unsigned int ip = 0 ; ip < npol ; ip++ )
416 ret( ip, 0 ) = (casa::Float)(tsys[0][0]) ;
417 }
418 else if ( numRec == 1 && nchan == numChan ) {
419 ret.resize( npol, nchan ) ;
420 for ( unsigned int ip = 0 ; ip < npol ; ip++ )
421 for ( unsigned int ic = 0 ; ic < nchan ; ic++ )
422 ret( ip, ic ) = (casa::Float)(tsys[0][ic]) ;
423 }
424 else if ( numRec == 1 && numChan == 1 ) {
425 ret.resize( npol, 1 ) ;
426 for ( unsigned int ip = 0 ; ip < npol ; ip++ )
427 ret( ip, 0 ) = (casa::Float)(tsys[0][0]) ;
428 }
429 else if ( numRec == 2 && npol == 4 && numChan == nchan ) {
430 // TODO: How to determine Tsys for XY?
431 // at the moment Tsys[XY] = 0.5*(Tsys[X]+Tsys[Y])
432 ret.resize( npol, nchan ) ;
433 for ( unsigned int ic = 0 ; ic < nchan ; ic++ ) {
434 casa::Float tsysxy = (casa::Float)(0.5*(tsys[0][ic]+tsys[1][ic])) ;
435 ret( 0, ic ) = (casa::Float)(tsys[0][ic]) ;
436 ret( 1, ic ) = (casa::Float)(tsys[1][ic]) ;
437 ret( 2, ic ) = tsysxy ;
438 ret( 3, ic ) = tsysxy ;
439 }
440 }
441 else if ( numRec == 2 && npol == 4 && numChan == 1 ) {
442 // TODO: How to determine Tsys for XY?
443 // at the moment Tsys[XY] = 0.5*(Tsys[X]+Tsys[Y])
444 ret.resize( npol, 1 ) ;
445 casa::Float tsysxy = (casa::Float)(0.5*(tsys[0][0]+tsys[1][0])) ;
446 ret( 0, 0 ) = (casa::Float)(tsys[0][0]) ;
447 ret( 1, 0 ) = (casa::Float)(tsys[1][0]) ;
448 ret( 2, 0 ) = tsysxy ;
449 ret( 3, 0 ) = tsysxy ;
450 }
451 else {
452 // I don't know how to handle ...
453 for ( unsigned int ip = 0 ; ip < npol ; ip++ )
454 for ( unsigned int ic = 0 ; ic < nchan ; ic++ )
455 ret( ip, ic ) = (casa::Float)(tsys[0][ic]) ;
456 }
457 return ret ;
458}
459
460Vector<casa::Float> ASDMFiller::toVector( vector<float> &tau,
461 unsigned int npol )
462{
463 Vector<casa::Float> ret( npol ) ;
464
465 if ( npol == 4 ) {
466 ret[0] = (casa::Float)tau[0] ;
467 ret[1] = (casa::Float)tau[1] ;
468 ret[2] = 0.5 * ( ret[0] + ret[1] ) ;
469 ret[3] = ret[2] ;
470 }
471 else if ( npol == tau.size() ) {
472 for ( unsigned int ipol = 0 ; ipol < npol ; ipol++ )
473 ret[ipol] = (casa::Float)tau[ipol] ;
474 }
475 else {
476 // I don't know how to handle...
477 for ( unsigned int ipol = 0 ; ipol < npol ; ipol++ )
478 ret[ipol] = (casa::Float)tau[0] ;
479 }
480 return ret ;
481}
482
483String ASDMFiller::toTcalTime( casa::Double mjd )
484{
485 return MVTime( mjd ).string( MVTime::YMD ) ;
486}
487
488void ASDMFiller::toJ2000( Vector<casa::Double> &dir,
489 double az,
490 double el,
491 casa::Double mjd,
492 Vector<casa::Double> antpos )
493{
[2208]494 String funcName = "toJ2000" ;
495
[2197]496 Vector<casa::Double> azel( 2 ) ;
497 azel[0] = az ;
498 azel[1] = el ;
499 MEpoch me( Quantity( mjd, "d" ), MEpoch::UTC ) ;
500 Vector<Quantity> qantpos( 3 ) ;
501 qantpos[0] = Quantity( antpos[0], "m" ) ;
502 qantpos[1] = Quantity( antpos[1], "m" ) ;
503 qantpos[2] = Quantity( antpos[2], "m" ) ;
504 MPosition mp( MVPosition( qantpos ),
505 MPosition::ITRF ) ;
[2208]506// mp.print( os_.output() ) ;
[2197]507 MeasFrame mf( me, mp ) ;
508 MDirection::Convert toj2000( MDirection::AZELGEO,
509 MDirection::Ref( MDirection::J2000, mf ) ) ;
510 dir = toj2000( azel ).getAngle( "rad" ).getValue() ;
[2208]511 //logsink->postLocally( LogMessage("dir = "+String::toString(dir),LogOrigin(className_,funcName,WHERE)) ) ;
[2197]512}
513
[2218]514MFrequency::Types ASDMFiller::toFrameType( string &s )
515{
516 MFrequency::Types ftype = MFrequency::DEFAULT ;
517 if ( s == "LABREST" )
518 ftype = MFrequency::REST ;
519 else {
520 Bool b = MFrequency::getType( ftype, String(s) ) ;
521 if (!b)
522 ftype = MFrequency::DEFAULT ;
523 }
524 return ftype ;
525}
Note: See TracBrowser for help on using the repository browser.