casa  $Rev:20696$
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines
ArrayMeasColumn.h
Go to the documentation of this file.
00001 //# ArrayMeasColumn.h: Access to array Measure columns in Tables.
00002 //# Copyright (C) 1997,1998,1999,2000
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 //# $Id: ArrayMeasColumn.h 21298 2012-12-07 14:53:03Z gervandiepen $
00027 
00028 #ifndef MEASURES_ARRAYMEASCOLUMN_H
00029 #define MEASURES_ARRAYMEASCOLUMN_H
00030 
00031 //# Includes
00032 #include <measures/TableMeasures/TableMeasColumn.h>
00033 #include <measures/Measures/MeasRef.h>
00034 
00035 namespace casa { //# NAMESPACE CASA - BEGIN
00036 
00037 //# Forward Declarations
00038 template <class T> class ArrayColumn;
00039 template <class T> class ScalarColumn;
00040 template <class T> class Array;
00041 template <class M> class ScalarMeasColumn;
00042 
00043 
00044 // <summary>
00045 // Read only access to table array Measure columns.
00046 // </summary>
00047 
00048 // <use visibility=export>
00049 
00050 // <reviewed reviewer="Bob Garwood" date="1999/12/23" tests="tTableMeasures.cc">
00051 // </reviewed>
00052 
00053 // <prerequisite>
00054 //   <li> <linkto module=Measures>Measures</linkto>
00055 //   <li> <linkto module=Tables>Tables</linkto>
00056 //   <li> TableMeasDesc
00057 // </prerequisite>
00058 
00059 // <synopsis>
00060 // ArrayMeasColumn objects can be used to access array Measure Columns
00061 // in tables, both for reading and writing (if the table is writable).
00062 //
00063 // Before a column can be accessed it must have previously been defined as
00064 // a Measure column by use of the
00065 // <linkto class="TableMeasDesc">TableMeasDesc</linkto> object.
00066 //
00067 // The ArrayMeasColumn class is templated on Measure type and MeasValue
00068 // type but typedefs exist for making declaration less long winded. The
00069 // Measure classes (like MEpoch) have typedefs <src>ArrayColumn</src>
00070 // to assist in creating ArrayMeasColumn objects.
00071 //
00072 // Constructing array Measure column objects using these typedefs looks like
00073 // this:
00074 // <srcblock>
00075 // // Read/write MEpoch array column
00076 // MEpoch::ArrayColumn ec(table, "ColumnName);
00077 // </srcblock>
00078 //
00079 // <h3>Reading and writing Measures</h3>
00080 //
00081 // The reading and writing of Measures columns is very similar to reading and
00082 // writing of "ordinary" Table columns.
00083 // <linkto class="ArrayMeasColumn#get">get()</linkto>
00084 // and <linkto class="ArrayMeasColumn#get">operator()</linkto>
00085 // exist for reading Measures and the
00086 // <linkto class="ArrayMeasColumn#put">put()</linkto> member for adding
00087 // Measures to a column.  (put() is obviously not defined for
00088 // ScalarMeasColumn objects.)  Each of these members accepts a row number
00089 // as an argument.
00090 //
00091 // Care needs to be taken when adding Measures to a column.  The user needs
00092 // to be aware that Measures are not checked for consistency, with respect to
00093 // a Measure's reference, between the Measures being added to a column and
00094 // the column's predefined Measure reference.  This is only an issue if the
00095 // Measure column was defined to have a fixed reference. For such columns
00096 // the reference component of Measures added to a column is silently
00097 // ignored, that is, there is no warning nor is there any sort of conversion
00098 // to the column's reference should the reference of the added Measure be
00099 // different from the column's reference.  The functions
00100 // <linkto class="TableMeasDescBase#isRefCodeVariable()">
00101 // TableMeasDescBase::isRefVariable()</linkto>
00102 // and
00103 // <linkto class="ArrayMeasColumn#getMeasRef()">
00104 // ArrayMeasColumn::getMeasRef()</linkto> can be
00105 // used to discover a Measure column's Measure reference characteristics.
00106 // </synopsis>
00107 
00108 // <example>
00109 // <srcblock>
00110 //    // create an MEpoch array column object
00111 //    ArrayMeasColumn<MEpoch> arrayCol;
00112 //
00113 //    // should be null.  Can test this and attach a real MEpoch column
00114 //    // The column Time1Arr should exist in the table and would have been
00115 //    // defined by using a TableMeasDesc
00116 //    if (arrayCol.isNull()) {
00117 //          arrayCol.attach(tab, "Time1Arr");
00118 //    }
00119 //
00120 //    // This would throw an Exception if the object is still null....but
00121 //    // hopefully won't
00122 //    arrayCol.throwIfNull();
00123 //
00124 //    // create a vector of MEpochs
00125 //    MEpoch last(Quantity(13.45, "h"), MEpoch::Ref(MEpoch::TAI));
00126 //    Vector<MEpoch> ev(10);
00127 //    for (uInt i=0; i<10; i++) {
00128 //        last.set(Quantity(13.45 + i, "h"));
00129 //        ev(i) = last;
00130 //    }
00131 //
00132 //    // before adding something check the isDefined() member
00133 //    if (!arrayCol.isDefined(0)) {
00134 //        cout << "PASS - nothing in the measure array column row yet\n";
00135 //    } else {
00136 //        cout << "FAIL - there shouldn't be a valid value in the row!\n";
00137 //    }
00138 //
00139 //    // add the MEpoch vector to the array Measure column at row 0
00140 //    arrayCol.put(0, ev);
00141 //
00142 //    // now read the array from the row.  Could use same object to do this
00143 //    // but here we'll create a ArrayMeasColumn<MEpoch> to do this
00144 //    ArrayMeasColumn<MEpoch> roArrCol(tab, "Time1Arr");
00145 //
00146 //    // need a vector to put the MEpochs into
00147 //    Vector<MEpoch> ew;
00148 //
00149 //    // setting the resize parameter to True automatically sets ew to the
00150 //    // same shape as the array contained in the row
00151 //    arrayCol.get(0, ew, True);
00152 // </srcblock>
00153 // </example>
00154 
00155 // <motivation>
00156 // The standard Casacore Table system does not support array Measure columns.
00157 // This class overcomes this limitation.
00158 // </motivation>
00159 
00160 // <thrown>
00161 //    <li>ArrayConformanceError during get() if supplied array is the wrong
00162 //        shape.
00163 // </thrown>
00164 
00165 //# <todo asof="$DATE:$">
00166 //# A List of bugs, limitations, extensions or planned refinements.
00167 //# </todo>
00168 
00169 
00170 template<class M> class ArrayMeasColumn : public TableMeasColumn
00171 {
00172 public:
00173   // The default constructor creates a null object.  Useful for creating
00174   // arrays of ArrayMeasColumn objects.  Attempting to use a null object
00175   // will produce a segmentation fault so care needs to be taken to
00176   // initialise the objects by using the attach() member before any attempt
00177   // is made to use the object.  A ArrayMeasColumn object can be tested
00178   // if it is null by using the isNull() member.
00179   ArrayMeasColumn();
00180 
00181   // Create the ArrayMeasColumn from the table and column Name.
00182   ArrayMeasColumn (const Table& tab, const String& columnName);
00183 
00184   // Copy constructor (copy semantics).
00185   ArrayMeasColumn (const ArrayMeasColumn<M>& that);
00186 
00187   virtual ~ArrayMeasColumn();
00188 
00189   // Change the reference to another column.
00190   void reference (const ArrayMeasColumn<M>& that);
00191 
00192   // Attach a column to the object.
00193   void attach (const Table& tab, const String& columnName);
00194 
00195   // Get the Measure array in the specified row.  For get() the supplied
00196   // array's shape should match the shape in the row unless resize is True.
00197   // <group name=get>
00198   void get (uInt rownr, Array<M>& meas, Bool resize = False) const;
00199   Array<M> operator() (uInt rownr) const;
00200   // </group>
00201 
00202   // Get the Measure array contained in the specified row and convert
00203   // it to the reference and offset found in the given measure.
00204   Array<M> convert (uInt rownr, const M& meas) const
00205     { return convert (rownr, meas.getRef()); }
00206 
00207   // Get the Measure array contained in the specified row and convert
00208   // it to the given reference.
00209   // <group>
00210   Array<M> convert (uInt rownr, const MeasRef<M>& measRef) const;
00211   Array<M> convert (uInt rownr, uInt refCode) const;
00212   // </group>
00213 
00214   // Get the column's reference.
00215   const MeasRef<M>& getMeasRef() const
00216     { return itsMeasRef; }
00217 
00218   // Reset the refCode, offset, or units.
00219   // It overwrites the value used when defining the TableMeasDesc.
00220   // Resetting the refCode and offset can only be done if they were
00221   // defined as fixed in the description.
00222   // <note role=tip>
00223   // In principle the functions can only be used if the table is empty,
00224   // otherwise already written values have thereafter the incorrect
00225   // reference, offset, or unit.
00226   // However, it is possible that part of the table is already
00227   // written and that the entire measure column is filled in later.
00228   // In that case the reference, offset, or units can be set by using
00229   // a False <src>tableMustBeEmpty</src> argument.
00230   // </note>
00231   // <group>
00232   void setDescRefCode (uInt refCode, Bool tableMustBeEmpty=True);
00233   void setDescOffset (const Measure& offset, Bool tableMustBeEmpty=True);
00234   void setDescUnits (const Vector<Unit>& units, Bool tableMustBeEmpty=True);
00235   // </group>
00236 
00237   // Add a Measure array to the specified row.
00238   // <group name=put>
00239   void put (uInt rownr, const Array<M>&);
00240   // </group>
00241 
00242 protected:
00243   //# Its measure reference when the MeasRef is constant per row.
00244   MeasRef<M> itsMeasRef;
00245 
00246 private:
00247   //# Column which contains the Measure's actual data.
00248   ArrayColumn<Double>* itsDataCol;
00249   //# Its MeasRef code column when references are variable.
00250   ScalarColumn<Int>* itsRefIntCol;
00251   ArrayColumn<Int>* itsArrRefIntCol;
00252   //# Its MeasRef column when references are variable and stored as Strings.
00253   ScalarColumn<String>* itsRefStrCol;
00254   ArrayColumn<String>* itsArrRefStrCol;
00255   //# Column containing its variable offsets.  Only applicable if the
00256   //# measure references have offsets and they are variable.
00257   ScalarMeasColumn<M>* itsOffsetCol;
00258   ArrayMeasColumn<M>* itsArrOffsetCol;
00259 
00260 
00261   // Assignment makes no sense in a read only class.
00262   // Declaring this operator private makes it unusable.
00263   ArrayMeasColumn& operator= (const ArrayMeasColumn<M>& that);
00264 
00265   // Deletes allocated memory etc. Called by ~tor and any member which needs
00266   // to reallocate data.
00267   void cleanUp();
00268 
00269   // Get the data and convert using conversion engine.
00270   Array<M> doConvert (uInt rownr, typename M::Convert& conv) const;
00271 };
00272 
00273 
00274 } //# NAMESPACE CASA - END
00275 
00276 
00277 //# Make old name ROArrayMeasColumn still available.
00278 #define ROArrayMeasColumn ArrayMeasColumn
00279 
00280 
00281 #ifndef CASACORE_NO_AUTO_TEMPLATES
00282 #include <measures/TableMeasures/ArrayMeasColumn.tcc>
00283 #endif //# CASACORE_NO_AUTO_TEMPLATES
00284 #endif