Main Page | Modules | Alphabetical List | Class List | File List | Class Members | File Members

fitshandle.h

Go to the documentation of this file.
00001 /*
00002  *  This file is part of Healpix_cxx.
00003  *
00004  *  Healpix_cxx is free software; you can redistribute it and/or modify
00005  *  it under the terms of the GNU General Public License as published by
00006  *  the Free Software Foundation; either version 2 of the License, or
00007  *  (at your option) any later version.
00008  *
00009  *  Healpix_cxx is distributed in the hope that it will be useful,
00010  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00011  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00012  *  GNU General Public License for more details.
00013  *
00014  *  You should have received a copy of the GNU General Public License
00015  *  along with Healpix_cxx; if not, write to the Free Software
00016  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
00017  *
00018  *  For more information about HEALPix, see http://healpix.jpl.nasa.gov
00019  */
00020 
00021 /*
00022  *  Healpix_cxx is being developed at the Max-Planck-Institut fuer Astrophysik
00023  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
00024  *  (DLR).
00025  */
00026 
00027 /*! \file fitshandle.h
00028  *  Declaration of the FITS I/O helper class used by LevelS
00029  *
00030  *  Copyright (C) 2002, 2003, 2004, 2005 Max-Planck-Society
00031  *  \author Martin Reinecke
00032  */
00033 
00034 #ifndef PLANCK_FITSHANDLE_H
00035 #define PLANCK_FITSHANDLE_H
00036 
00037 #include <string>
00038 #include <vector>
00039 #include "fitsio.h"
00040 #include "arr.h"
00041 #include "datatypes.h"
00042 
00043 /*! \defgroup fitsgroup FITS-related functionality */
00044 /*! \{ */
00045 
00046 template<typename T> struct FITSUTIL {};
00047 
00048 template<> struct FITSUTIL<int>
00049   { enum { DTYPE=TINT }; };
00050 template<> struct FITSUTIL<long>
00051   { enum { DTYPE=TLONG }; };
00052 template<> struct FITSUTIL<float>
00053   { enum { DTYPE=TFLOAT }; };
00054 template<> struct FITSUTIL<double>
00055   { enum { DTYPE=TDOUBLE }; };
00056 
00057 /*! Class containing information about a single column in a FITS table. */
00058 class fitscolumn
00059   {
00060   private:
00061     std::string name_, unit_;
00062     long repcount_;
00063     int type_;
00064 
00065   public:
00066     /*! Creates a \a fitscolumn with name \a nm, unit \a un, a repetition
00067         count of \a rc, and a FITS type code of \a tp. */
00068     fitscolumn (const std::string &nm, const std::string &un, long rc, int tp)
00069       : name_(nm), unit_(un), repcount_(rc), type_(tp) {}
00070 
00071     /*! Returns the column name. */
00072     const std::string &name() const {return name_;}
00073     /*! Returns the column unit string. */
00074     const std::string &unit() const {return unit_;}
00075     /*! Returns the repetition count of the column. */
00076     long repcount() const {return repcount_;}
00077     /*! Returns the FITS type code of the column. */
00078     int type() const {return type_;}
00079   };
00080 
00081 /*! Class for performing I/O from/to FITS files. */
00082 class fitshandle
00083   {
00084   private:
00085     enum { INVALID = -4711 };
00086 
00087     int status;
00088     fitsfile *fptr;
00089     int hdutype_, bitpix_;
00090     std::vector<long> axes_;
00091     std::vector<fitscolumn> columns_;
00092     long nrows_;
00093 
00094     void check_errors();
00095 
00096     void clean_data();
00097     void clean_all();
00098 
00099     void assert_connected (const std::string &func) const
00100       {
00101       planck_assert (hdutype_!=INVALID,
00102         func + ": not connected to a HDU");
00103       }
00104     void assert_table_hdu (const std::string &func, unsigned int col) const
00105       {
00106       planck_assert ((hdutype_==ASCII_TBL) || (hdutype_==BINARY_TBL),
00107         func + ": HDU is not a table");
00108       planck_assert (col>0 && col<=columns_.size(),
00109         func + ": column number out of range");
00110       }
00111     void assert_image_hdu (const std::string &func) const
00112       {
00113       planck_assert ((hdutype_==IMAGE_HDU), func + ": HDU is not an image");
00114       }
00115 
00116     void init_image();
00117     void init_asciitab();
00118     void init_bintab();
00119     void init_data();
00120 
00121     void check_key_present(const std::string &name);
00122 
00123     void read_col (int colnum, void *data, long ndata, int dtype,
00124                    long offset);
00125     void write_col (int colnum, const void *data, long ndata, int dtype,
00126                    long offset);
00127 
00128   public:
00129     /*! the list of modes in which a \a fitshandle can be opened. */
00130     typedef enum { CREATE, /*!< the file must not yet exist */
00131                    OPEN    /*!< the file must already exist */
00132                  } openmethod;
00133 
00134     /*! \name File-level access and manipulation. */
00135     /*! \{ */
00136 
00137     /*! Creates an unconnected \a fitshandle. */
00138     fitshandle ()
00139       : status(0), fptr(0), hdutype_(INVALID), bitpix_(INVALID), nrows_(0) {}
00140     /*! Creates a \a fitshandle connected to file \a fname.
00141         If \a rwmode == READONLY, no writing access is permitted; if it is
00142         READWRITE, reading and writing can be performed. */
00143     fitshandle (const std::string &fname, openmethod mode=OPEN,
00144       int rwmode=READONLY)
00145       : status(0), fptr(0), hdutype_(INVALID), bitpix_(INVALID), nrows_(0)
00146       {
00147       if (mode==OPEN)
00148         open (fname, rwmode);
00149       else
00150         create (fname);
00151       }
00152     /*! Creates a \a fitshandle connected to file \a fname and jumps directly
00153         to the HDU with the number \a hdunum.
00154         If \a rwmode == READONLY, no writing access is permitted; if it is
00155         READWRITE, reading and writing can be performed. */
00156     fitshandle (const std::string &fname, int hdunum, int rwmode=READONLY)
00157       : status(0), fptr(0), hdutype_(INVALID), bitpix_(INVALID), nrows_(0)
00158       {
00159       open (fname, rwmode);
00160       goto_hdu (hdunum);
00161       }
00162 
00163     /*! Performs all necessary cleanups. */
00164     ~fitshandle() { clean_all(); }
00165 
00166     /*! Connects to the file \a fname.
00167         If \a rwmode == READONLY, no writing access is permitted; if it is
00168         READWRITE, reading and writing can be performed. */
00169     void open (const std::string &fname, int rwmode=READONLY);
00170     /*! Creates the file \a fname and connects to it. */
00171     void create (const std::string &fname);
00172     /*! Closes the current file. */
00173     void close () { clean_all(); }
00174     /*! Jumps to the HDU with the absolute number \a hdu. */
00175     void goto_hdu (int hdu);
00176     /*! Asserts that the PDMTYPE of the current HDU is \a pdmtype. */
00177     void assert_pdmtype (const std::string &pdmtype);
00178     /*! Inserts a binary table described by \a cols. */
00179     void insert_bintab (const std::vector<fitscolumn> &cols);
00180     /*! Inserts an ASCII table described by \a cols. The width of the
00181         columns is chosen automatically, in a way that avoids truncation. */
00182     void insert_asctab (const std::vector<fitscolumn> &cols);
00183     /*! Inserts a FITS image with the type given by \a btpx and dimensions
00184         given by \a Axes. */
00185     void insert_image (int btpx, const std::vector<long> &Axes);
00186     /*! Inserts a 2D FITS image with the type given by \a btpx, whose
00187         contents are given in \a data. */
00188     template<typename T>
00189       void insert_image (int btpx, const arr2<T> &data);
00190 
00191     /*! \} */
00192 
00193     /*! \name Information about the current HDU */
00194     /*! \{ */
00195 
00196     /*! If the current HDU is an image, returns the BITPIX parameter of that
00197         image, else throws an exception. */
00198     int bitpix() const
00199       {
00200       assert_image_hdu ("fitshandle::bitpix()");
00201       return bitpix_;
00202       }
00203     /*! Returns the FITS type code for the current HDU. */
00204     int hdutype() const {return hdutype_;}
00205     /*! Returns the dimensions of the current image. */
00206     const std::vector<long> &axes() const
00207       {
00208       assert_image_hdu ("fitshandle::axes()");
00209       return axes_;
00210       }
00211     /*! Returns the name of column \a #i. */
00212     const std::string &colname(int i) const
00213       {
00214       assert_table_hdu("fitshandle::colname()",i);
00215       return columns_[i-1].name();
00216       }
00217     /*! Returns the unit of column \a #i. */
00218     const std::string &colunit(int i) const
00219       {
00220       assert_table_hdu("fitshandle::colunit()",i);
00221       return columns_[i-1].unit();
00222       }
00223     /*! Returns repetition count of column \a #i. */
00224     long repcount(int i) const
00225       {
00226       assert_table_hdu("fitshandle::repcount()",i);
00227       return columns_[i-1].repcount();
00228       }
00229     /*! Returns the FITS type code for column \a #i. */
00230     int coltype(int i) const
00231       {
00232       assert_table_hdu("fitshandle::coltype()",i);
00233       return columns_[i-1].type();
00234       }
00235     /*! Returns the number of columns in the current table. */
00236     int ncols() const
00237       {
00238       assert_table_hdu("fitshandle::ncols()",1);
00239       return columns_.size();
00240       }
00241     /*! Returns the number of rows in the current table. */
00242     int nrows() const
00243       {
00244       assert_table_hdu("fitshandle::nrows()",1);
00245       return nrows_;
00246       }
00247     /*! Returns the total number of elements (nrows*repcount)
00248         in column \a #i. */
00249     long nelems(int i) const
00250       {
00251       assert_table_hdu("fitshandle::nelems()",i);
00252       if (columns_[i-1].type()==TSTRING) return nrows_;
00253       return nrows_*columns_[i-1].repcount();
00254       }
00255 
00256     /*! \} */
00257 
00258     /*! \name Keyword-handling methods */
00259     /*! \{ */
00260 
00261     /*! Copies all header keywords from the current HDU of \a orig to
00262         the current HDU of \a *this. */
00263     void copy_header (const fitshandle &orig);
00264     /*! Copies all header keywords from the current HDU of \a orig to
00265         the current HDU of \a *this, prepending a HISTORY keyword to
00266         every line. */
00267     void copy_historified_header (const fitshandle &orig);
00268 
00269     /*! Adds a new header line consisting of \a key, \a value and
00270         \a comment. */
00271     template<typename T> void add_key (const std::string &name, const T &value,
00272       const std::string &comment="");
00273     /*! Updates \a key with \a value and \a comment. */
00274     template<typename T> void update_key (const std::string &name,
00275       const T &value, const std::string &comment="");
00276     /*! Deletes \a key from the header. */
00277     void delete_key (const std::string &name);
00278     /*! Adds \a comment as a comment line. */
00279     void add_comment (const std::string &comment);
00280     /*! Reads the value belonging to \a key and returns it in \a value. */
00281     template<typename T> void get_key (const std::string &name, T &value);
00282     /*! Returms the value belonging to \a key. */
00283     template<typename T> T get_key (const std::string &name)
00284       { T tmp; get_key(name, tmp); return tmp; }
00285     /*! Returns \a true if \a key is present, else \a false. */
00286     bool key_present (const std::string &name);
00287 
00288     /*! \} */
00289 
00290     /*! \name Methods for table data I/O */
00291     /*! \{ */
00292 
00293     void read_column_raw_void
00294       (int colnum, void *data, int type, long num, long offset=0);
00295     /*! Copies \a num elements from column \a colnum to the memory pointed
00296         to by \a data, starting at offset \a offset in the column. */
00297     template<typename T> void read_column_raw
00298       (int colnum, T *data, long num, long offset=0)
00299       { read_column_raw_void (colnum, data, typehelper<T>::id, num, offset); }
00300     /*! Fills \a data with elements from column \a colnum,
00301         starting at offset \a offset in the column. */
00302     template<typename T> void read_column
00303       (int colnum, arr<T> &data, long offset=0)
00304       { read_column_raw (colnum, &(data[0]), data.size(), offset); }
00305     /*! Reads the element \a #offset from column \a colnum into \a data. */
00306     template<typename T> void read_column
00307       (int colnum, T &data, long offset=0)
00308       { read_column_raw (colnum, &data, 1, offset); }
00309     /* Reads the whole column \a colnum into \a data (which is resized
00310        accordingly). */
00311     template<typename T> void read_entire_column (int colnum, arr<T> &data)
00312       { data.alloc(nelems(colnum)); read_column (colnum, data); }
00313 
00314 
00315     void write_column_raw_void
00316       (int colnum, const void *data, int type, long num, long offset=0);
00317     /*! Copies \a num elements from the memory pointed to by \a data to the
00318         column \a colnum, starting at offset \a offset in the column. */
00319     template<typename T> void write_column_raw
00320       (int colnum, const T *data, long num, long offset=0)
00321       { write_column_raw_void (colnum, data, typehelper<T>::id, num, offset); }
00322     /*! Copies all elements from \a data to the
00323         column \a colnum, starting at offset \a offset in the column. */
00324     template<typename T> void write_column
00325       (int colnum, const arr<T> &data, long offset=0)
00326       { write_column_raw (colnum, &(data[0]), data.size(), offset); }
00327     /*! Copies \a data to the column \a colnum, at the position \a offset. */
00328     template<typename T> void write_column
00329       (int colnum, const T &data, long offset=0)
00330       { write_column_raw (colnum, &data, 1, offset); }
00331 
00332     /*! \} */
00333 
00334     /*! \name Methods for image data I/O */
00335     /*! \{ */
00336 
00337     /*! Reads the current image into \a data, which is resized accordingly. */
00338     template<typename T> void read_image (arr2<T> &data);
00339     /*! Reads a partial image, whose dimensions are given by the dimensions
00340         of \a data, into data. The starting pixel indices are given by
00341         \a xl and \a yl. */
00342     template<typename T> void read_subimage (arr2<T> &data, int xl, int yl);
00343     /*! Fills \a data with values from the image, starting at the offset
00344         \a offset in the image. The image is treated as a one-dimensional
00345         array. */
00346     template<typename T> void read_subimage (arr<T> &data, long offset=0);
00347     /*! Writes \a data into the current image. \a data must have the same
00348         dimensions as specified in the HDU. */
00349     template<typename T> void write_image (const arr2<T> &data);
00350     /*! Copies \a data to the image, starting at the offset
00351         \a offset in the image. The image is treated as a one-dimensional
00352         array. */
00353     template<typename T> void write_subimage (const arr<T> &data,
00354       long offset=0);
00355 
00356     /*! \} */
00357 
00358     void add_healpix_keys (int datasize);
00359   };
00360 
00361 /*! \} */
00362 
00363 // announce the specialisations
00364 template<> void fitshandle::add_key(const std::string &name,
00365   const bool &value, const std::string &comment);
00366 template<> void fitshandle::add_key (const std::string &name,
00367   const std::string &value, const std::string &comment);
00368 template<> void fitshandle::update_key(const std::string &name,
00369   const bool &value, const std::string &comment);
00370 template<> void fitshandle::update_key (const std::string &name,
00371   const std::string &value, const std::string &comment);
00372 template<> void fitshandle::get_key(const std::string &name,bool &value);
00373 template<> void fitshandle::get_key (const std::string &name,
00374   std::string &value);
00375 
00376 #endif

Generated on Fri Jul 8 09:37:14 2005 for LevelS C++ support library