casa
$Rev:20696$
|
00001 //# MeasConvert.h: Conversion of Measures 00002 //# Copyright (C) 1995,1996,1997,1998,1999,2000,2001 00003 //# Associated Universities, Inc. Washington DC, USA. 00004 //# 00005 //# This library is free software; you can redistribute it and/or modify it 00006 //# under the terms of the GNU Library General Public License as published by 00007 //# the Free Software Foundation; either version 2 of the License, or (at your 00008 //# option) any later version. 00009 //# 00010 //# This library is distributed in the hope that it will be useful, but WITHOUT 00011 //# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 00012 //# FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public 00013 //# License for more details. 00014 //# 00015 //# You should have received a copy of the GNU Library General Public License 00016 //# along with this library; if not, write to the Free Software Foundation, 00017 //# Inc., 675 Massachusetts Ave, Cambridge, MA 02139, USA. 00018 //# 00019 //# Correspondence concerning AIPS++ should be addressed as follows: 00020 //# Internet email: aips2-request@nrao.edu. 00021 //# Postal address: AIPS++ Project Office 00022 //# National Radio Astronomy Observatory 00023 //# 520 Edgemont Road 00024 //# Charlottesville, VA 22903-2475 USA 00025 //# 00026 //# 00027 //# $Id: MeasConvert.h 21024 2011-03-01 11:46:18Z gervandiepen $ 00028 00029 #ifndef MEASURES_MEASCONVERT_H 00030 #define MEASURES_MEASCONVERT_H 00031 00032 //# Includes 00033 #include <casa/aips.h> 00034 #include <casa/Containers/Block.h> 00035 #include <measures/Measures/MConvertBase.h> 00036 #include <casa/Quanta/Quantum.h> 00037 #include <measures/Measures/Measure.h> 00038 namespace casa { //# NAMESPACE CASA - BEGIN 00039 00041 00042 //# Forward Declarations 00043 class MCBase; 00044 class MeasVal; 00045 00046 //# Typedefs 00047 00048 //# Constants 00049 00050 // <summary> Conversion of Measures </summary> 00051 00052 // <use visibility=export> 00053 00054 // <reviewed reviewer="UNKNOWN" date="before2004/08/25" tests="tMeasure" demos=""> 00055 // </reviewed> 00056 00057 // <prerequisite> 00058 // <li> <linkto class=Measure>Measure</linkto> class 00059 // <li> <linkto class=MRBase>MeasRef</linkto> base class 00060 // <li> <linkto class=MConvertBase>MConvertBase</linkto> class 00061 // <li> <linkto class=Quantum>Quantum</linkto> class 00062 // </prerequisite> 00063 // 00064 // <etymology> 00065 // </etymology> 00066 // 00067 // <synopsis> 00068 // MeasConvert can convert a Measure to the same type of Measure in a 00069 // different reference frame. The MeasConvert is a templated class, but 00070 // has typedefs, which are strongly recommended to be used, 00071 // for the allowed conversions, like <src>MEpoch::Convert.</src><br> 00072 // The basic operation is to create a MeasConvert with either of: 00073 // <ul> 00074 // <li> MEpoch::Convert(MEpoch, MEpoch::Ref), where the 00075 // <linkto class=MEpoch>MEpoch</linkto> is a template for subsequent 00076 // conversions, i.e. it will remember the value (with its reference) and 00077 // the <linkto class=MeasRef>MeasRef</linkto> output reference. 00078 // <li> MEpoch::Convert(MEpoch) with a subsequent setOut(MEpoch::Ref) 00079 // <li> MEpoch::Convert(MEpoch::Ref in, MEpoch::Ref out) is a template for 00080 // conversions from the input reference to the output reference. The 00081 // 'template' model used is the default value for the Measure, with 00082 // no units. 00083 // <li> MEpoch::Convert(Unit, MEpoch::Ref in, MEpoch::Ref out) is a 00084 // template for 00085 // conversions from the input reference to the output reference. The 00086 // 'template' model used is the default value for the Measure, with 00087 // the default units as specified. 00088 // <li> MEpoch::Convert() with a setModel(MEpoch) and setOut(). 00089 // </ul> 00090 // An empty MeasRef argument indicates no conversion will be attempted<br>. 00091 // The constructor, and set functions, analyse the 'template' Measure and the 00092 // output reference frame, and construct a pointer (in practice a list 00093 // of pointers to bypass the necessity of creating too many conversion 00094 // functions) to a conversion routine. 00095 // 00096 // An <src>isNOP()</src> function is available to test if the created 00097 // conversion engine is empty. 00098 // 00099 // Actual conversions are done with the () operator, which produces a new 00100 // MEpoch (or other appropiate Measure).<br> 00101 // Possible arguments are (MVEpoch is used here generic, and indicates the 00102 // internal format of a Measure; possibly, to make sure distinction between 00103 // values with and without units possible, even simple Measures will 00104 // have their own internal class format, e.g. MVDouble. 00105 // The possible arguments to the () conversion operator are (again Epoch 00106 // is used for the generic Measure): 00107 // <ul> 00108 // <li> (MEpoch, MEpoch::Ref): will create a new conversion method, and use 00109 // it to produce the result of converting the MEpoch to the specified 00110 // frame 00111 // <li> (MEpoch): will create a new conversion method from the 00112 // MEpoch to the MeasRef belonging to the MeasConvert 00113 // <li> (Quantity): will use the conversion chain deduced from the 00114 // MEpoch model in the definition of MeasConvert, and will convert the 00115 // Quantity 00116 // <li> (Quantum<Vector<Double> >) as previous 00117 // <li> (Double): will use the units (if present) as specified in the 00118 // MeasConvert object to construct the internal value 00119 // to be converted 00120 // <li> (Vector<Double> >): as previous 00121 // </ul> 00122 // Float versions will be produced if necessary.<br> 00123 // The conversion analyser expects that all Measure classes have a set 00124 // of routines to do the actual analysing and conversion. 00125 // (see <linkto class=MCBase>MCBase</linkto> class for how this is done in 00126 // practice).<br> 00127 // If the standard conversion is not sufficient, additional methods can be 00128 // added at the end of the list with the <src>addMethod()</src> member 00129 // function (for real pros).<br> 00130 // </synopsis> 00131 // 00132 // <example> 00133 // See <linkto class=Measure>Measure</linkto> for an example 00134 // </example> 00135 // 00136 // <motivation> 00137 // Conversion of Measures will in general be done on a series of values. 00138 // Separating the analysis of the calculations necessary for the conversion 00139 // from the actual conversion could speed up the process. 00140 // </motivation> 00141 // 00142 // <todo asof="1999/09/24"> 00143 // </todo> 00144 00145 template<class M> class MeasConvert : public MConvertBase { 00146 00147 public: 00148 00149 //# Friends 00150 00151 //# Constructors 00152 // <note role=tip> In the following constructors and other functions, all 00153 // <em>MeasRef</em> can be replaced with simple <src>Measure::TYPE</src> 00154 // where no offsets or frames are needed in the reference.</note> 00155 // Construct an empty MeasConvert. It is not usable, unless a setModel, and 00156 // probably a setOut has been done. 00157 MeasConvert(); 00158 // Copy constructor 00159 MeasConvert(const MeasConvert<M> &other); 00160 // Copy assignment 00161 MeasConvert<M> &operator=(const MeasConvert<M> &other); 00162 00163 // Construct a conversion for the specified Measure and reference 00164 // <group> 00165 MeasConvert(const M &ep); 00166 MeasConvert(const M &ep, const typename M::Ref &mr); 00167 MeasConvert(const Measure &ep, const typename M::Ref &mr); 00168 MeasConvert(const M &ep, typename M::Types mr); 00169 MeasConvert(const Measure &ep, typename M::Types mr); 00170 MeasConvert(const typename M::Ref &mrin, const typename M::Ref &mr); 00171 MeasConvert(const typename M::Ref &mrin, typename M::Types mr); 00172 MeasConvert(typename M::Types mrin, const typename M::Ref &mr); 00173 MeasConvert(typename M::Types mrin, typename M::Types mr); 00174 MeasConvert(const Unit &inunit, const typename M::Ref &mrin, 00175 const typename M::Ref &mr); 00176 MeasConvert(const Unit &inunit, const typename M::Ref &mrin, 00177 typename M::Types mr); 00178 MeasConvert(const Unit &inunit, typename M::Types mrin, 00179 const typename M::Ref &mr); 00180 MeasConvert(const Unit &inunit, typename M::Types mrin, 00181 typename M::Types mr); 00182 // </group> 00183 00184 //# Destructor 00185 ~MeasConvert(); 00186 00187 //# Operators 00188 // The actual conversion operations 00189 // <group> 00190 // Convert model Measure to output frame 00191 const M &operator()(); 00192 const M &operator()(Double val); 00193 const M &operator()(const Vector<Double> &val); 00194 const M &operator()(const Quantum<Double> &val); 00195 const M &operator()(const Quantum<Vector<Double> > &val); 00196 const M &operator()(const typename M::MVType &val); 00197 const M &operator()(const MeasVal *val); 00198 const M &operator()(const M &val); 00199 const M &operator()(const M &val, const typename M::Ref &mr); 00200 const M &operator()(const M &val, typename M::Types mr); 00201 const M &operator()(const typename M::Ref &mr); 00202 const M &operator()(typename M::Types mr); 00203 // </group> 00204 00205 //# General Member Functions 00206 // Set a new model for the conversion 00207 virtual void setModel(const Measure &val); 00208 // Set a new output reference 00209 // <group> 00210 void setOut(const typename M::Ref &mr); 00211 void setOut(typename M::Types mr); 00212 // </group> 00213 // Set a new model and reference 00214 // <group> 00215 void set(const M &val, const typename M::Ref &mr); 00216 void set(const M &val, typename M::Types mr); 00217 // </group> 00218 // Set a new model value only 00219 virtual void set(const MeasValue &val); 00220 // Set a new model unit only 00221 virtual void set(const Unit &inunit); 00222 00223 // Add a method (Note: uInt should be an enum from the appropiate Measure) 00224 virtual void addMethod(uInt method); 00225 // Add the frame type (Note: tp should be an MeasFrame::FrameType) 00226 virtual void addFrameType(uInt tp); 00227 // Get number of methods 00228 virtual Int nMethod() const; 00229 // Get method 00230 virtual uInt getMethod(uInt which) const; 00231 // Is the conversion engine empty? 00232 Bool isNOP() { return crout.nelements() == 0; } 00233 // Print conversion engine 00234 virtual void print(ostream &os) const; 00235 00236 private: 00237 //# Data 00238 // The model template Measure 00239 Measure *model; 00240 // The model unit to be used in conversions 00241 Unit unit; 00242 // The output reference 00243 typename M::Ref outref; 00244 // The input offset 00245 typename M::MVType *offin; 00246 // The output offset 00247 typename M::MVType *offout; 00248 // Vector of conversion routines (length variable) 00249 Block<uInt> crout; 00250 // Coded (with MeasFrame::FrameTypes) frames used in conversion 00251 uInt crtype; 00252 // Local conversion data 00253 MCBase *cvdat; 00254 // Cyclic buffer for return values 00255 // <group> 00256 // Current pointer 00257 Int lres; 00258 M *result[4]; 00259 // </group> 00260 // Local variables that can be used in conversion 00261 // <group> 00262 typename M::MVType *locres; 00263 // </group> 00264 00265 //# Member functions 00266 // Initialise pointers 00267 void init(); 00268 // Copy a MeasConvert 00269 void copy(const MeasConvert<M> &other); 00270 // Clear self 00271 void clear(); 00272 // Create the conversion routine chain 00273 void create(); 00274 // Convert a value 00275 // <group> 00276 const typename M::MVType &convert(); 00277 const typename M::MVType &convert(const typename M::MVType &val); 00278 // </group> 00279 }; 00280 00281 //# Global functions 00282 00283 00284 } //# NAMESPACE CASA - END 00285 00286 #ifndef CASACORE_NO_AUTO_TEMPLATES 00287 #include <measures/Measures/MeasConvert.tcc> 00288 #endif //# CASACORE_NO_AUTO_TEMPLATES 00289 #endif