00001 //# LatticeConcat.h: concatenate lattices along an axis 00002 //# Copyright (C) 1996,1997,1998,1999,2000,2003 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$ 00027 00028 #ifndef LATTICES_LATTICECONCAT_H 00029 #define LATTICES_LATTICECONCAT_H 00030 00031 00032 //# Includes 00033 #include <casacore/casa/aips.h> 00034 #include <casacore/lattices/Lattices/MaskedLattice.h> 00035 #include <casacore/casa/Containers/Block.h> 00036 00037 namespace casacore { //# NAMESPACE CASACORE - BEGIN 00038 00039 //# Forward Declarations 00040 class IPosition; 00041 class Slicer; 00042 00043 00044 // <summary> 00045 // Concatenates lattices along a specified axis 00046 // </summary> 00047 00048 // <use visibility=export> 00049 00050 // <reviewed reviewer="" date="yyyy/mm/dd" tests="" demos=""> 00051 // </reviewed> 00052 00053 // <prerequisite> 00054 // <li> <linkto class=MaskedLattice>MaskedLattice</linkto> (base class) 00055 // </prerequisite> 00056 00057 // <etymology> 00058 // This is a class designed to concatenate lattices along a specified axis 00059 // </etymology> 00060 00061 // <synopsis> 00062 // This is a class designed to concatenate lattices along a specified 00063 // axis. This means you can join them together. E.g., 00064 // join lattices of shape [10,20,30] and [10,20,40] into a lattice 00065 // of shape [10,20,70]. 00066 // 00067 // In addition, you can increase the dimensionality 00068 // and join lattices [10,20] and [10,20] to [10,20,2]. This is 00069 // done by specifying the concatenation axis to be higher than 00070 // currently exists in the input lattices 00071 // 00072 // The LatticeConcat object does not copy the input lattices, it 00073 // just references them. You can use the Lattice<T>::copyData(Lattice<T>) 00074 // function to fill an output lattice with the concatenated input lattices. 00075 // 00076 // If you use the putSlice function, be aware that it will change the 00077 // underlying lattices if they are writable. 00078 // </synopsis> 00079 // 00080 // <example> 00081 // <srcBlock> 00082 // 00084 // 00085 // ArrayLattice<Float> al1(a1); al1.set(1.0); 00086 // ArrayLattice<Float> al2(a2); al2.set(10.0); 00087 // 00089 // 00090 // SubLattice<Float> ml1(al1, True); 00091 // SubLattice<Float> ml2(al2, True); 00092 // 00094 // 00095 // LatticeConcat<Float> lc (1); 00096 // lc.setLattice(ml1); 00097 // lc.setLattice(ml2); 00098 // 00100 // 00101 // ArrayLattice<Float> al3(lc.shape()); 00102 // SubLattice<Float> ml3(al3, True); 00103 // 00105 // 00106 // ml3.copyData(lc); 00107 // 00108 // 00109 // </srcBlock> 00110 // In this example no masks are involved. See tLatticeConcat 00111 // for more examples. 00112 // </example> 00113 00114 // 00115 // <motivation> 00116 // Image concatentation is a useful enduser requirement. An object of 00117 // this class is contained by an ImageConcat object. 00118 // </motivation> 00119 00120 // <todo asof="1999/10/23"> 00121 // </todo> 00122 00123 00124 template <class T> class LatticeConcat : public MaskedLattice<T> 00125 { 00126 public: 00127 00128 // Constructor. Argument <src>axis</src> specifies the concatenation 00129 // axis (0 relative). If this is one more than the number of axes 00130 // in the input lattices (set with function <src>setLattice</src>) 00131 // then the resultant concatenated lattice has dimension 00132 // one greater than that the input lattices. 00133 // Argument <src>tempClose</src> specifies whether you wish 00134 // all internal lattice copies to be 00135 // opened/closed on demand, rather than just being left open. 00136 // This prevents open file limits being reached 00137 LatticeConcat (uInt axis, Bool tempClose=True); 00138 00139 // Default constructor. Sets the concatenation axis to 0 00140 // and tempClose is True 00141 LatticeConcat (); 00142 00143 // Copy constructor (reference semantics) 00144 LatticeConcat(const LatticeConcat<T> &other); 00145 00146 // Destructor 00147 virtual ~LatticeConcat (); 00148 00149 // Assignment operator (reference semantics) 00150 LatticeConcat<T> &operator=(const LatticeConcat<T> &other); 00151 00152 // Adds a clone of the lattice to the list to be concatenated. 00153 // Exception thrown if lattices are incompatible 00154 void setLattice (MaskedLattice<T>& lattice); 00155 00156 // Return the number of lattices set so far 00157 uInt nlattices() const 00158 {return lattices_p.nelements();} 00159 00160 // Returns the current concatenation axis (0 relative) 00161 uInt axis () const 00162 {return axis_p;} 00163 00164 // Set the tempClose state. 00165 void setTempClose (Bool tmpClose) 00166 { tempClose_p = tmpClose; } 00167 00168 // Returns the tempClose constructor state 00169 Bool isTempClose () const 00170 {return tempClose_p;} 00171 00172 // Returns the number of dimensions of the *input* lattices (may be different 00173 // by one from output lattice). Returns 0 if none yet set. 00174 uInt latticeDim() const; 00175 00176 // Return pointer for specified lattice. Do not delete it. 00177 MaskedLattice<T>* lattice(uInt i) const 00178 { return lattices_p[i]; } 00179 00180 // Handle the (un)locking and syncing, etc. 00181 // <group> 00182 virtual Bool lock (FileLocker::LockType, uInt nattempts); 00183 virtual void unlock(); 00184 virtual Bool hasLock (FileLocker::LockType) const; 00185 virtual void resync(); 00186 virtual void flush(); 00187 virtual void tempClose(); 00188 virtual void reopen(); 00189 // </group> 00190 00191 // Close/reopen a specific lattice. It is your responsibility to leave the 00192 // LatticeConcat object in a fully closed state. So always pair 00193 // a reopen with a tempClose. 00194 // <group> 00195 void tempClose(uInt which); 00196 void reopen(uInt which); 00197 // </group> 00198 00199 // Name. Since many lattices may go into the concatenation, the name 00200 // is rather meaningless. Returns the string "Concatenation :" 00201 virtual String name (Bool stripPath=False) const; 00202 00203 // Make a copy of the derived object (reference semantics). 00204 virtual LatticeConcat<T>* cloneML() const; 00205 00206 // Has the object really a mask? 00207 virtual Bool isMasked() const; 00208 00209 // Get the region used (always returns 0). 00210 virtual const LatticeRegion* getRegionPtr() const; 00211 00212 // If all of the underlying lattices are writable returns True 00213 virtual Bool isWritable() const; 00214 00215 // Does the lattice have a pixelmask? 00216 virtual Bool hasPixelMask() const; 00217 00218 // Get access to the pixelmask. 00219 // An exception is thrown if the lattice does not have a pixelmask 00220 // <group> 00221 virtual const Lattice<Bool>& pixelMask() const; 00222 virtual Lattice<Bool>& pixelMask(); 00223 // </group> 00224 00225 // Find the shape that the concatenated lattice will be. 00226 // Returns a null IPosition if function setLattice has not yet 00227 // been called 00228 virtual IPosition shape () const; 00229 00230 // Return the best cursor shape. This isn't very meaningful for a LatticeConcat 00231 // Lattice since it isn't on disk ! But if you do copy it out, this is 00232 // what you should use. The maxPixels aregument is ignored. 00233 virtual IPosition doNiceCursorShape (uInt maxPixels) const; 00234 00235 // Do the actual get of the data. 00236 // The return value is always False, thus the buffer does not reference 00237 // another array. Generally the user should use function getSlice 00238 virtual Bool doGetSlice (Array<T>& buffer, const Slicer& section); 00239 00240 // Do the actual get of the mask data. 00241 // The return value is always False, thus the buffer does not reference 00242 // another array. Generally the user should use function getMaskSlice 00243 virtual Bool doGetMaskSlice (Array<Bool>& buffer, const Slicer& section); 00244 00245 // Do the actual put of the data into the Lattice. This will change the underlying 00246 // lattices (if they are writable) that were used to create the 00247 // LatticeConcat object. It throws an exception if not writable. 00248 // Generally the user should use function putSlice 00249 virtual void doPutSlice (const Array<T>& sourceBuffer, 00250 const IPosition& where, 00251 const IPosition& stride); 00252 00253 00254 private: 00255 PtrBlock<MaskedLattice<T>* > lattices_p; 00256 uInt axis_p; 00257 IPosition shape_p; 00258 Bool isMasked_p, dimUpOne_p, tempClose_p; 00259 LatticeConcat<Bool>* pPixelMask_p; 00260 // 00261 void checkAxis(uInt axis, uInt ndim) const; 00262 // 00263 void setup1 (IPosition& blc, IPosition& trc, IPosition& stride, 00264 IPosition& blc2, IPosition& trc2, 00265 IPosition& blc3, IPosition& trc3, IPosition& stride3, 00266 const Slicer& section); 00267 Slicer setup2 (Bool& first, IPosition& blc2, IPosition& trc2, 00268 Int shape2, Int axis, const IPosition& blc, 00269 const IPosition& trc, const IPosition& stride, Int start); 00270 Bool getSlice1 (Array<T>& buffer, const Slicer& section, 00271 uInt nLattices); 00272 Bool getSlice2 (Array<T>& buffer, const Slicer& section, 00273 uInt nLattices); 00274 Bool putSlice1 (const Array<T>& buffer, const IPosition& where, 00275 const IPosition& stride, uInt nLattices); 00276 00277 Bool putSlice2 (const Array<T>& buffer, const IPosition& where, 00278 const IPosition& stride, uInt nLattices); 00279 Bool getMaskSlice1 (Array<Bool>& buffer, const Slicer& section, 00280 uInt nLattices); 00281 Bool getMaskSlice2 (Array<Bool>& buffer, const Slicer& section, 00282 uInt nLattices); 00283 }; 00284 00285 00286 00287 } //# NAMESPACE CASACORE - END 00288 00289 #ifndef CASACORE_NO_AUTO_TEMPLATES 00290 #include <casacore/lattices/Lattices/LatticeConcat.tcc> 00291 #endif //# CASACORE_NO_AUTO_TEMPLATES 00292 #endif