Line data Source code
1 : //# FlagReport.cc: This file contains the implementation of the FlagReport class.
2 : //#
3 : //# CASA - Common Astronomy Software Applications (http://casa.nrao.edu/)
4 : //# Copyright (C) Associated Universities, Inc. Washington DC, USA 2011, All rights reserved.
5 : //# Copyright (C) European Southern Observatory, 2011, All rights reserved.
6 : //#
7 : //# This library is free software; you can redistribute it and/or
8 : //# modify it under the terms of the GNU Lesser General Public
9 : //# License as published by the Free software Foundation; either
10 : //# version 2.1 of the License, or (at your option) any later version.
11 : //#
12 : //# This library is distributed in the hope that it will be useful,
13 : //# but WITHOUT ANY WARRANTY, without even the implied warranty of
14 : //# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 : //# Lesser General Public License for more details.
16 : //#
17 : //# You should have received a copy of the GNU Lesser General Public
18 : //# License along with this library; if not, write to the Free Software
19 : //# Foundation, Inc., 59 Temple Place, Suite 330, Boston,
20 : //# MA 02111-1307 USA
21 : //# $Id: $
22 :
23 : #include <flagging/Flagging/FlagReport.h>
24 :
25 : using namespace casacore;
26 : namespace casa { //# NAMESPACE CASA - BEGIN
27 :
28 :
29 : ////////////////////////////////////
30 : /// FlagReport implementation ///
31 : ////////////////////////////////////
32 :
33 : // All FlagReports must have 'type' and 'name' defined.
34 4819 : FlagReport::FlagReport(String type,String name, String title, String xlabel,
35 4819 : String ylabel):Record(),logger_p()
36 : {
37 4819 : logger_p.origin(LogOrigin("FlagReport",__FUNCTION__,WHERE));
38 :
39 : // Type of report. Options : none, list, plotraster, plotpoints
40 4819 : if( ! ( type == "list" || type == "none" || type == "plotraster"
41 0 : || type == "plotpoints") )
42 : {
43 0 : logger_p << LogIO::WARN << "Invalid FlagReport type : " << type << ". Setting to 'none' " << LogIO::POST;
44 0 : type="none";
45 : }
46 :
47 4819 : define( RecordFieldId("type") , type );
48 :
49 4819 : if( type == "list" ) // List of reports
50 : {
51 1745 : define( RecordFieldId("nreport") , (Int)0 );
52 : }
53 : else // One report
54 : {
55 3074 : define( RecordFieldId("name") , name );
56 : }
57 :
58 : // One report of type "plot"
59 4819 : if( type == "plotraster" || type == "plotpoints")
60 : {
61 0 : define( RecordFieldId("title") , title );
62 0 : define( RecordFieldId("xlabel") , xlabel );
63 0 : define( RecordFieldId("ylabel") , ylabel );
64 0 : define( RecordFieldId("ndata") , (Int)0 );
65 : }
66 :
67 4819 : }
68 :
69 423 : FlagReport::FlagReport(String type, String name, const Record &other)
70 : {
71 :
72 423 : assign(other);
73 423 : logger_p = casacore::LogIO();
74 :
75 : // Type of report. Options : none, summary
76 423 : if( ! ( type == "summary" || type == "rflag" || type == "none" ) )
77 : {
78 0 : logger_p << LogIO::WARN << "Invalid FlagReport type : " << type << ". Setting to 'none' " << LogIO::POST;
79 0 : type="none";
80 : }
81 :
82 423 : if( isDefined("type") )
83 : {
84 0 : logger_p << LogIO::WARN << "Overwriting field 'type' of input record by that supplied in this FlagReport constructor : " << type << LogIO::POST;
85 : }
86 423 : define( RecordFieldId("type") , type );
87 :
88 423 : if( isDefined("name") )
89 : {
90 0 : logger_p << LogIO::WARN << "Overwriting field 'name' of input record by that supplied in this FlagReport constructor : " << type << LogIO::POST;
91 : }
92 423 : define( RecordFieldId("name") , name );
93 :
94 423 : }
95 :
96 10 : FlagReport::FlagReport(const Record &other)
97 : {
98 10 : assign(other);
99 10 : logger_p = casacore::LogIO();
100 :
101 10 : if( ! isDefined( "type" ) )
102 : {
103 : // add a type='none' field, and send for validation checks.
104 0 : define( RecordFieldId("type") , "none" );
105 : }
106 :
107 10 : if( ! isDefined( "name" ) )
108 : {
109 : // add a type='none' field, and send for validation checks.
110 0 : define( RecordFieldId("name") , "UnknownAgent" );
111 : }
112 :
113 10 : }
114 :
115 5267 : FlagReport::~FlagReport()
116 : {
117 5267 : }
118 :
119 : // Add a FlagReport of any type to a FlagReport of type "list".
120 : // If it is a single report, add as a subRecord
121 : // If it is a list of reports, append this list, and re-index.
122 : Bool
123 2689 : FlagReport::addReport(FlagReport inpReport)
124 : {
125 2689 : logger_p.origin(LogOrigin("FlagReport",__FUNCTION__,WHERE));
126 :
127 : // Verify and read type of current record
128 2689 : if( !verifyFields() )
129 : {
130 0 : return false;
131 : }
132 :
133 : // Reports can be added only to flagreports of type 'list'
134 2689 : if( reportType() != String("list"))
135 : {
136 0 : logger_p << LogIO::WARN << "Current FlagReport must be of type 'list' " << LogIO::POST;
137 0 : return false;
138 : }
139 :
140 : // Now that we know it's of type list, read nreport
141 2689 : Int numReport = nReport();
142 :
143 : // React to different types of input FlagReports
144 2689 : if( inpReport.reportType() != String("list")) // It's not a list.
145 : {
146 2228 : if ( inpReport.reportType() != String("none") ) // It's not empty either. Add as a subRecord.
147 : {
148 423 : defineRecord( RecordFieldId(String("report")+String::toString(numReport)) , inpReport );
149 423 : define( RecordFieldId("nreport") , (Int)(numReport+1) );
150 : }
151 : }
152 : else // It's a list. Append the input list to the current one, re-indexing appropriately
153 : {
154 461 : Int nInpReps = inpReport.nReport();
155 :
156 884 : for(Int rep=0;rep<nInpReps;rep++)
157 : {
158 423 : defineRecord( RecordFieldId(String("report")+String::toString(numReport+rep)) , inpReport.asRecord( (String("report")+String::toString(rep)) ) );
159 : }
160 461 : define( RecordFieldId("nreport") , (Int)(numReport + nInpReps) );
161 : }
162 2689 : return true;
163 : }// end of addReport
164 :
165 : //----------------------------------------------------------------------------------------------
166 : Bool
167 0 : FlagReport::addData(Array<Float> data)
168 : {
169 0 : logger_p.origin(LogOrigin("FlagReport",__FUNCTION__,WHERE));
170 :
171 0 : String thisType = reportType();
172 0 : Bool retval = true;
173 :
174 0 : if( thisType != "plotraster" )
175 : {
176 0 : logger_p << LogIO::WARN << "Current FlagReport must be of type 'plotraster' " << LogIO::POST;
177 : // return false;
178 0 : retval = false;
179 : }
180 : else
181 : {
182 0 : Int numData = nData();
183 0 : if(numData == 1)
184 : {
185 0 : logger_p << LogIO::WARN << "Cannot overlay raster plots." << LogIO::POST;
186 : // return false;
187 0 : retval = false;
188 :
189 : }
190 : else
191 : {
192 0 : define( RecordFieldId(String("data")+String::toString(numData)) , data );
193 0 : define( RecordFieldId("ndata") , (Int)(numData+1) );
194 0 : retval = true;
195 : }
196 : }
197 :
198 0 : return retval;
199 0 : }
200 :
201 : //----------------------------------------------------------------------------------------------
202 : Bool
203 0 : FlagReport::addData(String plottype, Vector<Float> xdata, Vector<Float> ydata, String errortype, Vector<Float> error, String label)
204 : {
205 0 : logger_p.origin(LogOrigin("FlagReport",__FUNCTION__,WHERE));
206 :
207 0 : String thisType = reportType();
208 0 : if( thisType != "plotpoints" )
209 : {
210 0 : logger_p << LogIO::WARN << "Current FlagReport must be of type 'plotpoints' " << LogIO::POST;
211 0 : return false;
212 : }
213 : else
214 : {
215 0 : Int numData = nData();
216 0 : define( RecordFieldId(String("plottype")+String::toString(numData)) , plottype );
217 0 : define( RecordFieldId(String("xdata")+String::toString(numData)) , xdata );
218 0 : define( RecordFieldId(String("ydata")+String::toString(numData)) , ydata );
219 0 : define( RecordFieldId(String("label")+String::toString(numData)) , label );
220 0 : define( RecordFieldId("ndata") , (Int)(numData+1) );
221 :
222 0 : if( error.nelements() > 0 )
223 : {
224 0 : define( RecordFieldId(String("error")+String::toString(numData)) , error );
225 0 : define( RecordFieldId(String("errortype")+String::toString(numData)) , errortype );
226 : }
227 :
228 : }
229 :
230 0 : return true;
231 0 : }
232 :
233 : //----------------------------------------------------------------------------------------------
234 : //----------------------------------------------------------------------------------------------
235 :
236 : String
237 10756 : FlagReport::reportType()
238 : {
239 10756 : String thisType;
240 10756 : if( ! isDefined("type") )
241 : {
242 0 : ostringstream xxx;
243 0 : print(xxx);
244 0 : cout << "Report with no type : " << xxx.str() << endl;
245 0 : }
246 10756 : get( RecordFieldId("type") , thisType );
247 10756 : return thisType;
248 0 : }
249 :
250 : Int
251 3150 : FlagReport::nReport()
252 : {
253 3150 : if( reportType() != "list" )
254 : {
255 0 : return -1;
256 : }
257 : else
258 : {
259 : Int nrep;
260 3150 : get( RecordFieldId("nreport") , nrep );
261 3150 : return nrep;
262 : }
263 : }
264 :
265 : Int
266 0 : FlagReport::nData()
267 : {
268 0 : String thisType = reportType();
269 :
270 0 : if( thisType != "plotraster" && thisType != "plotpoints" )
271 : {
272 0 : return -1;
273 : }
274 : else
275 : {
276 : Int ndat;
277 0 : get( RecordFieldId("ndata") , ndat );
278 0 : return ndat;
279 : }
280 0 : }
281 :
282 : Bool
283 0 : FlagReport::accessReport(Int index, FlagReport &outReport)
284 : {
285 : // Verify and read type of current record
286 0 : if( !verifyFields() )
287 : {
288 0 : return false;
289 : }
290 :
291 0 : if( reportType() != "list" )
292 : {
293 0 : return false;
294 : }
295 :
296 0 : if( index < 0 || index >= nReport() )
297 : {
298 0 : return false;
299 : }
300 :
301 0 : String repName(String("report")+String::toString(index));
302 0 : outReport = subRecord( RecordFieldId(repName) );
303 0 : return true;
304 0 : }
305 :
306 :
307 : //----------------------------------------------------------------------------------------------
308 :
309 : // Check that all required fields have valid values.
310 : Bool
311 2699 : FlagReport::verifyFields()
312 : {
313 2699 : logger_p.origin(LogOrigin("FlagReport",__FUNCTION__,WHERE));
314 :
315 2699 : if( ! (isDefined("type") ) )
316 : {
317 0 : logger_p << LogIO::WARN << "Invalid FlagReport state ! No type is defined." << LogIO::POST;
318 0 : return false;
319 : }
320 :
321 : // Read type of current record
322 2699 : String thisType;
323 2699 : get( RecordFieldId("type") , thisType );
324 :
325 : // For a FlagReport of type "list", check that nreport exists and is correct.
326 2699 : if(thisType == "list")
327 : {
328 2689 : if( ! isDefined("nreport") )
329 : {
330 0 : logger_p << LogIO::WARN << "No 'nreport' defined" << LogIO::POST;
331 0 : return false; // nreport field is not defined
332 : }
333 : else // check that nreport subRecords exist, and verify each one.
334 : {
335 : Int nReps;
336 2689 : get( RecordFieldId("nreport") , nReps );
337 2699 : for(Int rep=0; rep<nReps; rep++)
338 : {
339 20 : String repname = String("report")+String::toString(rep);
340 10 : if( ! isDefined(repname) )
341 : {
342 0 : logger_p << LogIO::WARN << "Report : " << repname << " is not defined" << LogIO::POST;
343 0 : return false; // Does not contain a subReport
344 : }
345 : else
346 : {
347 10 : FlagReport subRep(subRecord( RecordFieldId(repname) ));
348 10 : if( ! subRep.verifyFields() )
349 : {
350 0 : logger_p << LogIO::WARN << "Invalid subRecord for " << repname << LogIO::POST;
351 0 : return false; // subReport is invalid
352 : }
353 10 : }
354 10 : }
355 : }
356 : }
357 10 : else if(thisType=="plotraster" || thisType=="plotpoints")
358 : {
359 0 : if( !isDefined("name") || !isDefined("title") ||
360 0 : !isDefined("xlabel") || !isDefined("ylabel") ||
361 0 : !isDefined("ndata") )
362 : {
363 0 : logger_p << LogIO::WARN << "Invalid FlagReport of type " << thisType << LogIO::POST;
364 0 : return false;
365 : }
366 :
367 : Int numData;
368 0 : get( RecordFieldId("ndata") , numData);
369 :
370 0 : for(Int dat=0;dat<numData;dat++)
371 : {
372 0 : if( (thisType=="plotraster" && ! isDefined(String("data")+String::toString(dat)) ) ||
373 0 : ( (thisType=="plotpoints") && (!isDefined(String("xdata")+String::toString(dat)) || !isDefined(String("ydata")+String::toString(dat)) ) ) )
374 : {
375 0 : logger_p << LogIO::WARN << "Data for " << dat << " is not defined" << LogIO::POST;
376 0 : return false; // Does not contain data.
377 : }
378 :
379 : }
380 :
381 : }
382 : // else it is of type 'summary' or 'none' and we don't check anything there.
383 :
384 2699 : return true;
385 :
386 2699 : }// end of verifyFields()
387 :
388 :
389 : } //# NAMESPACE CASA - END
390 :
|