CCfits 2.3
|
00001 // Astrophysics Science Division, 00002 // NASA/ Goddard Space Flight Center 00003 // HEASARC 00004 // http://heasarc.gsfc.nasa.gov 00005 // e-mail: ccfits@legacy.gsfc.nasa.gov 00006 // 00007 // Original author: Ben Dorman 00008 00009 #ifndef COLUMNT_H 00010 #define COLUMNT_H 00011 00012 #ifdef _MSC_VER 00013 #include "MSconfig.h" 00014 #endif 00015 00016 #include "ColumnData.h" 00017 #include "ColumnVectorData.h" 00018 #include "FITSUtil.h" 00019 #include <typeinfo> 00020 #include <vector> 00021 #include <algorithm> 00022 #include "NewKeyword.h" 00023 00024 #ifdef SSTREAM_DEFECT 00025 # include <strstream> 00026 #else 00027 # include <sstream> 00028 #endif 00029 00030 00031 // by design, if the data are not read yet we will return an exception. 00032 // here the test is if the entire column has already been read. 00033 using std::complex; 00034 using std::valarray; 00035 00036 // get specified elements of a scalar column. These two functions allow the 00037 // user to return either a vector or a valarray depending on the input container. 00038 00039 namespace CCfits 00040 { 00041 template <typename S> 00042 void Column::read(std::vector<S>& vals, long first, long last) 00043 { 00044 read(vals,first,last,static_cast<S*>(0)); 00045 } 00046 00047 00048 template <typename S> 00049 void Column::read(std::vector<S>& vals, long first, long last, S* nullValue) 00050 { 00051 // problem: S does not give the type of the Column, but the return type, 00052 // so the user must specify this. 00053 parent()->makeThisCurrent(); 00054 long nelements = numberOfElements(first,last); 00055 00056 if (ColumnData<S>* col = dynamic_cast<ColumnData<S>*>(this)) 00057 { 00058 // fails if user requested outputType different from input type. 00059 00060 00061 if (!isRead()) col->readColumnData(first,nelements,nullValue); 00062 // scalar column with vector output can just be assigned. 00063 FITSUtil::fill(vals,col->data(),first,last); 00064 } 00065 else 00066 { 00067 FITSUtil::MatchType<S> outputType; 00068 if ( outputType() == type() ) 00069 { 00070 // in this case user tried to read vector data from scalar, 00071 // (i.e. first argument was vector<valarray<S> >. 00072 // since the cast won't fail on template parameter grounds. 00073 throw Column::WrongColumnType(name()); 00074 } 00075 00076 try 00077 { 00078 // about exceptions. The dynamic_casts could throw 00079 // std::bad_cast. If this happens something is seriously 00080 // wrong since the Column stores the value of type() 00081 // appropriate to each of the casts on construction. 00082 // 00083 // the InvalidDataType exception should not be possible. 00084 if ( type() == Tdouble ) 00085 { 00086 ColumnData<double>& col 00087 = dynamic_cast<ColumnData<double>&>(*this); 00088 if (!isRead()) col.readColumnData(first,nelements); 00089 FITSUtil::fill(vals,col.data(),first,last); 00090 00091 } 00092 else if (type() == Tfloat) 00093 { 00094 ColumnData<float>& col 00095 = dynamic_cast<ColumnData<float>&>(*this); 00096 if (!isRead()) col.readColumnData(first,nelements); 00097 FITSUtil::fill(vals,col.data(),first,last); 00098 } 00099 else if (type() == Tint) 00100 { 00101 int nullVal(0); 00102 if (nullValue) nullVal = static_cast<int>(*nullValue); 00103 ColumnData<int>& col 00104 = dynamic_cast<ColumnData<int>&>(*this); 00105 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00106 FITSUtil::fill(vals,col.data(),first,last); 00107 } 00108 else if (type() == Tshort) 00109 { 00110 short nullVal(0); 00111 if (nullValue) nullVal = static_cast<short>(*nullValue); 00112 ColumnData<short>& col 00113 = dynamic_cast<ColumnData<short>&>(*this); 00114 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00115 FITSUtil::fill(vals,col.data(),first,last); 00116 } 00117 else if (type() == Tlong) 00118 { 00119 long nullVal(0); 00120 if (nullValue) nullVal = static_cast<long>(*nullValue); 00121 ColumnData<long>& col 00122 = dynamic_cast<ColumnData<long>&>(*this); 00123 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00124 FITSUtil::fill(vals,col.data(),first,last); 00125 } 00126 else if (type() == Tlonglong) 00127 { 00128 LONGLONG nullVal(0); 00129 if (nullValue) nullVal = static_cast<LONGLONG>(*nullValue); 00130 ColumnData<LONGLONG>& col 00131 = dynamic_cast<ColumnData<LONGLONG>&>(*this); 00132 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00133 FITSUtil::fill(vals,col.data(),first,last); 00134 } 00135 else if (type() == Tlogical) 00136 { 00137 bool nullVal(0); 00138 if (nullValue) nullVal = static_cast<bool>(*nullValue); 00139 ColumnData<bool>& col 00140 = dynamic_cast<ColumnData<bool>&>(*this); 00141 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00142 FITSUtil::fill(vals,col.data(),first,last); 00143 } 00144 else if (type() == Tbit || type() == Tbyte) 00145 { 00146 unsigned char nullVal(0); 00147 if (nullValue) nullVal = static_cast<unsigned char>(*nullValue); 00148 ColumnData<unsigned char>& col 00149 = dynamic_cast<ColumnData<unsigned char>&>(*this); 00150 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00151 FITSUtil::fill(vals,col.data(),first,last); 00152 } 00153 else if (type() == Tushort) 00154 { 00155 unsigned short nullVal(0); 00156 if (nullValue) nullVal= static_cast<unsigned short>(*nullValue); 00157 ColumnData<unsigned short>& col 00158 = dynamic_cast<ColumnData<unsigned short>&>(*this); 00159 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00160 FITSUtil::fill(vals,col.data(),first,last); 00161 } 00162 else if (type() == Tuint) 00163 { 00164 unsigned int nullVal(0); 00165 if (nullValue) nullVal = static_cast<unsigned int>(*nullValue); 00166 ColumnData<unsigned int>& col 00167 = dynamic_cast<ColumnData<unsigned int>&>(*this); 00168 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00169 FITSUtil::fill(vals,col.data(),first,last); 00170 } 00171 else if (type() == Tulong) 00172 { 00173 unsigned long nullVal(0); 00174 if (nullValue) nullVal = static_cast<unsigned long>(*nullValue); 00175 ColumnData<unsigned long>& col 00176 = dynamic_cast<ColumnData<unsigned long>&>(*this); 00177 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00178 FITSUtil::fill(vals,col.data(),first,last); 00179 } 00180 else 00181 { 00182 throw InvalidDataType(name()); 00183 00184 } 00185 00186 } 00187 catch (std::bad_cast) 00188 { 00189 throw WrongColumnType(name()); 00190 } 00191 } 00192 00193 } 00194 00195 template <typename S> 00196 void Column::read(std::valarray<S>& vals, long first, long last) 00197 { 00198 read(vals,first,last,static_cast<S*>(0)); 00199 } 00200 00201 00202 template <typename S> 00203 void Column::read(std::valarray<S>& vals, long first, long last, S* nullValue) 00204 { 00205 // require the whole scalar column to have been read. 00206 00207 00208 long nelements = numberOfElements(first,last); 00209 parent()->makeThisCurrent(); 00210 if ( ColumnData<S>* col = dynamic_cast<ColumnData<S>*>(this)) 00211 { 00212 // fails if user requested outputType different from input type. 00213 00214 00215 if (!isRead()) col->readColumnData(first,nelements,nullValue); 00216 FITSUtil::fill(vals,col->data(),first,last); 00217 00218 } 00219 else 00220 { 00221 FITSUtil::MatchType<S> outputType; 00222 if ( outputType() == type() ) 00223 { 00224 // in this case user tried to read vector data from scalar, 00225 // (i.e. first argument was vector<valarray<S> >. 00226 // since the cast won't fail on template parameter grounds. 00227 throw Column::WrongColumnType(name()); 00228 } 00229 00230 try 00231 { 00232 // about exceptions. The dynamic_casts could throw 00233 // std::bad_cast. If this happens something is seriously 00234 // wrong since the Column stores the value of type() 00235 // appropriate to each of the casts on construction. 00236 // 00237 // the InvalidDataType exception should not be possible. 00238 if ( type() == Tdouble ) 00239 { 00240 ColumnData<double>& col 00241 = dynamic_cast<ColumnData<double>&>(*this); 00242 if (!isRead()) col.readColumnData(first,nelements); 00243 FITSUtil::fill(vals,col.data(),first,last); 00244 } 00245 else if (type() == Tfloat) 00246 { 00247 ColumnData<float>& col 00248 = dynamic_cast<ColumnData<float>&>(*this); 00249 if (!isRead()) col.readColumnData(first,nelements); 00250 FITSUtil::fill(vals,col.data(),first,last); 00251 } 00252 else if (type() == Tint) 00253 { 00254 int nullVal(0); 00255 if (nullValue) nullVal = static_cast<int>(*nullValue); 00256 ColumnData<int>& col 00257 = dynamic_cast<ColumnData<int>&>(*this); 00258 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00259 FITSUtil::fill(vals,col.data(),first,last); 00260 } 00261 else if (type() == Tshort) 00262 { 00263 short nullVal(0); 00264 if (nullValue) nullVal = static_cast<short>(*nullValue); 00265 ColumnData<short>& col 00266 = dynamic_cast<ColumnData<short>&>(*this); 00267 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00268 FITSUtil::fill(vals,col.data(),first,last); 00269 } 00270 else if (type() == Tlong) 00271 { 00272 long nullVal(0); 00273 if (nullValue) nullVal = static_cast<long>(*nullValue); 00274 ColumnData<long>& col 00275 = dynamic_cast<ColumnData<long>&>(*this); 00276 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00277 FITSUtil::fill(vals,col.data(),first,last); 00278 } 00279 else if (type() == Tlonglong) 00280 { 00281 LONGLONG nullVal(0); 00282 if (nullValue) nullVal = static_cast<LONGLONG>(*nullValue); 00283 ColumnData<LONGLONG>& col 00284 = dynamic_cast<ColumnData<LONGLONG>&>(*this); 00285 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00286 FITSUtil::fill(vals,col.data(),first,last); 00287 } 00288 else if (type() == Tlogical) 00289 { 00290 bool nullVal(0); 00291 if (nullValue) nullVal = static_cast<bool>(*nullValue); 00292 ColumnData<bool>& col 00293 = dynamic_cast<ColumnData<bool>&>(*this); 00294 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00295 FITSUtil::fill(vals,col.data(),first,last); 00296 } 00297 else if (type() == Tbit || type() == Tbyte) 00298 { 00299 unsigned char nullVal(0); 00300 if (nullValue) nullVal = static_cast<unsigned char>(*nullValue); 00301 ColumnData<unsigned char>& col 00302 = dynamic_cast<ColumnData<unsigned char>&>(*this); 00303 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00304 FITSUtil::fill(vals,col.data(),first,last); 00305 } 00306 else if (type() == Tushort) 00307 { 00308 unsigned short nullVal(0); 00309 if (nullValue) nullVal 00310 = static_cast<unsigned short>(*nullValue); 00311 ColumnData<unsigned short>& col 00312 = dynamic_cast<ColumnData<unsigned short>&>(*this); 00313 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00314 FITSUtil::fill(vals,col.data(),first,last); 00315 } 00316 else if (type() == Tuint) 00317 { 00318 unsigned int nullVal(0); 00319 if (nullValue) nullVal 00320 = static_cast<unsigned int>(*nullValue); 00321 ColumnData<unsigned int>& col 00322 = dynamic_cast<ColumnData<unsigned int>&>(*this); 00323 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00324 FITSUtil::fill(vals,col.data(),first,last); 00325 } 00326 else if (type() == Tulong) 00327 { 00328 unsigned long nullVal(0); 00329 if (nullValue) nullVal 00330 = static_cast<unsigned long>(*nullValue); 00331 ColumnData<unsigned long>& col 00332 = dynamic_cast<ColumnData<unsigned long>&>(*this); 00333 if (!isRead()) col.readColumnData(first,nelements,&nullVal); 00334 FITSUtil::fill(vals,col.data(),first,last); 00335 } 00336 else 00337 { 00338 throw InvalidDataType(name()); 00339 00340 } 00341 00342 } 00343 catch (std::bad_cast) 00344 { 00345 throw WrongColumnType(name()); 00346 } 00347 } 00348 00349 } 00350 00351 // get a single row from a vector column. There's no default row number, must 00352 // be specified. 00353 template <typename S> 00354 void Column::read(std::valarray<S>& vals, long row) 00355 { 00356 read(vals,row,static_cast<S*>(0)); 00357 } 00358 00359 00360 template <typename S> 00361 void Column::read(std::valarray<S>& vals, long row, S* nullValue) 00362 { 00363 if (row > parent()->rows()) 00364 { 00365 throw Column::InvalidRowNumber(name()); 00366 } 00367 parent()->makeThisCurrent(); 00368 // isRead() returns true if the data were read in the ctor. 00369 if ( ColumnVectorData<S>* col = dynamic_cast<ColumnVectorData<S>*>(this)) 00370 { 00371 // fails if user requested outputType different from input type. 00372 00373 00374 00375 // input and output are both valarrays. Since one should not 00376 // be able to call a constructor for a non-numeric valarray type, 00377 // there shouldn't be any InvalidType problems. However, there 00378 // is still the vector/scalar possibility and the implicit 00379 // conversion request to deal with. 00380 00381 if (!isRead()) col->readRow(row,nullValue); 00382 FITSUtil::fill(vals,col->data(row)); 00383 } 00384 else 00385 { 00386 FITSUtil::MatchType<S> outputType; 00387 if ( outputType() == type() ) 00388 { 00389 // in this case user tried to read vector row from scalar column. 00390 // one could be charitable and return a valarray of size 1, 00391 // but... I'm going to throw an exception suggesting the user 00392 // might not have meant that. 00393 00394 throw Column::WrongColumnType(name()); 00395 } 00396 00397 // the InvalidDataType exception should not be possible. 00398 try 00399 { 00400 // about exceptions. The dynamic_casts could throw 00401 // std::bad_cast. If this happens something is seriously 00402 // wrong since the Column stores the value of type() 00403 // appropriate to each of the casts on construction. 00404 // 00405 // the InvalidDataType exception should not be possible. 00406 if ( type() == Tdouble || type() == VTdouble ) 00407 { 00408 ColumnVectorData<double>& col 00409 = dynamic_cast<ColumnVectorData<double>&>(*this); 00410 if (!isRead()) col.readRow(row); 00411 FITSUtil::fill(vals,col.data(row)); 00412 00413 } 00414 else if (type() == Tfloat || type() == VTfloat ) 00415 { 00416 ColumnVectorData<float>& col 00417 = dynamic_cast<ColumnVectorData<float>&>(*this); 00418 if (!isRead()) col.readRow(row); 00419 FITSUtil::fill(vals,col.data(row)); 00420 } 00421 else if (type() == Tint || type() == VTint ) 00422 { 00423 int nullVal(0); 00424 if (nullValue) nullVal = static_cast<int>(*nullValue); 00425 ColumnVectorData<int>& col 00426 = dynamic_cast<ColumnVectorData<int>&>(*this); 00427 if (!isRead()) col.readRow(row,&nullVal); 00428 FITSUtil::fill(vals,col.data(row)); 00429 } 00430 else if (type() == Tshort || type() == VTshort ) 00431 { 00432 short nullVal(0); 00433 if (nullValue) nullVal = static_cast<short>(*nullValue); 00434 ColumnVectorData<short>& col 00435 = dynamic_cast<ColumnVectorData<short>&>(*this); 00436 if (!isRead()) col.readRow(row,&nullVal); 00437 FITSUtil::fill(vals,col.data(row)); 00438 } 00439 else if (type() == Tlong || type() == VTlong ) 00440 { 00441 long nullVal(0); 00442 if (nullValue) nullVal = static_cast<long>(*nullValue); 00443 ColumnVectorData<long>& col 00444 = dynamic_cast<ColumnVectorData<long>&>(*this); 00445 if (!isRead()) col.readRow(row,&nullVal); 00446 FITSUtil::fill(vals,col.data(row)); 00447 } 00448 else if (type() == Tlonglong || type() == VTlonglong ) 00449 { 00450 LONGLONG nullVal(0); 00451 if (nullValue) nullVal = static_cast<LONGLONG>(*nullValue); 00452 ColumnVectorData<LONGLONG>& col 00453 = dynamic_cast<ColumnVectorData<LONGLONG>&>(*this); 00454 if (!isRead()) col.readRow(row,&nullVal); 00455 FITSUtil::fill(vals,col.data(row)); 00456 } 00457 else if (type() == Tlogical || type() == VTlogical ) 00458 { 00459 bool nullVal(0); 00460 if (nullValue) nullVal = static_cast<bool>(*nullValue); 00461 ColumnVectorData<bool>& col 00462 = dynamic_cast<ColumnVectorData<bool>&>(*this); 00463 if (!isRead()) col.readRow(row,&nullVal); 00464 FITSUtil::fill(vals,col.data(row)); 00465 } 00466 else if (type() == Tbit || type() == Tbyte || 00467 type() == VTbit || type() == VTbyte ) 00468 { 00469 unsigned char nullVal(0); 00470 if (nullValue) nullVal 00471 = static_cast<unsigned char>(*nullValue); 00472 ColumnVectorData<unsigned char>& col 00473 = dynamic_cast<ColumnVectorData<unsigned char>&>(*this); 00474 if (!isRead()) col.readRow(row,&nullVal); 00475 FITSUtil::fill(vals,col.data(row)); 00476 } 00477 else if (type() == Tushort || type() == VTushort) 00478 { 00479 unsigned short nullVal(0); 00480 if (nullValue) nullVal 00481 = static_cast<unsigned short>(*nullValue); 00482 ColumnVectorData<unsigned short>& col 00483 = dynamic_cast<ColumnVectorData<unsigned short>&>(*this); 00484 if (!isRead()) col.readRow(row,&nullVal); 00485 FITSUtil::fill(vals,col.data(row)); 00486 } 00487 else if (type() == Tuint || type() == VTuint) 00488 { 00489 unsigned int nullVal(0); 00490 if (nullValue) nullVal 00491 = static_cast<unsigned int>(*nullValue); 00492 ColumnVectorData<unsigned int>& col 00493 = dynamic_cast<ColumnVectorData<unsigned int>&>(*this); 00494 if (!isRead()) col.readRow(row,&nullVal); 00495 FITSUtil::fill(vals,col.data(row)); 00496 } 00497 else if (type() == Tulong || type() == VTulong) 00498 { 00499 unsigned long nullVal(0); 00500 if (nullValue) nullVal 00501 = static_cast<unsigned long>(*nullValue); 00502 ColumnVectorData<unsigned long>& col 00503 = dynamic_cast<ColumnVectorData<unsigned long>&>(*this); 00504 if (!isRead()) col.readRow(row,&nullVal); 00505 FITSUtil::fill(vals,col.data(row)); 00506 } 00507 else 00508 { 00509 throw InvalidDataType(name()); 00510 00511 } 00512 00513 } 00514 catch (std::bad_cast) 00515 { 00516 throw WrongColumnType(name()); 00517 } 00518 } 00519 } 00520 00521 template <typename S> 00522 void Column::readArrays(std::vector<std::valarray<S> >& vals, long first, long last) 00523 { 00524 readArrays(vals,first,last,static_cast<S*>(0)); 00525 } 00526 00527 template <typename S> 00528 void Column::readArrays(std::vector<std::valarray<S> >& vals, 00529 long first, long last, S* nullValue) 00530 { 00531 00532 parent()->makeThisCurrent(); 00533 // again, can only call this if the entire column has been read from disk. 00534 // user expects 1 based indexing. If 0 based indices are supplied, 00535 // add one to both ranges. 00536 long range = numberOfElements(first,last); 00537 00538 vals.resize(range); 00539 00540 00541 if ( ColumnVectorData<S>* col = dynamic_cast<ColumnVectorData<S>*>(this)) 00542 { 00543 for (int j = 0; j < range; ++j) 00544 { 00545 if (!isRead()) col->readRow(j + first,nullValue); 00546 FITSUtil::fill(vals[j],col->data(j+first)); 00547 } 00548 } 00549 else 00550 { 00551 FITSUtil::MatchType<S> outputType; 00552 if ( outputType() == type() ) 00553 { 00554 // in this case user tried to read vector data from scalar, 00555 // (i.e. first argument was vector<valarray<S> >. 00556 // since the cast won't fail on template parameter grounds. 00557 throw Column::WrongColumnType(name()); 00558 } 00559 // the InvalidDataType exception should not be possible. 00560 try 00561 { 00562 if ( type() == Tdouble || type() == VTdouble ) 00563 { 00564 ColumnVectorData<double>& col 00565 = dynamic_cast<ColumnVectorData<double>&>(*this); 00566 for (int j = 0; j < range; ++j) 00567 { 00568 if (!isRead()) col.readRow(j + first); 00569 FITSUtil::fill(vals[j],col.data(j+first)); 00570 } 00571 } 00572 else if ( type() == Tfloat || type() == VTfloat ) 00573 { 00574 ColumnVectorData<float>& col 00575 = dynamic_cast<ColumnVectorData<float>&>(*this); 00576 for (int j = 0; j < range; ++j) 00577 { 00578 if (!isRead()) col.readRow(j + first); 00579 FITSUtil::fill(vals[j],col.data(j+first)); 00580 } 00581 } 00582 else if ( type() == Tint || type() == VTint ) 00583 { 00584 int nullVal(0); 00585 if (nullValue) nullVal = static_cast<int>(*nullValue); 00586 ColumnVectorData<int>& col 00587 = dynamic_cast<ColumnVectorData<int>&>(*this); 00588 for (int j = 0; j < range; ++j) 00589 { 00590 if (!isRead()) col.readRow(j + first,&nullVal); 00591 FITSUtil::fill(vals[j],col.data(j+first)); 00592 } 00593 } 00594 else if ( type() == Tshort || type() == VTshort ) 00595 { 00596 short nullVal(0); 00597 if (nullValue) nullVal = static_cast<short>(*nullValue); 00598 ColumnVectorData<short>& col 00599 = dynamic_cast<ColumnVectorData<short>&>(*this); 00600 for (int j = 0; j < range; ++j) 00601 { 00602 if (!isRead()) col.readRow(j + first,&nullVal); 00603 FITSUtil::fill(vals[j],col.data(j+first)); 00604 } 00605 } 00606 else if ( type() == Tlong || type() == VTlong ) 00607 { 00608 long nullVal(0); 00609 if (nullValue) nullVal = static_cast<long>(*nullValue); 00610 ColumnVectorData<long>& col 00611 = dynamic_cast<ColumnVectorData<long>&>(*this); 00612 for (int j = 0; j < range; ++j) 00613 { 00614 if (!isRead()) col.readRow(j + first,&nullVal); 00615 FITSUtil::fill(vals[j],col.data(j+first)); 00616 } 00617 } 00618 else if ( type() == Tlonglong || type() == VTlonglong ) 00619 { 00620 LONGLONG nullVal(0); 00621 if (nullValue) nullVal = static_cast<LONGLONG>(*nullValue); 00622 ColumnVectorData<LONGLONG>& col 00623 = dynamic_cast<ColumnVectorData<LONGLONG>&>(*this); 00624 for (int j = 0; j < range; ++j) 00625 { 00626 if (!isRead()) col.readRow(j + first,&nullVal); 00627 FITSUtil::fill(vals[j],col.data(j+first)); 00628 } 00629 } 00630 else if ( type() == Tlogical || type() == VTlogical ) 00631 { 00632 bool nullVal(0); 00633 if (nullValue) nullVal = static_cast<bool>(*nullValue); 00634 ColumnVectorData<bool>& col 00635 = dynamic_cast<ColumnVectorData<bool>&>(*this); 00636 for (int j = 0; j < range; ++j) 00637 { 00638 if (!isRead()) col.readRow(j + first,&nullVal); 00639 FITSUtil::fill(vals[j],col.data(j+first)); 00640 } 00641 } 00642 else if (type() == Tbit || type() == Tbyte || 00643 type() == VTbit || type() == VTbyte ) 00644 { 00645 unsigned char nullVal(0); 00646 if (nullValue) nullVal 00647 = static_cast<unsigned char>(*nullValue); 00648 ColumnVectorData<unsigned char>& col 00649 = dynamic_cast<ColumnVectorData<unsigned char>&>(*this); 00650 for (int j = 0; j < range; ++j) 00651 { 00652 if (!isRead()) col.readRow(j + first,&nullVal); 00653 FITSUtil::fill(vals[j],col.data(j+first)); 00654 } 00655 } 00656 else if ( type() == Tushort || type() == VTushort ) 00657 { 00658 unsigned short nullVal(0); 00659 if (nullValue) nullVal 00660 = static_cast<unsigned short>(*nullValue); 00661 ColumnVectorData<unsigned short>& col 00662 = dynamic_cast<ColumnVectorData<unsigned short>&>(*this); 00663 for (int j = 0; j < range; ++j) 00664 { 00665 if (!isRead()) col.readRow(j + first,&nullVal); 00666 FITSUtil::fill(vals[j],col.data(j+first)); 00667 } 00668 } 00669 else if ( type() == Tuint || type() == VTuint ) 00670 { 00671 unsigned int nullVal(0); 00672 if (nullValue) nullVal 00673 = static_cast<unsigned int>(*nullValue); 00674 ColumnVectorData<unsigned int>& col 00675 = dynamic_cast<ColumnVectorData<unsigned int>&>(*this); 00676 for (int j = 0; j < range; ++j) 00677 { 00678 if (!isRead()) col.readRow(j + first,&nullVal); 00679 FITSUtil::fill(vals[j],col.data(j+first)); 00680 } 00681 } 00682 else if ( type() == Tulong || type() == VTulong ) 00683 { 00684 unsigned long nullVal(0); 00685 if (nullValue) nullVal 00686 = static_cast<unsigned long>(*nullValue); 00687 ColumnVectorData<unsigned long>& col 00688 = dynamic_cast<ColumnVectorData<unsigned long>&>(*this); 00689 for (int j = 0; j < range; ++j) 00690 { 00691 if (!isRead()) col.readRow(j + first,&nullVal); 00692 FITSUtil::fill(vals[j],col.data(j+first)); 00693 } 00694 } 00695 else 00696 { 00697 throw InvalidDataType(name()); 00698 } 00699 00700 } 00701 catch (std::bad_cast) 00702 { 00703 throw WrongColumnType(name()); 00704 00705 } 00706 00707 } 00708 } 00709 00710 template <typename S> 00711 void Column::write (const std::vector<S>& indata, long firstRow) 00712 { 00713 // nullValue is now a pointer, so this is ok. 00714 // got to cast the 0 to a pointer to S to avoid 00715 // overloading ambiguities. 00716 write(indata,firstRow,static_cast<S*>(0)); 00717 } 00718 00719 template <typename S> 00720 void Column::write (const std::valarray<S>& indata, long firstRow) 00721 { 00722 size_t n(indata.size()); 00723 std::vector<S> __tmp(n); 00724 for (size_t j = 0; j < n; ++j) __tmp[j] = indata[j]; 00725 write(__tmp,firstRow,static_cast<S*>(0)); 00726 } 00727 00728 template <typename S> 00729 void Column::write (S* indata, long nRows, long firstRow) 00730 { 00731 write(indata,nRows,firstRow,static_cast<S*>(0)); 00732 } 00733 00734 00735 template <typename S> 00736 void Column::write (const std::vector<S>& indata, long firstRow, S* nullValue) 00737 { 00738 // although underlying code needs to convert the input vector 00739 // into a C array, this must be the underlying implementation 00740 // [which the others call] because it accepts string arguments 00741 // which the version with a pointer won't. [no version that 00742 // translates to a char** argument]. 00743 00744 00745 parent()->makeThisCurrent(); 00746 firstRow = std::max(firstRow,static_cast<long>(1)); 00747 if (ColumnData<S>* col = dynamic_cast<ColumnData<S>*>(this)) 00748 { 00749 col->writeData(indata,firstRow,nullValue); 00750 } 00751 else 00752 { 00753 // alright, input data type has to be rewritten as output 00754 // data type. 00755 FITSUtil::MatchType<S> inType; 00756 if ( inType() == type()) 00757 { 00758 String msg("Incorrect call: writing to vector column "); 00759 msg += name(); 00760 msg += " requires specification of # rows or vector lengths"; 00761 throw WrongColumnType(msg); 00762 } 00763 else 00764 { 00765 if ( type() == Tdouble ) 00766 { 00767 ColumnData<double>& col 00768 = dynamic_cast<ColumnData<double>&>(*this); 00769 std::vector<double> __tmp; 00770 FITSUtil::fill(__tmp,indata,1,indata.size()); 00771 col.writeData(__tmp,firstRow); 00772 } 00773 else if ( type() == Tfloat ) 00774 { 00775 ColumnData<float>& col 00776 = dynamic_cast<ColumnData<float>&>(*this); 00777 std::vector<float> __tmp; 00778 FITSUtil::fill(__tmp,indata,1,indata.size()); 00779 col.writeData(__tmp,firstRow); 00780 } 00781 else if ( type() == Tint ) 00782 { 00783 int nullVal = 0; 00784 int* pNullVal = 0; 00785 if (nullValue) 00786 { 00787 nullVal = static_cast<int>(*nullValue); 00788 pNullVal = &nullVal; 00789 } 00790 if (nullValue) nullVal = static_cast<int>(*nullValue); 00791 ColumnData<int>& col 00792 = dynamic_cast<ColumnData<int>&>(*this); 00793 std::vector<int> __tmp; 00794 FITSUtil::fill(__tmp,indata,1,indata.size()); 00795 col.writeData(__tmp,firstRow,pNullVal); 00796 } 00797 else if ( type() == Tshort ) 00798 { 00799 short nullVal(0); 00800 short* pNullVal = 0; 00801 if (nullValue) 00802 { 00803 nullVal = static_cast<short>(*nullValue); 00804 pNullVal = &nullVal; 00805 } 00806 ColumnData<short>& col 00807 = dynamic_cast<ColumnData<short>&>(*this); 00808 std::vector<short> __tmp; 00809 FITSUtil::fill(__tmp,indata,1,indata.size()); 00810 col.writeData(__tmp,firstRow,pNullVal); 00811 } 00812 else if ( type() == Tlong ) 00813 { 00814 long nullVal(0); 00815 long* pNullVal = 0; 00816 if (nullValue) 00817 { 00818 nullVal = static_cast<long>(*nullValue); 00819 pNullVal = &nullVal; 00820 } 00821 ColumnData<long>& col 00822 = dynamic_cast<ColumnData<long>&>(*this); 00823 std::vector<long> __tmp; 00824 FITSUtil::fill(__tmp,indata,1,indata.size()); 00825 col.writeData(__tmp,firstRow,pNullVal); 00826 } 00827 else if ( type() == Tlonglong ) 00828 { 00829 LONGLONG nullVal(0); 00830 LONGLONG* pNullVal = 0; 00831 if (nullValue) 00832 { 00833 nullVal = static_cast<LONGLONG>(*nullValue); 00834 pNullVal = &nullVal; 00835 } 00836 ColumnData<LONGLONG>& col 00837 = dynamic_cast<ColumnData<LONGLONG>&>(*this); 00838 std::vector<LONGLONG> __tmp; 00839 FITSUtil::fill(__tmp,indata,1,indata.size()); 00840 col.writeData(__tmp,firstRow,pNullVal); 00841 } 00842 else if ( type() == Tlogical ) 00843 { 00844 bool nullVal(0); 00845 bool* pNullVal = 0; 00846 if (nullValue) 00847 { 00848 nullVal = static_cast<bool>(*nullValue); 00849 pNullVal = &nullVal; 00850 } 00851 ColumnData<bool>& col 00852 = dynamic_cast<ColumnData<bool>&>(*this); 00853 std::vector<bool> __tmp; 00854 FITSUtil::fill(__tmp,indata,1,indata.size()); 00855 col.writeData(__tmp,firstRow,pNullVal); 00856 } 00857 else if ( type() == Tbyte ) 00858 { 00859 unsigned char nullVal(0); 00860 unsigned char* pNullVal = 0; 00861 if (nullValue) 00862 { 00863 nullVal = static_cast<unsigned char>(*nullValue); 00864 pNullVal = &nullVal; 00865 } 00866 ColumnData<unsigned char>& col 00867 = dynamic_cast<ColumnData<unsigned char>&>(*this); 00868 std::vector<unsigned char> __tmp; 00869 FITSUtil::fill(__tmp,indata,1,indata.size()); 00870 col.writeData(__tmp,firstRow,pNullVal); 00871 } 00872 else if ( type() == Tushort ) 00873 { 00874 unsigned short nullVal(0); 00875 unsigned short* pNullVal = 0; 00876 if (nullValue) 00877 { 00878 nullVal = static_cast<unsigned short>(*nullValue); 00879 pNullVal = &nullVal; 00880 } 00881 ColumnData<unsigned short>& col 00882 = dynamic_cast<ColumnData<unsigned short>&>(*this); 00883 std::vector<unsigned short> __tmp; 00884 FITSUtil::fill(__tmp,indata,1,indata.size()); 00885 col.writeData(__tmp,firstRow,pNullVal); 00886 } 00887 else if ( type() == Tuint ) 00888 { 00889 unsigned int nullVal(0); 00890 unsigned int* pNullVal = 0; 00891 if (nullValue) 00892 { 00893 nullVal = static_cast<unsigned int>(*nullValue); 00894 pNullVal = &nullVal; 00895 } 00896 ColumnData<unsigned int>& col 00897 = dynamic_cast<ColumnData<unsigned int>&>(*this); 00898 std::vector<unsigned int> __tmp; 00899 FITSUtil::fill(__tmp,indata,1,indata.size()); 00900 col.writeData(__tmp,firstRow,pNullVal); 00901 } 00902 else if ( type() == Tulong ) 00903 { 00904 unsigned long nullVal(0); 00905 unsigned long* pNullVal = 0; 00906 if (nullValue) 00907 { 00908 nullVal = static_cast<unsigned long>(*nullValue); 00909 pNullVal = &nullVal; 00910 } 00911 ColumnData<unsigned long>& col 00912 = dynamic_cast<ColumnData<unsigned long>&>(*this); 00913 std::vector<unsigned long> __tmp; 00914 FITSUtil::fill(__tmp,indata,1,indata.size()); 00915 col.writeData(__tmp,firstRow,pNullVal); 00916 } 00917 else 00918 { 00919 throw InvalidDataType(name()); 00920 } 00921 } 00922 } 00923 } 00924 00925 00926 template <typename S> 00927 void Column::write (const std::valarray<S>& indata, long firstRow, S* nullValue) 00928 { 00929 // for scalar columns. 00930 std::vector<S> __tmp; 00931 FITSUtil::fill(__tmp,indata); 00932 write(__tmp,firstRow,nullValue); 00933 } 00934 00935 template <typename S> 00936 void Column::write (S* indata, long nRows, long firstRow, S* nullValue) 00937 { 00938 // for scalar columns, data specified with C array 00939 if (nRows <= 0) throw InvalidNumberOfRows(nRows); 00940 std::vector<S> __tmp(nRows); 00941 std::copy(&indata[0],&indata[nRows],__tmp.begin()); 00942 write(__tmp,firstRow, nullValue); 00943 00944 } 00945 00946 template <typename S> 00947 void Column::write (const std::valarray<S>& indata, const std::vector<long>& vectorLengths, 00948 long firstRow) 00949 { 00950 // variable length arrays written from an input valarray. 00951 // does not allow NULL value. 00952 00953 using std::valarray; 00954 parent()->makeThisCurrent(); 00955 firstRow = std::max(firstRow,static_cast<long>(1)); 00956 if (ColumnVectorData<S>* col = dynamic_cast<ColumnVectorData<S>*>(this)) 00957 { 00958 col->writeData(indata,vectorLengths,firstRow); 00959 } 00960 else 00961 { 00962 // alright, input data type has to be rewritten as output 00963 // data type. 00964 FITSUtil::MatchType<S> inType; 00965 if ( inType() == type()) 00966 { 00967 String msg("Incorrect call: scalar column "); 00968 msg += name(); 00969 msg += " does not have vector lengths"; 00970 throw WrongColumnType(msg); 00971 } 00972 else 00973 { 00974 if ( type() == Tdouble ) 00975 { 00976 ColumnVectorData<double>& col 00977 = dynamic_cast<ColumnVectorData<double>&>(*this); 00978 valarray<double> __tmp; 00979 FITSUtil::fill(__tmp,indata); 00980 col.writeData(__tmp,vectorLengths,firstRow); 00981 } 00982 else if ( type() == Tfloat ) 00983 { 00984 ColumnVectorData<float>& col 00985 = dynamic_cast<ColumnVectorData<float>&>(*this); 00986 valarray<float> __tmp; 00987 FITSUtil::fill(__tmp,indata); 00988 col.writeData(__tmp,vectorLengths,firstRow); 00989 } 00990 else if ( type() == Tint ) 00991 { 00992 ColumnVectorData<int>& col 00993 = dynamic_cast<ColumnVectorData<int>&>(*this); 00994 valarray<int> __tmp; 00995 FITSUtil::fill(__tmp,indata); 00996 col.writeData(__tmp,vectorLengths,firstRow); 00997 } 00998 else if ( type() == Tshort ) 00999 { 01000 ColumnVectorData<short>& col 01001 = dynamic_cast<ColumnVectorData<short>&>(*this); 01002 valarray<short> __tmp; 01003 FITSUtil::fill(__tmp,indata); 01004 col.writeData(__tmp,vectorLengths,firstRow); 01005 } 01006 else if ( type() == Tlong ) 01007 { 01008 ColumnVectorData<long>& col 01009 = dynamic_cast<ColumnVectorData<long>&>(*this); 01010 valarray<long> __tmp; 01011 FITSUtil::fill(__tmp,indata); 01012 col.writeData(__tmp,vectorLengths,firstRow); 01013 } 01014 else if ( type() == Tlonglong ) 01015 { 01016 ColumnVectorData<LONGLONG>& col 01017 = dynamic_cast<ColumnVectorData<LONGLONG>&>(*this); 01018 valarray<LONGLONG> __tmp; 01019 FITSUtil::fill(__tmp,indata); 01020 col.writeData(__tmp,vectorLengths,firstRow); 01021 } 01022 else if ( type() == Tlogical ) 01023 { 01024 ColumnVectorData<bool>& col 01025 = dynamic_cast<ColumnVectorData<bool>&>(*this); 01026 valarray<bool> __tmp; 01027 FITSUtil::fill(__tmp,indata); 01028 col.writeData(__tmp,vectorLengths,firstRow); 01029 } 01030 else if ( type() == Tbyte ) 01031 { 01032 ColumnVectorData<unsigned char>& col 01033 = dynamic_cast<ColumnVectorData<unsigned char>&>(*this); 01034 valarray<unsigned char> __tmp; 01035 FITSUtil::fill(__tmp,indata); 01036 col.writeData(__tmp,firstRow); 01037 } 01038 else if ( type() == Tushort ) 01039 { 01040 ColumnVectorData<unsigned short>& col 01041 = dynamic_cast<ColumnVectorData<unsigned short>&>(*this); 01042 valarray<unsigned short> __tmp; 01043 FITSUtil::fill(__tmp,indata); 01044 col.writeData(__tmp,vectorLengths,firstRow); 01045 } 01046 else if ( type() == Tuint ) 01047 { 01048 ColumnVectorData<unsigned int>& col 01049 = dynamic_cast<ColumnVectorData<unsigned int>&>(*this); 01050 valarray<unsigned int> __tmp; 01051 FITSUtil::fill(__tmp,indata); 01052 col.writeData(__tmp,vectorLengths,firstRow); 01053 } 01054 else if ( type() == Tulong ) 01055 { 01056 ColumnVectorData<unsigned long>& col 01057 = dynamic_cast<ColumnVectorData<unsigned long>&>(*this); 01058 valarray<unsigned long> __tmp; 01059 FITSUtil::fill(__tmp,indata); 01060 col.writeData(__tmp,vectorLengths,firstRow); 01061 } 01062 else 01063 { 01064 throw InvalidDataType(name()); 01065 } 01066 } 01067 } 01068 } 01069 01070 template <typename S> 01071 void Column::write (const std::vector<S>& indata,const std::vector<long>& vectorLengths, 01072 long firstRow) 01073 { 01074 // variable length write 01075 // implement as valarray version 01076 std::valarray<S> __tmp(indata.size()); 01077 std::copy(indata.begin(),indata.end(),&__tmp[0]); 01078 write(__tmp,vectorLengths,firstRow); 01079 01080 } 01081 01082 template <typename S> 01083 void Column::write (S* indata, long nelements, const std::vector<long>& vectorLengths, 01084 long firstRow) 01085 { 01086 // implement as valarray version, which will also check array size. 01087 size_t n(vectorLengths.size()); 01088 std::valarray<S> __tmp(indata,nelements); 01089 write(__tmp,vectorLengths,firstRow); 01090 } 01091 01092 template <typename S> 01093 void Column::write (const std::valarray<S>& indata, long nRows, long firstRow) 01094 { 01095 write(indata,nRows,firstRow,static_cast<S*>(0)); 01096 } 01097 01098 template <typename S> 01099 void Column::write (const std::vector<S>& indata, long nRows, long firstRow) 01100 { 01101 write(indata,nRows,firstRow,static_cast<S*>(0)); 01102 } 01103 01104 template <typename S> 01105 void Column::write (S* indata, long nelements, long nRows, long firstRow) 01106 { 01107 write(indata,nelements,nRows,firstRow,static_cast<S*>(0)); 01108 } 01109 01110 01111 01112 template <typename S> 01113 void Column::write (const std::valarray<S>& indata, long nRows, long firstRow, 01114 S* nullValue) 01115 { 01116 // primary implementation, nullValue: write fixed-length data 01117 // to rows of a vector column. 01118 if (nRows <= 0) throw InvalidNumberOfRows(nRows); 01119 parent()->makeThisCurrent(); 01120 firstRow = std::max(firstRow,static_cast<long>(1)); 01121 if (ColumnVectorData<S>* col = dynamic_cast<ColumnVectorData<S>*>(this)) 01122 { 01123 col->writeData(indata,nRows,firstRow,nullValue); 01124 } 01125 else 01126 { 01127 // alright, input data type has to be rewritten as output 01128 // data type. 01129 FITSUtil::MatchType<S> inType; 01130 if ( inType() == type()) 01131 { 01132 String 01133 msg("Incorrect call: writing to valarray data to scalar column: "); 01134 msg += name(); 01135 msg += " does not require specification of number of rows"; 01136 throw WrongColumnType(msg); 01137 } 01138 else 01139 { 01140 if ( type() == Tdouble ) 01141 { 01142 ColumnVectorData<double>& col 01143 = dynamic_cast<ColumnVectorData<double>&>(*this); 01144 std::valarray<double> __tmp; 01145 FITSUtil::fill(__tmp,indata); 01146 col.writeData(__tmp,nRows,firstRow); 01147 } 01148 else if ( type() == Tfloat ) 01149 { 01150 ColumnVectorData<float>& col 01151 = dynamic_cast<ColumnVectorData<float>&>(*this); 01152 std::valarray<float> __tmp; 01153 FITSUtil::fill(__tmp,indata); 01154 col.writeData(__tmp,nRows,firstRow); 01155 } 01156 else if ( type() == Tint ) 01157 { 01158 int nullVal(0); 01159 int* pNullVal = 0; 01160 if (nullValue) 01161 { 01162 nullVal = static_cast<int>(*nullValue); 01163 pNullVal = &nullVal; 01164 } 01165 ColumnVectorData<int>& col 01166 = dynamic_cast<ColumnVectorData<int>&>(*this); 01167 std::valarray<int> __tmp; 01168 FITSUtil::fill(__tmp,indata); 01169 col.writeData(__tmp,nRows,firstRow,pNullVal); 01170 } 01171 else if ( type() == Tshort ) 01172 { 01173 short nullVal(0); 01174 short* pNullVal = 0; 01175 if (nullValue) 01176 { 01177 nullVal = static_cast<short>(*nullValue); 01178 pNullVal = &nullVal; 01179 } 01180 ColumnVectorData<short>& col 01181 = dynamic_cast<ColumnVectorData<short>&>(*this); 01182 std::valarray<short> __tmp; 01183 FITSUtil::fill(__tmp,indata); 01184 col.writeData(__tmp,nRows,firstRow,pNullVal); 01185 } 01186 else if ( type() == Tlong ) 01187 { 01188 long nullVal(0); 01189 long* pNullVal = 0; 01190 if (nullValue) 01191 { 01192 nullVal = static_cast<long>(*nullValue); 01193 pNullVal = &nullVal; 01194 } 01195 ColumnVectorData<long>& col 01196 = dynamic_cast<ColumnVectorData<long>&>(*this); 01197 std::valarray<long> __tmp; 01198 FITSUtil::fill(__tmp,indata); 01199 col.writeData(__tmp,nRows,firstRow,pNullVal); 01200 } 01201 else if ( type() == Tlonglong ) 01202 { 01203 LONGLONG nullVal(0); 01204 LONGLONG* pNullVal = 0; 01205 if (nullValue) 01206 { 01207 nullVal = static_cast<LONGLONG>(*nullValue); 01208 pNullVal = &nullVal; 01209 } 01210 ColumnVectorData<LONGLONG>& col 01211 = dynamic_cast<ColumnVectorData<LONGLONG>&>(*this); 01212 std::valarray<LONGLONG> __tmp; 01213 FITSUtil::fill(__tmp,indata); 01214 col.writeData(__tmp,nRows,firstRow,pNullVal); 01215 } 01216 else if ( type() == Tlogical ) 01217 { 01218 bool nullVal(0); 01219 bool* pNullVal = 0; 01220 if (nullValue) 01221 { 01222 nullVal = static_cast<bool>(*nullValue); 01223 pNullVal = &nullVal; 01224 } 01225 ColumnVectorData<bool>& col 01226 = dynamic_cast<ColumnVectorData<bool>&>(*this); 01227 std::valarray<bool> __tmp; 01228 FITSUtil::fill(__tmp,indata); 01229 col.writeData(__tmp,nRows,firstRow,pNullVal); 01230 } 01231 else if ( type() == Tbyte ) 01232 { 01233 unsigned char nullVal(0); 01234 unsigned char* pNullVal = 0; 01235 if (nullValue) 01236 { 01237 nullVal = static_cast<unsigned char>(*nullValue); 01238 pNullVal = &nullVal; 01239 } 01240 ColumnVectorData<unsigned char>& col 01241 = dynamic_cast<ColumnVectorData<unsigned char>&>(*this); 01242 std::valarray<unsigned char> __tmp; 01243 FITSUtil::fill(__tmp,indata); 01244 col.writeData(__tmp,nRows,firstRow,pNullVal); 01245 } 01246 else if ( type() == Tushort ) 01247 { 01248 unsigned short nullVal(0); 01249 unsigned short* pNullVal = 0; 01250 if (nullValue) 01251 { 01252 nullVal = static_cast<unsigned short>(*nullValue); 01253 pNullVal = &nullVal; 01254 } 01255 ColumnVectorData<unsigned short>& col 01256 = dynamic_cast<ColumnVectorData<unsigned short>&>(*this); 01257 std::valarray<unsigned short> __tmp; 01258 FITSUtil::fill(__tmp,indata); 01259 col.writeData(__tmp,nRows,firstRow,pNullVal); 01260 } 01261 else if ( type() == Tuint ) 01262 { 01263 unsigned int nullVal(0); 01264 unsigned int* pNullVal = 0; 01265 if (nullValue) 01266 { 01267 nullVal = static_cast<unsigned int>(*nullValue); 01268 pNullVal = &nullVal; 01269 } 01270 ColumnVectorData<unsigned int>& col 01271 = dynamic_cast<ColumnVectorData<unsigned int>&>(*this); 01272 std::valarray<unsigned int> __tmp; 01273 FITSUtil::fill(__tmp,indata); 01274 col.writeData(__tmp,nRows,firstRow,pNullVal); 01275 } 01276 else if ( type() == Tulong ) 01277 { 01278 unsigned long nullVal(0); 01279 unsigned long* pNullVal = 0; 01280 if (nullValue) 01281 { 01282 nullVal = static_cast<unsigned long>(*nullValue); 01283 pNullVal = &nullVal; 01284 } 01285 ColumnVectorData<unsigned long>& col 01286 = dynamic_cast<ColumnVectorData<unsigned long>&>(*this); 01287 std::valarray<unsigned long> __tmp; 01288 FITSUtil::fill(__tmp,indata); 01289 col.writeData(__tmp,nRows,firstRow,pNullVal); 01290 } 01291 else 01292 { 01293 throw InvalidDataType(name()); 01294 } 01295 } 01296 } 01297 } 01298 01299 template <typename S> 01300 void Column::write (const std::vector<S>& indata, long nRows, long firstRow, S* nullValue) 01301 { 01302 // fixed length write of vector 01303 // implement as valarray version 01304 if (nRows <= 0) throw InvalidNumberOfRows(nRows); 01305 std::valarray<S> __tmp(indata.size()); 01306 std::copy(indata.begin(),indata.end(),&__tmp[0]); 01307 write(__tmp,nRows,firstRow, nullValue); 01308 } 01309 01310 template <typename S> 01311 void Column::write (S* indata, long nelements, long nRows, long firstRow, S* nullValue) 01312 { 01313 // fixed length write of C-array 01314 // implement as valarray version 01315 if (nRows <= 0) throw InvalidNumberOfRows(nRows); 01316 std::valarray<S> __tmp(indata,nelements); 01317 write(__tmp,nRows,firstRow, nullValue); 01318 } 01319 01320 01321 template <typename S> 01322 void Column::writeArrays (const std::vector<std::valarray<S> >& indata, long firstRow) 01323 { 01324 // vector<valarray>, no null value. 01325 writeArrays(indata,firstRow,static_cast<S*>(0)); 01326 } 01327 01328 template <typename S> 01329 void Column::writeArrays (const std::vector<std::valarray<S> >& indata, long firstRow, 01330 S* nullValue) 01331 { 01332 // vector<valarray>, null value. primary 01333 01334 01335 using std::valarray; 01336 using std::vector; 01337 parent()->makeThisCurrent(); 01338 firstRow = std::max(firstRow,static_cast<long>(1)); 01339 if (ColumnVectorData<S>* col = dynamic_cast<ColumnVectorData<S>*>(this)) 01340 { 01341 col->writeData(indata,firstRow,nullValue); 01342 } 01343 else 01344 { 01345 // alright, input data type has to be rewritten as output 01346 // data type. 01347 FITSUtil::MatchType<S> inType; 01348 if ( inType() == type()) 01349 { 01350 String msg("Incorrect call: writing vectors to scalar column "); 01351 throw WrongColumnType(msg); 01352 } 01353 else 01354 { 01355 size_t n(indata.size()); 01356 if ( type() == Tdouble ) 01357 { 01358 ColumnVectorData<double>& col 01359 = dynamic_cast<ColumnVectorData<double>&>(*this); 01360 vector<valarray<double> > __tmp(n); 01361 for (size_t i = 0; i < n; ++i) 01362 { 01363 FITSUtil::fill(__tmp[i],indata[i]); 01364 } 01365 col.writeData(__tmp,firstRow); 01366 } 01367 else if ( type() == Tfloat ) 01368 { 01369 ColumnVectorData<float>& col 01370 = dynamic_cast<ColumnVectorData<float>&>(*this); 01371 vector<valarray<float> > __tmp(n); 01372 for (size_t i = 0; i < n; ++i) 01373 { 01374 FITSUtil::fill(__tmp[i],indata[i]); 01375 } 01376 col.writeData(__tmp,firstRow); 01377 } 01378 else if ( type() == Tint ) 01379 { 01380 ColumnVectorData<int>& col 01381 = dynamic_cast<ColumnVectorData<int>&>(*this); 01382 vector<valarray<int> > __tmp(n); 01383 int nullVal(0); 01384 int* pNullVal = 0; 01385 if (nullValue) 01386 { 01387 nullVal = static_cast<int>(*nullValue); 01388 pNullVal = &nullVal; 01389 } 01390 for (size_t i = 0; i < n; ++i) 01391 { 01392 FITSUtil::fill(__tmp[i],indata[i]); 01393 } 01394 col.writeData(__tmp,firstRow,pNullVal); 01395 } 01396 else if ( type() == Tshort ) 01397 { 01398 ColumnVectorData<short>& col 01399 = dynamic_cast<ColumnVectorData<short>&>(*this); 01400 vector<valarray<short> > __tmp(n); 01401 short nullVal(0); 01402 short* pNullVal = 0; 01403 if (nullValue) 01404 { 01405 nullVal = static_cast<short>(*nullValue); 01406 pNullVal = &nullVal; 01407 } 01408 for (size_t i = 0; i < n; ++i) 01409 { 01410 FITSUtil::fill(__tmp[i],indata[i]); 01411 } 01412 col.writeData(__tmp,firstRow,pNullVal); 01413 } 01414 else if ( type() == Tlong ) 01415 { 01416 ColumnVectorData<long>& col 01417 = dynamic_cast<ColumnVectorData<long>&>(*this); 01418 vector<valarray<long> > __tmp(n); 01419 long nullVal(0); 01420 long* pNullVal = 0; 01421 if (nullValue) 01422 { 01423 nullVal = static_cast<long>(*nullValue); 01424 pNullVal = &nullVal; 01425 } 01426 for (size_t i = 0; i < n; ++i) 01427 { 01428 FITSUtil::fill(__tmp[i],indata[i]); 01429 } 01430 col.writeData(__tmp,firstRow,pNullVal); 01431 } 01432 else if ( type() == Tlonglong ) 01433 { 01434 ColumnVectorData<LONGLONG>& col 01435 = dynamic_cast<ColumnVectorData<LONGLONG>&>(*this); 01436 vector<valarray<LONGLONG> > __tmp(n); 01437 LONGLONG nullVal(0); 01438 LONGLONG* pNullVal = 0; 01439 if (nullValue) 01440 { 01441 nullVal = static_cast<LONGLONG>(*nullValue); 01442 pNullVal = &nullVal; 01443 } 01444 for (size_t i = 0; i < n; ++i) 01445 { 01446 FITSUtil::fill(__tmp[i],indata[i]); 01447 } 01448 col.writeData(__tmp,firstRow,pNullVal); 01449 } 01450 else if ( type() == Tlogical ) 01451 { 01452 ColumnVectorData<bool>& col 01453 = dynamic_cast<ColumnVectorData<bool>&>(*this); 01454 bool nullVal(0); 01455 bool* pNullVal = 0; 01456 if (nullValue) 01457 { 01458 nullVal = static_cast<bool>(*nullValue); 01459 pNullVal = &nullVal; 01460 } 01461 vector<valarray<bool> > __tmp(n); 01462 for (size_t i = 0; i < n; ++i) 01463 { 01464 FITSUtil::fill(__tmp[i],indata[i]); 01465 } 01466 col.writeData(__tmp,firstRow,pNullVal); 01467 } 01468 else if ( type() == Tbyte ) 01469 { 01470 ColumnVectorData<unsigned char>& col 01471 = dynamic_cast<ColumnVectorData<unsigned char>&>(*this); 01472 unsigned char nullVal(0); 01473 unsigned char* pNullVal = 0; 01474 if (nullValue) 01475 { 01476 nullVal = static_cast<unsigned char>(*nullValue); 01477 pNullVal = &nullVal; 01478 } 01479 vector<valarray<unsigned char> > __tmp(n); 01480 for (size_t i = 0; i < n; ++i) 01481 { 01482 FITSUtil::fill(__tmp[i],indata[i]); 01483 } 01484 col.writeData(__tmp,firstRow,&nullVal); 01485 } 01486 else if ( type() == Tushort ) 01487 { 01488 ColumnVectorData<unsigned short>& col 01489 = dynamic_cast<ColumnVectorData<unsigned short>&>(*this); 01490 unsigned short nullVal(0); 01491 unsigned short* pNullVal = 0; 01492 if (nullValue) 01493 { 01494 nullVal = static_cast<unsigned short>(*nullValue); 01495 pNullVal = &nullVal; 01496 } 01497 vector<valarray<unsigned short> > __tmp(n); 01498 for (size_t i = 0; i < n; ++i) 01499 { 01500 FITSUtil::fill(__tmp[i],indata[i]); 01501 } 01502 col.writeData(__tmp,firstRow,pNullVal); 01503 } 01504 else if ( type() == Tuint ) 01505 { 01506 ColumnVectorData<unsigned int>& col 01507 = dynamic_cast<ColumnVectorData<unsigned int>&>(*this); 01508 unsigned int nullVal(0); 01509 unsigned int* pNullVal = 0; 01510 if (nullValue) 01511 { 01512 nullVal = static_cast<unsigned int>(*nullValue); 01513 pNullVal = &nullVal; 01514 } 01515 vector<valarray<unsigned int> > __tmp(n); 01516 for (size_t i = 0; i < n; ++i) 01517 { 01518 FITSUtil::fill(__tmp[i],indata[i]); 01519 } 01520 col.writeData(__tmp,firstRow,pNullVal); 01521 } 01522 else if ( type() == Tulong ) 01523 { 01524 ColumnVectorData<unsigned long>& col 01525 = dynamic_cast<ColumnVectorData<unsigned long>&>(*this); 01526 unsigned long nullVal(0); 01527 unsigned long* pNullVal = 0; 01528 if (nullValue) 01529 { 01530 nullVal = static_cast<unsigned long>(*nullValue); 01531 pNullVal = &nullVal; 01532 } 01533 vector<valarray<unsigned long> > __tmp(n); 01534 for (size_t i = 0; i < n; ++i) 01535 { 01536 FITSUtil::fill(__tmp[i],indata[i]); 01537 } 01538 col.writeData(__tmp,firstRow,pNullVal); 01539 } 01540 else 01541 { 01542 throw InvalidDataType(name()); 01543 } 01544 } 01545 } 01546 } 01547 01548 01549 template <typename T> 01550 void Column::addNullValue(T nullVal) 01551 { 01552 parent()->makeThisCurrent(); 01553 int status(0); 01554 #ifdef SSTREAM_DEFECT 01555 std::ostrstream keyName; 01556 keyName << "TNULL" << index() << std::ends; 01557 char* nullKey = const_cast<char*>(keyName.str()); 01558 #else 01559 std::ostringstream keyName; 01560 keyName << "TNULL" << index(); 01561 String keyNameStr = keyName.str(); 01562 char* nullKey = const_cast<char*>(keyNameStr.c_str()); 01563 #endif 01564 01565 01566 FITSUtil::MatchType<T> inputType; 01567 int dataType = static_cast<int>(inputType()); 01568 if (dataType == static_cast<int>(Tstring)) 01569 throw InvalidDataType("attempting to set TNULLn to a string."); 01570 01571 // update key but don't add to keyword list because it's really a column 01572 // property not a table metadata property. And it needs to be automatically 01573 // renumbered if columns are inserted or deleted. 01574 if (fits_update_key(fitsPointer(),dataType,nullKey,&nullVal,0,&status)) 01575 throw FitsError(status); 01576 01577 // The following is called to make sure the HDU struct is immediately 01578 // updated in case a column write operation is performed shortly after this 01579 // function exits. 01580 if (fits_set_hdustruc(fitsPointer(),&status)) throw FitsError(status); 01581 01582 } 01583 01584 template <typename T> 01585 bool Column::getNullValue(T* nullVal) const 01586 { 01587 parent()->makeThisCurrent(); 01588 #ifdef SSTREAM_DEFECT 01589 std::ostrstream keyName; 01590 keyName << "TNULL" << index() << std::ends; 01591 char* nullKey = const_cast<char*>(keyName.str()); 01592 #else 01593 std::ostringstream keyName; 01594 keyName << "TNULL" << index(); 01595 String keyNameStr = keyName.str(); 01596 char* nullKey = const_cast<char*>(keyNameStr.c_str()); 01597 #endif 01598 01599 int status=0; 01600 FITSUtil::MatchType<T> inputType; 01601 int dataType = static_cast<int>(inputType()); 01602 if (dataType == static_cast<int>(Tstring)) 01603 throw InvalidDataType("attempting to read TNULLn into a string."); 01604 T tmpVal(*nullVal); 01605 01606 bool keyExists = false; 01607 if (fits_read_key(m_parent->fitsPointer(), dataType, nullKey, &tmpVal, 0, &status)) 01608 { 01609 if (status == KEY_NO_EXIST || status == VALUE_UNDEFINED) 01610 return keyExists; 01611 else 01612 throw FitsError(status); 01613 } 01614 keyExists = true; 01615 *nullVal = tmpVal; 01616 return keyExists; 01617 } 01618 01619 } // namespace CCfits 01620 01621 #endif