casa
$Rev:20696$
|
00001 //# ScaledComplexData.h: Templated virtual column engine to scale a complex table array 00002 //# Copyright (C) 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 //# $Id: ScaledComplexData.h 21298 2012-12-07 14:53:03Z gervandiepen $ 00027 00028 #ifndef TABLES_SCALEDCOMPLEXDATA_H 00029 #define TABLES_SCALEDCOMPLEXDATA_H 00030 00031 00032 //# Includes 00033 #include <tables/Tables/BaseMappedArrayEngine.h> 00034 00035 namespace casa { //# NAMESPACE CASA - BEGIN 00036 00037 //# Forward Declarations 00038 template<class T> class ScalarColumn; 00039 00040 00041 // <summary> 00042 // Templated virtual column engine to scale a complex table array 00043 // </summary> 00044 00045 // <use visibility=export> 00046 00047 // <reviewed reviewer="Gareth Hunt" date="94Nov17" tests=""> 00048 // </reviewed> 00049 00050 // <prerequisite> 00051 //# Classes you should understand before using this one. 00052 // <li> VirtualColumnEngine 00053 // <li> VirtualArrayColumn 00054 // </prerequisite> 00055 00056 // <synopsis> 00057 // ScaledComplexData is a virtual column engine which scales an array 00058 // of a complex type to 2 values of another type (to save disk storage). 00059 // For example, <src>ScaledComplexData<Complex,Short></src> resembles the 00060 // classic AIPS compress method which scales the data from float to short. 00061 // The (complex) scale factor and offset value can be given in two ways: 00062 // <ul> 00063 // <li> As a fixed value which is used for all arrays in the column. 00064 // <li> As the name of a column. In this way each array in a 00065 // column can have its own scale and offset value. 00066 // The scale and offset value in a row must be put before 00067 // the array is put and should not be changed anymore. 00068 // </ul> 00069 // It is also possible to have a variable scale factor with a fixed offset 00070 // value. 00071 // As in FITS the scale and offset values are used as: 00072 // <br><src> True_value = Stored_value * scale + offset; </src> 00073 // 00074 // An engine object should be used for one column only, because the stored 00075 // column name is part of the engine. If it would be used for more than 00076 // one column, they would all share the same stored column. 00077 // When the engine is bound to a column, it is checked if the name 00078 // of that column matches the given virtual column name. 00079 // 00080 // The engine can be used for a column containing any kind of array 00081 // (thus direct or indirect, fixed or variable shaped)) as long as the 00082 // virtual array can be stored in the stored array. Thus a fixed shaped 00083 // virtual can use a variable shaped stored, but not vice versa. 00084 // A fixed shape indirect virtual can use a stored with direct arrays. 00085 // 00086 // This class can also serve as an example of how to implement 00087 // a virtual column engine. 00088 // </synopsis> 00089 00090 // <motivation> 00091 // This class allows to store data in a smaller representation. 00092 // It is needed to resemble the classic AIPS compress option. 00093 // It adds the scale and offset value on a per row basis. 00094 // 00095 // Because the engine can serve only one column, it was possible to 00096 // combine the engine and the column functionality in one class. 00097 // This has been achieved using multiple inheritance. 00098 // The advantage of this is that only one templated class is used, 00099 // so less template instantiations are needed. 00100 // 00101 // Class ScaledArrayEngine could not be used, because complex integer 00102 // types are not supported in the tabe system. 00103 // </motivation> 00104 00105 // <example> 00106 // <srcblock> 00107 // // Create the table description and 2 columns with indirect arrays in it. 00108 // // The Int column will be stored, while the double will be 00109 // // used as virtual. 00110 // TableDesc tableDesc ("", TableDesc::Scratch); 00111 // tableDesc.addColumn (ArrayColumnDesc<Short> ("storedArray")); 00112 // tableDesc.addColumn (ArrayColumnDesc<Complex> ("virtualArray")); 00113 // 00114 // // Create a new table using the table description. 00115 // SetupNewTable newtab (tableDesc, "tab.data", Table::New); 00116 // 00117 // // Create the array scaling engine to scale from double to Int 00118 // // and bind it to the double column. 00119 // // Create the table. 00120 // ScaledComplexData<Complex,Short> scalingEngine("virtualArray", 00121 // "storedArray", 10); 00122 // newtab.bindColumn ("virtualArray", scalingEngine); 00123 // Table table (newtab); 00124 // 00125 // // Store a 2-D array (with dim. 3,4) into each row of the column. 00126 // // The shape of each array in the column is implicitly set by the put 00127 // // function. This will also set the shape of the underlying Int array 00128 // // (as a 3-D array with shape 2,3,4). 00129 // ArrayColumn data (table, "virtualArray"); 00130 // Array<DComplex> someArray(IPosition(2,3,4)); 00131 // someArray = 0; 00132 // for (uInt i=0, i<10; i++) { // table will have 10 rows 00133 // table.addRow(); 00134 // data.put (i, someArray) 00135 // } 00136 // </srcblock> 00137 // </example> 00138 00139 // <templating arg=VirtualType> 00140 // <li> only complex data types 00141 // </templating> 00142 // <templating arg=StoredType> 00143 // <li> only built-in numerics data types 00144 // </templating> 00145 00146 template<class VirtualType, class StoredType> 00147 class ScaledComplexData : public BaseMappedArrayEngine<VirtualType, StoredType> 00148 { 00149 //# Make members of parent class known. 00150 public: 00151 using BaseMappedArrayEngine<VirtualType,StoredType>::virtualName; 00152 protected: 00153 using BaseMappedArrayEngine<VirtualType,StoredType>::storedName; 00154 using BaseMappedArrayEngine<VirtualType,StoredType>::table; 00155 using BaseMappedArrayEngine<VirtualType,StoredType>::roColumn; 00156 using BaseMappedArrayEngine<VirtualType,StoredType>::rwColumn; 00157 using BaseMappedArrayEngine<VirtualType,StoredType>::setNames; 00158 00159 public: 00160 // Construct an engine to scale all arrays in a column with 00161 // the given offset and scale factor. 00162 // StoredColumnName is the name of the column where the scaled 00163 // data will be put and must have data type StoredType. 00164 // The virtual column using this engine must have data type VirtualType. 00165 ScaledComplexData (const String& virtualColumnName, 00166 const String& storedColumnName, 00167 VirtualType scale, 00168 VirtualType offset = 0); 00169 00170 // Construct an engine to scale the arrays in a column. 00171 // The scale and offset values are taken from a column with 00172 // the given names. In that way each array has its own scale factor 00173 // and offset value. 00174 // An exception is thrown if these columns do not exist. 00175 // VirtualColumnName is the name of the virtual column and is used to 00176 // check if the engine gets bound to the correct column. 00177 // StoredColumnName is the name of the column where the scaled 00178 // data will be put and must have data type StoredType. 00179 // The virtual column using this engine must have data type VirtualType. 00180 // <group> 00181 ScaledComplexData (const String& virtualColumnName, 00182 const String& storedColumnName, 00183 const String& scaleColumnName, 00184 VirtualType offset = 0); 00185 ScaledComplexData (const String& virtualColumnName, 00186 const String& storedColumnName, 00187 const String& scaleColumnName, 00188 const String& offsetColumnName); 00189 // </group> 00190 00191 // Construct from a record specification as created by getmanagerSpec(). 00192 ScaledComplexData (const Record& spec); 00193 00194 // Destructor is mandatory. 00195 ~ScaledComplexData(); 00196 00197 // Return the type name of the engine (i.e. its class name). 00198 String dataManagerType() const; 00199 00200 // Record a record containing data manager specifications. 00201 virtual Record dataManagerSpec() const; 00202 00203 // Return the name of the class. 00204 // This includes the names of the template arguments. 00205 static String className(); 00206 00207 // The engine can access column cells. 00208 virtual Bool canAccessArrayColumnCells (Bool& reask) const; 00209 00210 // Register the class name and the static makeObject "constructor". 00211 // This will make the engine known to the table system. 00212 // The automatically invoked registration function in DataManReg.cc 00213 // contains ScaledComplexData<double,Int>. 00214 // Any other instantiation of this class must be registered "manually" 00215 // (or added to DataManReg.cc). 00216 static void registerClass(); 00217 00218 private: 00219 // The default constructor is required for reconstruction of the 00220 // engine when a table is read back. 00221 ScaledComplexData(); 00222 00223 // Copy constructor is only used by clone(). 00224 // (so it is made private). 00225 ScaledComplexData (const ScaledComplexData<VirtualType,StoredType>&); 00226 00227 // Assignment is not needed and therefore forbidden 00228 // (so it is made private and not implemented). 00229 ScaledComplexData<VirtualType,StoredType>& operator= 00230 (const ScaledComplexData<VirtualType,StoredType>&); 00231 00232 // Clone the engine object. 00233 virtual DataManager* clone() const; 00234 00235 // Initialize the object for a new table. 00236 // It defines the keywords containing the engine parameters. 00237 virtual void create (uInt initialNrrow); 00238 00239 // Preparing consists of setting the writable switch and 00240 // adding the initial number of rows in case of create. 00241 // Furthermore it reads the keywords containing the engine parameters. 00242 virtual void prepare(); 00243 00244 // Set the shape of the FixedShape arrays in the column. 00245 // This function only gets called if the column has FixedShape arrays. 00246 // The shape gets saved and used to set the shape of the arrays 00247 // in the stored in case the stored has non-FixedShape arrays. 00248 virtual void setShapeColumn (const IPosition& shape); 00249 00250 // Define the shape of the array in the given row. 00251 // When the shape of the (underlying) stored array has already been 00252 // defined, it checks whether its latter dimensions match the given 00253 // virtual shape. When matching, nothing will be done. 00254 // When mismatching or when the stored shape has not been defined 00255 // yet, the stored shape will be defined from the virtual shape and 00256 // the virtual element shape. 00257 // E.g. in case of a StokesVector a virtual shape of (512,512) 00258 // results in a stored shape of (4,512,512). 00259 virtual void setShape (uInt rownr, const IPosition& shape); 00260 00261 // Get the dimensionality of the array in the given row. 00262 virtual uInt ndim (uInt rownr); 00263 00264 // Get the shape of the array in the given row. 00265 // This is done by stripping the first dimension from the shape 00266 // of the underlying stored array. 00267 virtual IPosition shape (uInt rownr); 00268 00269 // Get an array in the given row. 00270 // This will scale and offset from the underlying array. 00271 virtual void getArray (uInt rownr, Array<VirtualType>& array); 00272 00273 // Put an array in the given row. 00274 // This will scale and offset to the underlying array. 00275 virtual void putArray (uInt rownr, const Array<VirtualType>& array); 00276 00277 // Get a section of the array in the given row. 00278 // This will scale and offset from the underlying array. 00279 virtual void getSlice (uInt rownr, const Slicer& slicer, 00280 Array<VirtualType>& array); 00281 00282 // Put into a section of the array in the given row. 00283 // This will scale and offset to the underlying array. 00284 virtual void putSlice (uInt rownr, const Slicer& slicer, 00285 const Array<VirtualType>& array); 00286 00287 // Get an entire column. 00288 // This will scale and offset from the underlying array. 00289 virtual void getArrayColumn (Array<VirtualType>& array); 00290 00291 // Put an entire column. 00292 // This will scale and offset to the underlying array. 00293 virtual void putArrayColumn (const Array<VirtualType>& array); 00294 00295 // Get some array values in the column. 00296 // This will scale and offset from the underlying array. 00297 virtual void getArrayColumnCells (const RefRows& rownrs, 00298 Array<VirtualType>& data); 00299 00300 // Put some array values in the column. 00301 // This will scale and offset to the underlying array. 00302 virtual void putArrayColumnCells (const RefRows& rownrs, 00303 const Array<VirtualType>& data); 00304 00305 // Get a section of all arrays in the column. 00306 // This will scale and offset from the underlying array. 00307 virtual void getColumnSlice (const Slicer& slicer, 00308 Array<VirtualType>& array); 00309 00310 // Put a section of all arrays in the column. 00311 // This will scale and offset to the underlying array. 00312 virtual void putColumnSlice (const Slicer& slicer, 00313 const Array<VirtualType>& array); 00314 00315 // Get a section of some arrays in the column. 00316 // This will scale and offset from the underlying array. 00317 virtual void getColumnSliceCells (const RefRows& rownrs, 00318 const Slicer& slicer, 00319 Array<VirtualType>& data); 00320 00321 // Put into a section of some arrays in the column. 00322 // This will scale and offset to the underlying array. 00323 virtual void putColumnSliceCells (const RefRows& rownrs, 00324 const Slicer& slicer, 00325 const Array<VirtualType>& data); 00326 00327 // Scale and/or offset stored to array. 00328 // This is meant when reading an array from the stored column. 00329 // It optimizes for scale=1 and/or offset=0. 00330 void scaleOnGet (VirtualType scale, VirtualType offset, 00331 Array<VirtualType>& array, 00332 const Array<StoredType>& stored); 00333 00334 // Scale and/or offset array to stored. 00335 // This is meant when writing an array into the stored column. 00336 // It optimizes for scale=1 and/or offset=0. 00337 void scaleOnPut (VirtualType scale, VirtualType offset, 00338 const Array<VirtualType>& array, 00339 Array<StoredType>& stored); 00340 00341 // Scale and/or offset stored to array for the entire column. 00342 // When the scale and offset are fixed, it will do the entire array. 00343 // Otherwise it iterates through the array and applies the scale 00344 // and offset per row. 00345 void scaleColumnOnGet (Array<VirtualType>& array, 00346 const Array<StoredType>& stored); 00347 00348 // Scale and/or offset array to stored for the entire column. 00349 // When the scale and offset are fixed, it will do the entire array. 00350 // Otherwise it iterates through the array and applies the scale 00351 // and offset per row. 00352 void scaleColumnOnPut (const Array<VirtualType>& array, 00353 Array<StoredType>& stored); 00354 00355 // Scale and/or offset stored to array for some cells in the column. 00356 // When the scale and offset are fixed, it will do the entire array. 00357 // Otherwise it iterates through the array and applies the scale 00358 // and offset per row. 00359 void scaleCellsOnGet (Array<VirtualType>& array, 00360 const Array<StoredType>& stored, 00361 const RefRows& rownrs); 00362 00363 // Scale and/or offset array to stored for some cells in the column. 00364 // When the scale and offset are fixed, it will do the entire array. 00365 // Otherwise it iterates through the array and applies the scale 00366 // and offset per row. 00367 void scaleCellsOnPut (const Array<VirtualType>& array, 00368 Array<StoredType>& stored, 00369 const RefRows& rownrs); 00370 00371 // Determine the shape of an array in the stored column. 00372 IPosition storedShape (const IPosition& virtualShape) const 00373 { return IPosition(1,2).concatenate (virtualShape); } 00374 00375 // Convert the Slicer for a virtual to a Slicer for the stored. 00376 Slicer storedSlicer (const Slicer& virtualSlicer) const; 00377 00378 //# Now define the data members. 00379 String scaleName_p; //# name of scale column 00380 String offsetName_p; //# name of offset column 00381 VirtualType scale_p; //# scale factor 00382 VirtualType offset_p; //# offset value 00383 Bool fixedScale_p; //# scale is a fixed column 00384 Bool fixedOffset_p; //# offset is a fixed column 00385 ScalarColumn<VirtualType>* scaleColumn_p; //# column with scale value 00386 ScalarColumn<VirtualType>* offsetColumn_p; //# column with offset value 00387 00388 // Get the scale value for this row. 00389 VirtualType getScale (uInt rownr); 00390 00391 // Get the offset value for this row. 00392 VirtualType getOffset (uInt rownr); 00393 00394 public: 00395 // Define the "constructor" to construct this engine when a 00396 // table is read back. 00397 // This "constructor" has to be registered by the user of the engine. 00398 // If the engine is commonly used, its registration can be added 00399 // to the registerAllCtor function in DataManReg.cc. 00400 // That function gets automatically invoked by the table system. 00401 static DataManager* makeObject (const String& dataManagerType, 00402 const Record& spec); 00403 }; 00404 00405 00406 00407 } //# NAMESPACE CASA - END 00408 00409 #ifndef CASACORE_NO_AUTO_TEMPLATES 00410 #include <tables/Tables/ScaledComplexData.tcc> 00411 #endif //# CASACORE_NO_AUTO_TEMPLATES 00412 #endif