source: tags/release-0.9/Cubes/cubes.cc @ 813

Last change on this file since 813 was 3, checked in by Matthew Whiting, 18 years ago

This is the first full import of all working code to
the Duchamp repository.
Made three directories at top level:

branches/ tags/ trunk/

and trunk/ has the full set of code:
ATrous/ Cubes/ Detection/ InputComplete? InputExample? README Utils/ docs/ mainDuchamp.cc param.cc param.hh

File size: 10.8 KB
Line 
1#include <iostream>
2#include <iomanip>
3#include <vector>
4#include <string>
5#include <wcs.h>
6#include <Cubes/cubes.hh>
7#include <Utils/utils.hh>
8using std::endl;
9
10/****************************************************************/
11///////////////////////////////////////////////////
12//// Functions for DataArray class:
13///////////////////////////////////////////////////
14
15DataArray::DataArray(short int nDim, long size){
16  // need error handling in case size<0 !!!
17  if(size>0) this->array = new float[size];
18  this->numPixels = size;
19  if(nDim>0) this->axisDim = new long[nDim];
20  this->numDim = nDim;
21}
22
23DataArray::DataArray(short int nDim, long *dimensions){
24  int size = dimensions[0];
25  for(int i=1;i<nDim;i++) size *= dimensions[i];
26  this->numPixels = size;
27  if(size>0){
28    this->array = new float[size];
29//     this->blankarray = new bool[size];
30  }
31  this->numDim=nDim;
32  if(nDim>0) this->axisDim = new long[nDim];
33  for(int i=0;i<nDim;i++) this->axisDim[i] = dimensions[i];
34}
35
36void DataArray::getDimArray(long *output){
37  for(int i=0;i<this->numDim;i++) output[i] = this->axisDim[i];
38}
39
40void DataArray::getArray(float *output){
41  for(int i=0;i<this->numPixels;i++) output[i] = this->array[i];
42}
43
44void DataArray::saveArray(float *input, long size){
45  delete [] this->array;
46  // Need check for change in number of pixels!
47  this->numPixels = size;
48  this->array = new float[size];
49  for(int i=0;i<size;i++) this->array[i] = input[i];
50}
51
52void DataArray::getDim(long &x, long &y, long &z){
53  if(numDim>0) x=axisDim[0];
54  else x=0;
55  if(numDim>1) y=axisDim[1];
56  else y=0;
57  if(numDim>2) z=axisDim[2];
58  else z=0;
59}
60
61void DataArray::addObject(Detection object){
62  // adds a single detection to the object list
63  // objectList is a vector, so just use push_back()
64  this->objectList.push_back(object);
65}
66
67void DataArray::addObjectList(vector <Detection> newlist) {
68  for(int i=0;i<newlist.size();i++) this->objectList.push_back(newlist[i]);
69}
70
71std::ostream& operator<< ( std::ostream& theStream, DataArray &array){
72
73  for(int i=0;i<array.numDim;i++){
74    if(i>0) theStream<<"x";
75    theStream<<array.axisDim[i];
76  }
77  theStream<<endl;
78  theStream<<array.objectList.size()<<" detections:"<<endl<<"--------------\n";
79  for(int i=0;i<array.objectList.size();i++){
80    theStream << "Detection #" << array.objectList[i].getID()<<endl;
81    Detection *obj = new Detection;
82    *obj = array.objectList[i];
83    for(int j=0;j<obj->getSize();j++){
84      obj->setX(j,obj->getX(j)+obj->getXOffset());
85      obj->setY(j,obj->getY(j)+obj->getYOffset());
86      obj->setZ(j,obj->getZ(j)+obj->getZOffset());
87    }
88    theStream<<*obj;
89    delete obj;
90  }
91  theStream<<"--------------\n";
92}
93
94/****************************************************************/
95/////////////////////////////////////////////////////////////
96//// Functions for Image class
97/////////////////////////////////////////////////////////////
98
99Image::Image(long size){
100  // need error handling in case size<0 !!!
101  if(size>0){
102    this->array = new float[size];
103    this->pValue = new float[size];
104    this->mask = new short int[size];
105  }
106  this->numPixels = size;
107  this->axisDim = new long[2];
108  this->numDim = 2;
109}
110
111Image::Image(long *dimensions){
112  int size = dimensions[0] * dimensions[1];
113  this->numPixels = size;
114  if(size>0){
115    this->array = new float[size];
116    this->pValue = new float[size];
117    this->mask = new short int[size];
118  }
119  this->numDim=2;
120  this->axisDim = new long[2];
121  for(int i=0;i<2;i++) this->axisDim[i] = dimensions[i];
122  for(int i=0;i<size;i++) this->mask[i] = 0;
123}
124
125void Image::saveArray(float *input, long size){
126  // Need check for change in number of pixels!
127  if(this->numPixels>0){
128    delete [] array;
129    delete [] pValue;
130    delete [] mask;
131  }
132  this->numPixels = size;
133  this->array = new float[size];
134  this->pValue = new float[size];
135  this->mask = new short int[size];
136  for(int i=0;i<size;i++) this->array[i] = input[i];
137  for(int i=0;i<size;i++) this->mask[i] = 0;
138}
139
140void Image::maskObject(Detection &object)
141{
142  /**
143   * Image::maskObject(Detection &)
144   *  A function that increments the mask for each pixel of the detection.
145   */
146
147  for(long i=0;i<object.getSize();i++){
148    this->setMaskValue(object.getX(i),object.getY(i),1);
149  }
150
151}
152
153/****************************************************************/
154/////////////////////////////////////////////////////////////
155//// Functions for Cube class
156/////////////////////////////////////////////////////////////
157
158Cube::Cube(long size){
159  // need error handling in case size<0 !!!
160  if(size>0){
161    this->array = new float[size];
162//     this->blankarray = new bool[size];
163    this->recon = new float[size];
164  }
165  this->numPixels = size;
166  this->axisDim = new long[2];
167  this->numDim = 3;
168  this->reconExists = false;
169  flagWCS = false;
170}
171
172Cube::Cube(long *dimensions){
173  int size   = dimensions[0] * dimensions[1] * dimensions[2];
174  int imsize = dimensions[0] * dimensions[1];
175  this->numPixels = size;
176  if(size>0){
177    this->array      = new float[size];
178//     this->blankarray = new bool[size];
179    this->detectMap  = new short[imsize];
180    if(this->par.getFlagATrous())
181      this->recon    = new float[size];
182    if(this->par.getFlagBaseline())
183      this->baseline = new float[size];
184  }
185  this->numDim  = 3;
186  this->axisDim = new long[3];
187  for(int i=0;i<3     ;i++) this->axisDim[i]   = dimensions[i];
188  for(int i=0;i<imsize;i++) this->detectMap[i] = 0;
189  this->wcs = new wcsprm;
190  this->wcs->flag=-1;
191  wcsini(true,3,this->wcs);
192  flagWCS = false;
193}
194
195void Cube::initialiseCube(long *dimensions){
196  int size   = dimensions[0] * dimensions[1] * dimensions[2];
197  int imsize = dimensions[0] * dimensions[1];
198  this->numPixels = size;
199  if(size>0){
200    this->array      = new float[size];
201//     this->blankarray = new bool[size];
202    this->detectMap  = new short[imsize];
203    this->specMean   = new float[imsize];
204    this->specSigma  = new float[imsize];
205    this->chanMean   = new float[dimensions[2]];
206    this->chanSigma  = new float[dimensions[2]];
207    if(this->par.getFlagATrous())
208      this->recon    = new float[size];
209    if(this->par.getFlagBaseline())
210      this->baseline = new float[size];
211  }
212  this->numDim  = 3;
213  this->axisDim = new long[3];
214  for(int i=0;i<3     ;i++) this->axisDim[i]   = dimensions[i];
215  for(int i=0;i<imsize;i++) this->detectMap[i] = 0;
216  this->wcs = new wcsprm;
217  this->wcs->flag=-1;
218  wcsini(true,3,this->wcs);
219}
220
221void Cube::saveArray(float *input, long size){
222  // Need check for change in number of pixels!
223  if(this->numPixels>0) delete [] array;
224  this->numPixels = size;
225  this->array = new float[size];
226  for(int i=0;i<size;i++) this->array[i] = input[i];
227}
228
229void Cube::saveRecon(float *input, long size){
230  // Need check for change in number of pixels!
231  if(this->numPixels>0) delete [] recon;
232  this->numPixels = size;
233  this->recon = new float[size];
234  for(int i=0;i<size;i++) this->recon[i] = input[i];
235  this->reconExists = true;
236}
237
238void Cube::getRecon(float *output){
239  // Need check for change in number of pixels!
240  long size = this->numPixels;
241  for(int i=0;i<size;i++){
242    if(this->reconExists) output[i] = this->recon[i];
243    else output[i] = 0.;
244  }
245}
246
247////////// WCS-related functions
248
249void Cube::setWCS(wcsprm *w)
250{
251  /**
252   * Cube::setWCS(wcsprm *)
253   *  A function that assigns the cube's wcs parameters, and runs
254   *   wcsset to set it up correctly.
255   *  Performs a check to see if the WCS is good (by looking at
256   *   the lng and lat wcsprm parameters), and sets the flagWCS accordingly.
257   */
258
259  wcscopy(true,w,this->wcs);
260  wcsset(this->wcs);
261  if( (w->lng!=-1) && (w->lat!=-1) ) this->flagWCS = true;
262}
263
264wcsprm *Cube::getWCS()
265{
266  /**
267   * Cube::getWCS()
268   *  A function that returns a wcsprm object corresponding to the cube's WCS.
269   */
270
271  wcsprm *wNew = new wcsprm;
272//   wcsprm *wOld = new wcsprm;
273//   wOld = this->wcs;
274  wNew->flag=-1;
275//   wcsini(true,wOld->naxis,wNew);
276//   wcscopy(true,wOld,wNew);
277  wcsini(true,this->wcs->naxis,wNew);
278  wcscopy(true,this->wcs,wNew);
279  return wNew;
280}
281
282void Cube::calcObjectWCSparams()
283{
284  /**
285   * Cube::calcObjectWCSparams()
286   *  A function that calculates the WCS parameters for each object in the
287   *  cube's list of detections.
288   *  Each object gets an ID number set (just the order in the list), and if the
289   *   WCS is good, the WCS paramters are calculated.
290   */
291 
292  for(int i=0; i<this->objectList.size();i++){
293    this->objectList[i].setID(i+1);
294    if(this->flagWCS) this->objectList[i].calcWCSparams(this->wcs);
295    this->objectList[i].setIntegFlux( this->objectList[i].getIntegFlux()/this->par.getBeamSize() );
296    // correct the integrated flux for the beam size.
297  } 
298
299 
300}
301
302void Cube::sortDetections()
303{
304  /**
305   * Cube::sortDetections()
306   *  A front end to the sort-by functions.
307   *  If there is a good WCS, the detection list is sorted by velocity.
308   *  Otherwise, it is sorted by increasing z-pixel value.
309   *  The ID numbers are then re-calculated.
310   */
311 
312  if(this->flagWCS) SortByVel(this->objectList);
313  else SortByZ(this->objectList);
314  for(int i=0; i<this->objectList.size();i++) this->objectList[i].setID(i+1);
315
316}
317
318void Cube::updateDetectMap()
319{
320  /**
321   * Cube::updateDetectMap()
322   *  A function that, for each detected object in the cube's list, increments the
323   *  cube's detection map by the required amount at each pixel.
324   */
325
326  for(int obj=0;obj<this->objectList.size();obj++)
327    for(int pix=0;pix<this->objectList[obj].getSize();pix++)
328      this->detectMap[this->objectList[obj].getX(pix)+this->objectList[obj].getY(pix)*this->axisDim[0]]++;
329}
330
331void Cube::updateDetectMap(Detection obj)
332{
333  /**
334   * Cube::updateDetectMap(Detection)
335   *  A function that, for the given object, increments the cube's
336   *  detection map by the required amount at each pixel.
337   */
338  for(int pix=0;pix<obj.getSize();pix++)
339    this->detectMap[obj.getX(pix)+obj.getY(pix)*this->axisDim[0]]++;
340}
341
342void Cube::setCubeStats()
343{
344  // First set the stats for each spectrum (ie. each spatial pixel)
345  long xySize = this->axisDim[0]*this->axisDim[1];
346  float *spec = new float[this->axisDim[2]];
347  for(int i=0;i<xySize;i++){
348    for(int z=0;z<this->axisDim[2];z++){
349      //Two cases: i) have reconstructed -- use residuals
350      //          ii) otherwise          -- use original array
351      if(this->reconExists) spec[z] = this->array[z*xySize+i] - this->recon[z*xySize+1];
352      else                  spec[z] = this->array[z*xySize+i];
353    }
354    findMedianStats(spec,this->axisDim[2],this->specMean[i],this->specSigma[i]);
355  }
356  delete spec;
357  // Then set the stats for each channel map
358  float *im = new float[xySize];
359  for(int z=0;z<this->axisDim[2];z++){
360    for(int i=0;i<xySize;i++){
361      if(this->reconExists) im[i] = this->array[z*xySize+i] - this->recon[z*xySize+1];
362      else                  im[i] = this->array[z*xySize+i];
363     
364    }
365    findMedianStats(im,this->axisDim[2],this->chanMean[z],this->chanSigma[z]);
366    this->chanSigma[z] /= correctionFactor;
367  }
368  delete im;
369
370}
Note: See TracBrowser for help on using the repository browser.