Commits
Renaud Miel authored d91a21cf493 Merge
20 20 | |
21 21 | |
22 22 | |
23 23 | |
24 24 | |
25 25 | |
26 26 | |
27 27 | |
28 28 | |
29 29 | |
30 + | |
31 + | |
32 + | |
33 + | |
30 34 | |
31 35 | |
32 36 | |
33 37 | |
34 38 | |
35 39 | |
36 40 | |
37 41 | |
38 42 | |
39 43 | |
167 171 | } |
168 172 | } |
169 173 | |
170 174 | } |
171 175 | |
172 176 | /** \brief Take a parameter than can be specified as a sequence of |
173 177 | antenna numbers or names and always return as a sequence of |
174 178 | antenna numbers. |
175 179 | */ |
176 180 | |
177 - | |
178 181 | |
179 - | |
180 - | struct hack01 { |
181 - | bool operator()(bool acc, const std::map<size_t, std::string >::value_type &p){ |
182 - | bool cmp = p.second == ele; |
183 - | if ( cmp ) match = p.first; |
184 - | return acc || cmp; |
185 - | } |
186 - | hack01( size_t &m, const std::string &e ) : match(m), ele(e) { } |
187 - | size_t &match; |
188 - | const std::string &ele; |
189 - | }; |
190 - | |
191 - | struct hack02 { |
192 - | bool operator()(bool acc, const std::map<size_t, std::string >::value_type &p) { return acc || (p.first == n); } |
193 - | hack02( int x ) : n(x) { } |
194 - | int n; |
195 - | }; |
196 - | |
197 - | |
198 - | LibAIR2::AntSet getAntPars(const std::string &s, |
199 - | const boost::program_options::variables_map &vm, |
200 - | const casacore::MeasurementSet &ms) |
182 + | std::vector<size_t> getAntParsV(const casacore::String &s, |
183 + | const boost::program_options::variables_map &vm, |
184 + | const casacore::MeasurementSet &ms) |
201 185 | { |
202 186 | using namespace LibAIR2; |
203 187 | aname_t anames=getAName(ms); |
204 - | std::vector<std::string> pars=vm[s].as<std::vector<std::string> >(); |
205 - | LibAIR2::AntSet res; |
188 + | casacore::Vector<casacore::String> pars = stringToVector(casacore::String(vm[s].as<std::string>()), ','); |
189 + | std::vector<size_t> res; |
190 + | |
206 191 | for (size_t i=0; i<pars.size(); ++i) |
207 192 | { |
208 - | size_t match; |
209 - | if (std::accumulate( anames.begin( ), |
210 - | anames.end( ), false, |
211 - | |
212 - | [&](bool acc, const aname_t::value_type &p){ |
213 - | bool cmp = p.second == pars[i]; |
214 - | if ( cmp ) match = p.first; |
215 - | return acc || cmp; |
216 - | } |
217 - | |
218 - | hack01(match,pars[i]) |
219 - | |
220 - | )) |
221 - | { |
222 - | res.insert(match); |
223 - | } |
193 + | size_t match; |
194 + | std::string thisant = pars[i]; |
195 + | if (std::accumulate( anames.begin( ), |
196 + | anames.end( ), false, |
197 + | [&](bool acc, const aname_t::value_type &p){ |
198 + | bool cmp = p.second == thisant; |
199 + | if ( cmp ) match = p.first; |
200 + | return acc || cmp; |
201 + | } |
202 + | )) |
203 + | { |
204 + | res.push_back(match); |
205 + | } |
224 206 | else |
225 - | { |
226 - | // should be an antenna number |
227 - | try { |
228 - | int n=boost::lexical_cast<int>(pars[i]); |
229 - | if ( std::accumulate( anames.begin(), |
230 - | anames.end(), false, |
231 - | |
232 - | [=](bool acc, const aname_t::value_type &p) { |
233 - | return acc || ((int)p.first == n); |
234 - | } |
235 - | |
236 - | hack02(n) |
237 - | |
238 - | ) == false ) |
239 - | { |
240 - | throw AntIDError(n, |
241 - | anames); |
207 + | { |
208 + | // should be an antenna number |
209 + | try { |
210 + | int n=boost::lexical_cast<int>(thisant); |
211 + | if ( std::accumulate( anames.begin(), |
212 + | anames.end(), false, |
213 + | [=](bool acc, const aname_t::value_type &p) { |
214 + | return acc || ((int)p.first == n); |
215 + | } |
216 + | ) == false ) |
217 + | { |
218 + | throw AntIDError(n, |
219 + | anames); |
220 + | } |
221 + | res.push_back(n); |
242 222 | } |
243 - | res.insert(n); |
223 + | catch (const boost::bad_lexical_cast & bc) |
224 + | { |
225 + | throw AntIDError(thisant, |
226 + | anames); |
227 + | } |
244 228 | } |
245 - | catch (const boost::bad_lexical_cast & bc) |
246 - | { |
247 - | throw AntIDError(pars[i], |
248 - | anames); |
229 + | } |
230 + | return res; |
231 + | } |
249 232 | |
250 - | } |
233 + | LibAIR2::AntSet getAntPars(const casacore::String &s, |
234 + | const boost::program_options::variables_map &vm, |
235 + | const casacore::MeasurementSet &ms) |
236 + | { |
237 + | std::vector<size_t> resv = getAntParsV(s, vm, ms); |
238 + | LibAIR2::AntSet res; |
239 + | |
251 240 | |
252 - | } |
241 + | for (size_t i=0; i<resv.size(); ++i) |
242 + | { |
243 + | res.insert(resv[i]); |
253 244 | } |
254 245 | |
255 - | |
256 246 | return res; |
257 247 | } |
258 248 | |
259 249 | |
260 250 | /** Simple function to turn the command line parameters into a single |
261 251 | string. |
262 252 | |
263 253 | Return by value as only needs to be called once in program |
264 254 | */ |
265 255 | static std::string buildCmdLine(int argc, |
477 467 | fselect, |
478 468 | (size_t) wvrspws[0], |
479 469 | tmask); |
480 470 | } |
481 471 | else |
482 472 | { |
483 473 | std::vector<std::string> fields=vm["statfield"].as<std::vector<std::string> >(); |
484 474 | LibAIR2::field_t fnames=LibAIR2::getFieldNames(ms); |
485 475 | |
486 476 | std::set<size_t> fselect; |
487 - | size_t val; |
477 + | size_t val; |
488 478 | if (std::accumulate( fnames.begin( ), |
489 - | fnames.end( ), false, |
490 - | |
491 - | [&](bool acc, const LibAIR2::field_t::value_type &p) { |
492 - | bool cmp = p.second == fields[0]; |
493 - | if ( cmp ) val = p.first; |
494 - | return acc || cmp; |
495 - | } |
496 - | |
497 - | hack01(val,fields[0]) |
498 - | |
499 - | )) // User supplied field *name* |
500 - | { |
501 - | fselect.insert(val); |
502 - | } |
503 - | else |
504 - | { |
505 - | try |
479 + | fnames.end( ), false, |
480 + | [&](bool acc, const LibAIR2::field_t::value_type &p) { |
481 + | bool cmp = p.second == fields[0]; |
482 + | if ( cmp ) val = p.first; |
483 + | return acc || cmp; |
484 + | } |
485 + | )) // User supplied field *name* |
506 486 | { |
507 - | size_t n=boost::lexical_cast<int>(fields[0]); |
508 - | fselect.insert(n); |
487 + | fselect.insert(val); |
509 488 | } |
510 - | catch (const boost::bad_lexical_cast & bc) |
489 + | else |
511 490 | { |
512 - | std::cout<<"Warning: Could not understand statfield argument. Will use zeroth field." |
513 - | <<std::endl; |
491 + | try |
492 + | { |
493 + | size_t n=boost::lexical_cast<int>(fields[0]); |
494 + | fselect.insert(n); |
495 + | } |
496 + | catch (const boost::bad_lexical_cast & bc) |
497 + | { |
498 + | std::cout<<"Warning: Could not understand statfield argument. Will use zeroth field." |
499 + | <<std::endl; |
500 + | } |
514 501 | } |
515 - | } |
516 502 | LibAIR2::fieldTimes(time, |
517 - | flds, |
518 - | spws, |
519 - | fselect, |
520 - | (size_t) wvrspws[0], |
521 - | tmask); |
503 + | flds, |
504 + | spws, |
505 + | fselect, |
506 + | (size_t) wvrspws[0], |
507 + | tmask); |
522 508 | } |
523 509 | LibAIR2::printStatTimes(std::cout, |
524 - | time, |
525 - | tmask); |
510 + | time, |
511 + | tmask); |
526 512 | } |
527 513 | |
528 514 | |
529 515 | /// Compute the discrepance in path estimate between channels 1 and 3 |
530 516 | void computePathDisc(const LibAIR2::InterpArrayData &d, |
531 517 | const std::vector<std::pair<double, double> > &tmask, |
532 518 | LibAIR2::dTdLCoeffsBase &coeffs, |
533 519 | std::vector<double> &res) |
534 520 | { |
535 521 | LibAIR2::ArrayGains g1(d.g_time(), |
618 604 | std::cerr << "Parameter 'tie': The source id " << *j << " is an integer but not a valid numerical Source ID. Will try to interpret it as a name ..." << std::endl; |
619 605 | throw std::exception(); |
620 606 | } |
621 607 | cs.insert(srcid); |
622 608 | } |
623 609 | catch (const std::exception& x) |
624 610 | { |
625 611 | size_t match; |
626 612 | if ( std::accumulate( srcmap.begin( ), |
627 613 | srcmap.end( ), false, |
628 - | |
629 614 | [&](bool acc, const std::map<size_t, std::string >::value_type &p) { |
630 - | bool cmp = p.second == *j; |
631 - | if ( cmp ) match = p.first; |
632 - | return acc || cmp; |
615 + | bool cmp = p.second == *j; |
616 + | if ( cmp ) match = p.first; |
617 + | return acc || cmp; |
633 618 | } |
634 - | |
635 - | hack01(match,*j) |
636 - | |
637 - | )) { |
619 + | )) { |
638 620 | cs.insert(match); |
639 621 | } else { |
640 622 | std::ostringstream oss; |
641 623 | oss << "Parameter 'tie': The field " << *j << " is not recognised. Please check for typos." << std::endl; |
642 624 | throw LibAIR2::WVRUserError(oss.str()); |
643 - | } |
625 + | } |
644 626 | } |
645 627 | } // end for |
646 628 | res.push_back(cs); |
647 629 | } |
648 630 | return res; |
649 631 | } |
650 632 | |
651 633 | void printTied(const std::vector<std::set<std::string> > &tied, |
652 634 | const std::vector<std::set<size_t> > &tiedi) |
653 635 | { |
678 660 | names. |
679 661 | */ |
680 662 | std::set<size_t> sourceSet(const std::vector<std::string> &sources, |
681 663 | const casacore::MeasurementSet &ms) |
682 664 | { |
683 665 | std::map<size_t, std::string > snames=LibAIR2::getSourceNames(ms); |
684 666 | std::set<size_t> sset; |
685 667 | for(size_t i=0; i<sources.size(); ++i) { |
686 668 | size_t match; |
687 669 | if (std::accumulate( snames.begin( ), |
688 - | snames.end( ), false, |
689 - | |
690 - | [&](bool acc, const std::map<size_t, std::string >::value_type &p) { |
691 - | bool cmp = p.second == sources[i]; |
692 - | if ( cmp ) match = p.first; |
693 - | return acc || cmp; |
694 - | } |
695 - | |
696 - | hack01(match,sources[i]) |
697 - | |
698 - | )) { |
699 - | sset.insert(match); |
670 + | snames.end( ), false, |
671 + | [&](bool acc, const std::map<size_t, std::string >::value_type &p) { |
672 + | bool cmp = p.second == sources[i]; |
673 + | if ( cmp ) match = p.first; |
674 + | return acc || cmp; |
675 + | } |
676 + | )) { |
677 + | sset.insert(match); |
700 678 | } |
701 679 | } |
702 680 | return sset; |
703 681 | } |
704 682 | |
705 683 | |
706 684 | /** Filter the set of input WVR measurements to retrieve the |
707 685 | coefficients from to exclude flagged sources |
708 686 | |
709 687 | This function takes and returns two containers: the first is the |
810 788 | ("reverse", |
811 789 | "Reverse the sign of correction in all SPW (e.g. due to AIV-1740)") |
812 790 | ("reversespw", |
813 791 | value< std::vector<int> >(), |
814 792 | "Reverse the sign correction for this spw") |
815 793 | ("disperse", |
816 794 | "Apply correction for dispersion") |
817 795 | ("cont", |
818 796 | "UNTESTED! Estimate the continuum (e.g., due to clouds)") |
819 797 | ("wvrflag", |
820 - | value< std::vector<std::string> >(), |
821 - | "Regard this WVR (labelled with either antenna number or antenna name) as bad, and use interpolated values instead") |
798 + | value< std::string >(), |
799 + | "Regard this WVR (labelled with either antenna number or antenna name) as bad, and use interpolated values instead. (Can be comma-separated list without spaces.) ") |
822 800 | ("sourceflag", |
823 801 | value< std::vector<std::string> >(), |
824 802 | "Flag the WVR data for this source and do not produce any phase corrections on it") |
825 803 | ("statfield", |
826 804 | value< std::vector<std::string> >(), |
827 805 | "Compute the statistics (Phase RMS, Disc) on this field only") |
828 806 | ("statsource", |
829 807 | value< std::vector<std::string> >(), |
830 808 | "Compute the statistics (Phase RMS, Disc) on this source only") |
831 809 | ("tie", |
848 826 | "If the fraction of unflagged data for an antenna is below this value (0. to 1.), the antenna is flagged.") |
849 827 | ("usefieldtab", |
850 828 | "Derive the antenna pointing information from the FIELD table instead of the POINTING table.") |
851 829 | ("spw", |
852 830 | value< std::vector<int> >(), |
853 831 | "Only write out corrections for these SPWs.") |
854 832 | ("wvrspw", |
855 833 | value< std::vector<int> >(), |
856 834 | "Only use data from these WVR SPWs.") |
857 835 | ("refant", |
858 - | value< std::vector<std::string> >(), |
859 - | "Use the WVR data from this antenna for calculating the dT/dL parameters.") |
836 + | value<std::string>(), |
837 + | "Use the WVR data from this antenna for calculating the dT/dL parameters. (Can be comma-separated ranked list without spaces.)") |
860 838 | ("offsets", |
861 839 | value<std::string>(), |
862 840 | "Name of the optional input table containing the temperature offsets, e.g. generated by remove_cloud") |
863 841 | ; |
864 842 | p.add("ms", -1); |
865 843 | } |
866 844 | |
867 845 | int main(int argc, char* argv[]) |
868 846 | { |
869 847 | using namespace boost::program_options; |
1058 1036 | interpwvrs, |
1059 1037 | *d, |
1060 1038 | vm["maxdistm"].as<double>(), |
1061 1039 | vm["minnumants"].as<int>(), |
1062 1040 | interpImpossibleAnts); |
1063 1041 | |
1064 1042 | // Determine the reference antenna for dTdL calculation |
1065 1043 | int refant = -1; |
1066 1044 | |
1067 1045 | if (vm.count("refant")){ |
1068 - | LibAIR2::AntSet refants=getAntPars("refant", vm, ms); |
1069 - | for(LibAIR2::AntSet::iterator it=refants.begin(); it != refants.end(); it++){ |
1046 + | std::vector<size_t> refants=getAntParsV("refant", vm, ms); |
1047 + | for(std::vector<size_t>::iterator it=refants.begin(); it != refants.end(); it++){ // |
1070 1048 | if(interpImpossibleAnts.count(*it)==0){ |
1071 1049 | refant = *it; // use the first of the given list of possible ref antennas which was OK or which could be interpolated to |
1072 1050 | break; |
1073 1051 | } |
1074 1052 | else{ |
1075 1053 | std::cout << "Given reference antenna " << *it << "==" << anames.at(*it) |
1076 1054 | << " is flagged and cannot be interpolated." << std::endl; |
1077 1055 | } |
1078 1056 | } |
1079 1057 | if(refant<0){ |