Ignore:
Timestamp:
02/08/13 22:23:22 (12 years ago)
Author:
WataruKawasaki
Message:

New Development: Yes

JIRA Issue: Yes CAS-4794

Ready for Test: Yes

Interface Changes: No

What Interface Changed:

Test Programs:

Put in Release Notes: No

Module(s): sd

Description: functions to apply/write STBaselineTable in which baseline parameters stored.


File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/Scantable.cpp

    r2740 r2767  
    24902490}
    24912491
    2492 void Scantable::polyBaseline(const std::vector<bool>& mask, int order, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile)
    2493 {
     2492std::vector<std::string> Scantable::applyBaselineTable(const std::string& bltable, const std::string& outbltable, const bool outbltableexists, const bool overwrite)
     2493{
     2494  STBaselineTable* btin = new STBaselineTable(bltable);
     2495
     2496  Vector<Bool> applyCol = btin->getApply();
     2497  int nRowBl = applyCol.size();
     2498  if (nRowBl != nrow()) {
     2499    throw(AipsError("Scantable and bltable have different number of rows."));
     2500  }
     2501
     2502  std::vector<std::string> res;
     2503  res.clear();
     2504
     2505  bool outBaselineTable = ((outbltable != "") && (!outbltableexists || overwrite));
     2506  bool bltableidentical = (bltable == outbltable);
     2507  STBaselineTable* btout = new STBaselineTable(*this);
     2508  ROScalarColumn<Double> *tcol = new ROScalarColumn<Double>(table_, "TIME");
     2509  Vector<Double> timeSecCol = tcol->getColumn();
     2510
     2511  for (int whichrow = 0; whichrow < nRowBl; ++whichrow) {
     2512    if (applyCol[whichrow]) {
     2513      std::vector<float> spec = getSpectrum(whichrow);
     2514
     2515      //--channel mask--  maybe the following choices should be available
     2516      std::vector<bool> mask = btin->getMask(whichrow);  //use mask_bltable only (default)
     2517      //std::vector<bool> mask = getMask(whichrow);    // or mask_scantable only
     2518      //std::vector<bool> mask = getCompositeChanMask(whichrow, btin->getMask(whichrow)); // or mask_scantable && mask_bltable
     2519
     2520      STBaselineFunc::FuncName ftype = btin->getFunctionName(whichrow);
     2521      std::vector<int> fpar = btin->getFuncParam(whichrow);
     2522      std::vector<float> params;
     2523      float rms;
     2524      std::vector<float> resfit = doApplyBaselineTable(spec, mask, ftype, fpar, params, rms);
     2525
     2526      setSpectrum(resfit, whichrow);
     2527
     2528      res.push_back(packFittingResults(whichrow, params, rms));
     2529
     2530      if (outBaselineTable) {
     2531        Vector<Int> fparam(fpar.size());
     2532        for (uInt j = 0; j < fparam.size(); ++j) {
     2533          fparam[j] = (Int)fpar[j];
     2534        }
     2535        std::vector<int> maskList0;
     2536        maskList0.clear();
     2537        for (uInt j = 0; j < mask.size(); ++j) {
     2538          if (mask[j]) {
     2539            if ((j == 0)||(j == mask.size()-1)) {
     2540              maskList0.push_back(j);
     2541            } else {
     2542              if ((mask[j])&&(!mask[j-1])) {
     2543                maskList0.push_back(j);
     2544              }
     2545              if ((mask[j])&&(!mask[j+1])) {
     2546                maskList0.push_back(j);
     2547              }
     2548            }
     2549          }
     2550        }
     2551        Vector<uInt> maskList(maskList0.size());
     2552        for (uInt j = 0; j < maskList0.size(); ++j) {
     2553          maskList[j] = (uInt)maskList0[j];
     2554        }
     2555
     2556        if (outbltableexists) {
     2557          if (overwrite) {
     2558            if (bltableidentical) {
     2559              btin->setresult(uInt(whichrow), Vector<Float>(params), Float(rms));
     2560            } else {
     2561              btout->setresult(uInt(whichrow), Vector<Float>(params), Float(rms));
     2562            }
     2563          }
     2564        } else {
     2565          btout->appenddata(uInt(getScan(whichrow)), uInt(getCycle(whichrow)),
     2566                            uInt(getBeam(whichrow)), uInt(getIF(whichrow)), uInt(getPol(whichrow)),
     2567                            uInt(0), timeSecCol[whichrow], Bool(true), ftype, fparam,
     2568                            Vector<Float>(), maskList, Vector<Float>(params),
     2569                            Float(rms), uInt(spec.size()), Float(3.0), uInt(0),
     2570                            Float(0.0), uInt(0), Vector<uInt>());
     2571        }
     2572      }
     2573    }
     2574  }
     2575
     2576  if (outBaselineTable) {
     2577    if (bltableidentical) {
     2578      btin->save(outbltable);
     2579    } else {
     2580      btout->save(outbltable);
     2581    }
     2582  }
     2583  delete btin;
     2584  delete btout;
     2585
     2586  return res;
     2587}
     2588
     2589std::vector<std::string> Scantable::subBaseline(const std::vector<std::string>& blInfoList, const std::string& outbltable, const bool outbltableexists, const bool overwrite)
     2590{
     2591  int nRowBl = blInfoList.size();
     2592  int nRowSt = nrow();
     2593
     2594  std::vector<std::string> res;
     2595  res.clear();
     2596
     2597  bool outBaselineTable = ((outbltable != "") && (!outbltableexists || overwrite));
     2598  if ((outbltable != "") && outbltableexists && !overwrite) {
     2599    throw(AipsError("Cannot overwrite bltable. Set overwrite=True."));
     2600  }
     2601
     2602  STBaselineTable* bt = new STBaselineTable(*this);
     2603  ROScalarColumn<Double> *tcol = new ROScalarColumn<Double>(table_, "TIME");
     2604  Vector<Double> timeSecCol = tcol->getColumn();
     2605
     2606  if (outBaselineTable && !outbltableexists) {
     2607    for (int i = 0; i < nRowSt; ++i) {
     2608      bt->appendbasedata(getScan(i), getCycle(i), getBeam(i), getIF(i), getPol(i),
     2609                         0, timeSecCol[i]);
     2610      bt->setApply(i, false);
     2611    }
     2612  }
     2613
     2614  for (int i = 0; i < nRowBl; ++i) {
     2615    int irow;
     2616    STBaselineFunc::FuncName ftype;
     2617    std::vector<bool> mask;
     2618    std::vector<int> fpar;
     2619    float clipth;
     2620    int clipn;
     2621    bool uself;
     2622    float lfth;
     2623    std::vector<int> lfedge;
     2624    int lfavg;
     2625    parseBlInfo(blInfoList[i], irow, ftype, fpar, mask, clipth, clipn, uself, lfth, lfedge, lfavg);
     2626
     2627    if (irow < nRowSt) {
     2628      std::vector<float> spec = getSpectrum(irow);
     2629      std::vector<float> params;
     2630      float rms;
     2631      std::vector<bool> finalmask;
     2632
     2633      std::vector<float> resfit = doSubtractBaseline(spec, mask, ftype, fpar, params, rms, finalmask, clipth, clipn, uself, irow, lfth, lfedge, lfavg);
     2634      setSpectrum(resfit, irow);
     2635      res.push_back(packFittingResults(irow, params, rms));
     2636
     2637      if (outBaselineTable) {
     2638        Vector<Int> fparam(fpar.size());
     2639        for (uInt j = 0; j < fparam.size(); ++j) {
     2640          fparam[j] = (Int)fpar[j];
     2641        }
     2642        std::vector<int> maskList0;
     2643        maskList0.clear();
     2644        for (uInt j = 0; j < finalmask.size(); ++j) {
     2645          if (finalmask[j]) {
     2646            if ((j == 0)||(j == finalmask.size()-1)) {
     2647              maskList0.push_back(j);
     2648            } else {
     2649              if ((finalmask[j])&&(!finalmask[j-1])) {
     2650                maskList0.push_back(j);
     2651              }
     2652              if ((finalmask[j])&&(!finalmask[j+1])) {
     2653                maskList0.push_back(j);
     2654              }
     2655            }
     2656          }
     2657        }
     2658        Vector<uInt> maskList(maskList0.size());
     2659        for (uInt j = 0; j < maskList0.size(); ++j) {
     2660          maskList[j] = (uInt)maskList0[j];
     2661        }
     2662
     2663        bt->setdata(uInt(irow),
     2664                    uInt(getScan(irow)), uInt(getCycle(irow)),
     2665                    uInt(getBeam(irow)), uInt(getIF(irow)), uInt(getPol(irow)),
     2666                    uInt(0), timeSecCol[irow], Bool(true), ftype, fparam,
     2667                    Vector<Float>(), maskList, Vector<Float>(params),
     2668                    Float(rms), uInt(spec.size()), Float(clipth), uInt(clipn),
     2669                    Float(0.0), uInt(0), Vector<uInt>());
     2670      }
     2671
     2672    }
     2673  }
     2674
     2675  if (outBaselineTable) {
     2676    bt->save(outbltable);
     2677  }
     2678  delete bt;
     2679
     2680  return res;
     2681}
     2682
     2683std::vector<float> Scantable::doApplyBaselineTable(std::vector<float>& spec, std::vector<bool>& mask, const STBaselineFunc::FuncName ftype, std::vector<int>& fpar, std::vector<float>& params, float&rms)
     2684{
     2685  std::vector<bool> finalmask;
     2686  std::vector<int> lfedge;
     2687  return doSubtractBaseline(spec, mask, ftype, fpar, params, rms, finalmask, 0.0, 0, false, 0, 0.0, lfedge, 0);
     2688}
     2689
     2690  std::vector<float> Scantable::doSubtractBaseline(std::vector<float>& spec, std::vector<bool>& mask, const STBaselineFunc::FuncName ftype, std::vector<int>& fpar, std::vector<float>& params, float&rms, std::vector<bool>& finalmask, float clipth, int clipn, bool uself, int irow, float lfth, std::vector<int>& lfedge, int lfavg)
     2691{
     2692  //---replace mask with (mask AND mask_linefinder).
     2693  if (uself) {
     2694    STLineFinder lineFinder = STLineFinder();
     2695    lineFinder.setOptions(lfth, 3, lfavg);
     2696
     2697    int minEdgeSize = getIFNos().size()*2;
     2698    int edgeSize = lfedge.size();
     2699    std::vector<int> currentEdge;
     2700    currentEdge.clear();
     2701    if (edgeSize >= 2) {
     2702      int idx = 0;
     2703      if (edgeSize > 2) {
     2704        if (edgeSize < minEdgeSize) {
     2705          throw(AipsError("Length of edge element info is less than that of IFs"));
     2706        }
     2707        idx = 2 * getIF(irow);
     2708      }
     2709      currentEdge.push_back(lfedge[idx]);
     2710      currentEdge.push_back(lfedge[idx+1]);
     2711    } else {
     2712      throw(AipsError("Wrong length of edge element"));
     2713    }
     2714    lineFinder.setData(spec);
     2715    lineFinder.findLines(getCompositeChanMask(irow, mask), currentEdge, irow);
     2716
     2717    std::vector<bool> lfcompmask = lineFinder.getMask();
     2718    mask.clear();
     2719    mask.resize(lfcompmask.size());
     2720    for (uInt i = 0; i < mask.size(); ++i) {
     2721      mask[i] = lfcompmask[i];
     2722    }
     2723  }
     2724  //---
     2725
     2726  std::vector<float> res;
     2727  if (ftype == STBaselineFunc::Polynomial) {
     2728    res = doPolynomialFitting(spec, mask, fpar[0], params, rms, finalmask, clipth, clipn);
     2729  } else if (ftype == STBaselineFunc::Chebyshev) {
     2730    res = doChebyshevFitting(spec, mask, fpar[0], params, rms, finalmask, clipth, clipn);
     2731  } else if (ftype == STBaselineFunc::CSpline) {
     2732    if (fpar.size() > 1) { // reading from baseline table in which pieceEdges are already calculated and stored.
     2733      res = doCubicSplineFitting(spec, mask, fpar, params, rms, finalmask, clipth, clipn);
     2734    } else {               // usual cspline fitting by giving nPiece only. fpar will be replaced with pieceEdges.
     2735      res = doCubicSplineFitting(spec, mask, fpar[0], fpar, params, rms, finalmask, clipth, clipn);
     2736    }
     2737  } else if (ftype == STBaselineFunc::Sinusoid) {
     2738    res = doSinusoidFitting(spec, mask, fpar, params, rms, finalmask, clipth, clipn);
     2739  }
     2740
     2741  return res;
     2742}
     2743
     2744std::string Scantable::packFittingResults(const int irow, const std::vector<float>& params, const float rms)
     2745{
     2746  // returned value: "irow:params[0],params[1],..,params[n-1]:rms"
     2747  ostringstream os;
     2748  os << irow << ':';
     2749  for (uInt i = 0; i < params.size(); ++i) {
     2750    if (i > 0) {
     2751      os << ',';
     2752    }
     2753    os << params[i];
     2754  }
     2755  os << ':' << rms;
     2756
     2757  return os.str();
     2758}
     2759
     2760void Scantable::parseBlInfo(const std::string& blInfo, int& irow, STBaselineFunc::FuncName& ftype, std::vector<int>& fpar, std::vector<bool>& mask, float& thresClip, int& nIterClip, bool& useLineFinder, float& thresLF, std::vector<int>& edgeLF, int& avgLF)
     2761{
     2762  // The baseline info to be parsed must be column-delimited string like
     2763  // "0:chebyshev:5:3,5,169,174,485,487" where the elements are
     2764  // row number, funcType, funcOrder, maskList, clipThreshold, clipNIter,
     2765  // useLineFinder, lfThreshold, lfEdge and lfChanAvgLimit.
     2766
     2767  std::vector<string> res = splitToStringList(blInfo, ':');
     2768  if (res.size() < 4) {
     2769    throw(AipsError("baseline info has bad format")) ;
     2770  }
     2771
     2772  string ftype0, fpar0, masklist0, uself0, edge0;
     2773  std::vector<int> masklist;
     2774
     2775  stringstream ss;
     2776  ss << res[0];
     2777  ss >> irow;
     2778  ss.clear(); ss.str("");
     2779
     2780  ss << res[1];
     2781  ss >> ftype0;
     2782  if (ftype0 == "poly") {
     2783    ftype = STBaselineFunc::Polynomial;
     2784  } else if (ftype0 == "cspline") {
     2785    ftype = STBaselineFunc::CSpline;
     2786  } else if (ftype0 == "sinusoid") {
     2787    ftype = STBaselineFunc::Sinusoid;
     2788  } else if (ftype0 == "chebyshev") {
     2789    ftype = STBaselineFunc::Chebyshev;
     2790  } else {
     2791    throw(AipsError("invalid function type."));
     2792  }
     2793  ss.clear(); ss.str("");
     2794
     2795  ss << res[2];
     2796  ss >> fpar0;
     2797  fpar = splitToIntList(fpar0, ',');
     2798  ss.clear(); ss.str("");
     2799
     2800  ss << res[3];
     2801  ss >> masklist0;
     2802  mask = getMaskFromMaskList(nchan(getIF(irow)), splitToIntList(masklist0, ','));
     2803
     2804  ss << res[4];
     2805  ss >> thresClip;
     2806  ss.clear(); ss.str("");
     2807
     2808  ss << res[5];
     2809  ss >> nIterClip;
     2810  ss.clear(); ss.str("");
     2811
     2812  ss << res[6];
     2813  ss >> uself0;
     2814  if (uself0 == "true") {
     2815    useLineFinder = true;
     2816  } else {
     2817    useLineFinder = false;
     2818  }
     2819  ss.clear(); ss.str("");
     2820
     2821  if (useLineFinder) {
     2822    ss << res[7];
     2823    ss >> thresLF;
     2824    ss.clear(); ss.str("");
     2825
     2826    ss << res[8];
     2827    ss >> edge0;
     2828    edgeLF = splitToIntList(edge0, ',');
     2829    ss.clear(); ss.str("");
     2830
     2831    ss << res[9];
     2832    ss >> avgLF;
     2833    ss.clear(); ss.str("");
     2834  }
     2835
     2836}
     2837
     2838std::vector<int> Scantable::splitToIntList(const std::string& s, const char delim)
     2839{
     2840  istringstream iss(s);
     2841  string tmp;
     2842  int tmpi;
     2843  std::vector<int> res;
     2844  stringstream ss;
     2845  while (getline(iss, tmp, delim)) {
     2846    ss << tmp;
     2847    ss >> tmpi;
     2848    res.push_back(tmpi);
     2849    ss.clear(); ss.str("");
     2850  }
     2851
     2852  return res;
     2853}
     2854
     2855std::vector<string> Scantable::splitToStringList(const std::string& s, const char delim)
     2856{
     2857  istringstream iss(s);
     2858  std::string tmp;
     2859  std::vector<string> res;
     2860  while (getline(iss, tmp, delim)) {
     2861    res.push_back(tmp);
     2862  }
     2863
     2864  return res;
     2865}
     2866
     2867std::vector<bool> Scantable::getMaskFromMaskList(const int nchan, const std::vector<int>& masklist)
     2868{
     2869  if (masklist.size() % 2 != 0) {
     2870    throw(AipsError("masklist must have even number of elements."));
     2871  }
     2872
     2873  std::vector<bool> res(nchan);
     2874
     2875  for (int i = 0; i < nchan; ++i) {
     2876    res[i] = false;
     2877  }
     2878  for (uInt j = 0; j < masklist.size(); j += 2) {
     2879    for (int i = masklist[j]; i <= masklist[j+1]; ++i) {
     2880      res[i] = true;
     2881    }
     2882  }
     2883
     2884  return res;
     2885}
     2886
     2887void Scantable::polyBaseline(const std::vector<bool>& mask, int order, float thresClip, int nIterClip, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile, const std::string& bltable)
     2888{
     2889  /****
     2890  double TimeStart = mathutil::gettimeofday_sec();
     2891  ****/
     2892
    24942893  try {
    24952894    ofstream ofs;
     
    25112910    }
    25122911
    2513     Fitter fitter = Fitter();
    2514     fitter.setExpression("poly", order);
    2515     //fitter.setIterClipping(thresClip, nIterClip);
    2516 
    2517     int nRow = nrow();
    2518     std::vector<bool> chanMask;
    25192912    bool showProgress;
    25202913    int minNRow;
    25212914    parseProgressInfo(progressInfo, showProgress, minNRow);
    25222915
     2916    int nRow = nrow();
     2917    std::vector<bool> chanMask;
     2918    std::vector<bool> finalChanMask;
     2919    float rms;
     2920
     2921    //---
     2922    bool outBaselintTable = (bltable != "");
     2923    STBaselineTable* bt = new STBaselineTable(*this);
     2924    ROScalarColumn<Double> *tcol = new ROScalarColumn<Double>(table_, "TIME");
     2925    Vector<Double> timeSecCol = tcol->getColumn();
     2926    //---
     2927
    25232928    for (int whichrow = 0; whichrow < nRow; ++whichrow) {
     2929      std::vector<float> sp = getSpectrum(whichrow);
    25242930      chanMask = getCompositeChanMask(whichrow, mask);
    2525       fitBaseline(chanMask, whichrow, fitter);
    2526       setSpectrum((getResidual ? fitter.getResidual() : fitter.getFit()), whichrow);
    2527       outputFittingResult(outLogger, outTextFile, csvFormat, chanMask, whichrow, coordInfo, hasSameNchan, ofs, "polyBaseline()", fitter);
     2931      std::vector<float> params(order+1);
     2932      int nClipped = 0;
     2933      std::vector<float> res = doPolynomialFitting(sp, chanMask, order, params, rms, finalChanMask, nClipped, thresClip, nIterClip, getResidual);
     2934
     2935      //---
     2936      if (outBaselintTable) {
     2937        Vector<Int> fparam(1);
     2938        fparam[0] = order;
     2939        std::vector<int> finalMaskList0;
     2940        finalMaskList0.clear();
     2941        for (uInt i = 0; i < finalChanMask.size(); ++i) {
     2942          if (finalChanMask[i]) {
     2943            if ((i == 0)||(i == finalChanMask.size()-1)) {
     2944              finalMaskList0.push_back(i);
     2945            } else {
     2946              if ((finalChanMask[i])&&(!finalChanMask[i-1])) {
     2947                finalMaskList0.push_back(i);
     2948              }
     2949              if ((finalChanMask[i])&&(!finalChanMask[i+1])) {
     2950                finalMaskList0.push_back(i);
     2951              }
     2952            }
     2953          }
     2954        }
     2955        Vector<uInt> finalMaskList(finalMaskList0.size());
     2956        for (uInt i = 0; i < finalMaskList0.size(); ++i) {
     2957          finalMaskList[i] = (uInt)finalMaskList0[i];
     2958        }
     2959
     2960        bt->appenddata(uInt(getScan(whichrow)), uInt(getCycle(whichrow)), uInt(getBeam(whichrow)), uInt(getIF(whichrow)), uInt(getPol(whichrow)),
     2961                       uInt(0),
     2962                       timeSecCol[whichrow],
     2963                       Bool(true),
     2964                       STBaselineFunc::Polynomial,
     2965                       fparam,
     2966                       Vector<Float>(),
     2967                       finalMaskList,
     2968                       Vector<Float>(params),
     2969                       Float(rms),
     2970                       uInt(sp.size()),
     2971                       Float(thresClip),
     2972                       uInt(nIterClip),
     2973                       Float(0.0),
     2974                       uInt(0),
     2975                       Vector<uInt>());
     2976      } else {
     2977        setSpectrum(res, whichrow);
     2978      }
     2979      //---
     2980
     2981      outputFittingResult(outLogger, outTextFile, csvFormat, chanMask, whichrow, coordInfo, hasSameNchan, ofs, "chebyshevBaseline()", params, nClipped);
    25282982      showProgressOnTerminal(whichrow, nRow, showProgress, minNRow);
    25292983    }
     2984   
     2985    //---
     2986    if (outBaselintTable) {
     2987      bt->save(bltable);
     2988    }
     2989    //---
     2990    delete bt;
    25302991
    25312992    if (outTextFile) ofs.close();
     
    25342995    throw;
    25352996  }
    2536 }
    2537 
    2538 void Scantable::autoPolyBaseline(const std::vector<bool>& mask, int order, const std::vector<int>& edge, float threshold, int chanAvgLimit, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile)
     2997
     2998  /****
     2999  double TimeEnd = mathutil::gettimeofday_sec();
     3000  double elapse1 = TimeEnd - TimeStart;
     3001  std::cout << "poly-new   : " << elapse1 << " (sec.)" << endl;
     3002  ****/
     3003}
     3004
     3005void Scantable::autoPolyBaseline(const std::vector<bool>& mask, int order, float thresClip, int nIterClip, const std::vector<int>& edge, float threshold, int chanAvgLimit, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile, const std::string& bltable)
    25393006{
    25403007  try {
     
    25573024    }
    25583025
    2559     Fitter fitter = Fitter();
    2560     fitter.setExpression("poly", order);
    2561     //fitter.setIterClipping(thresClip, nIterClip);
    2562 
    2563     int nRow = nrow();
    2564     std::vector<bool> chanMask;
     3026    bool showProgress;
     3027    int minNRow;
     3028    parseProgressInfo(progressInfo, showProgress, minNRow);
     3029
    25653030    int minEdgeSize = getIFNos().size()*2;
    25663031    STLineFinder lineFinder = STLineFinder();
    25673032    lineFinder.setOptions(threshold, 3, chanAvgLimit);
    25683033
    2569     bool showProgress;
    2570     int minNRow;
    2571     parseProgressInfo(progressInfo, showProgress, minNRow);
     3034    int nRow = nrow();
     3035    std::vector<bool> chanMask;
     3036    std::vector<bool> finalChanMask;
     3037    float rms;
     3038
     3039    //---
     3040    bool outBaselintTable = (bltable != "");
     3041    STBaselineTable* bt = new STBaselineTable(*this);
     3042    ROScalarColumn<Double> *tcol = new ROScalarColumn<Double>(table_, "TIME");
     3043    Vector<Double> timeSecCol = tcol->getColumn();
     3044    //---
    25723045
    25733046    for (int whichrow = 0; whichrow < nRow; ++whichrow) {
    2574 
    2575       //-------------------------------------------------------
    2576       //chanMask = getCompositeChanMask(whichrow, mask, edge, minEdgeSize, lineFinder);
    2577       //-------------------------------------------------------
     3047      std::vector<float> sp = getSpectrum(whichrow);
     3048      //-- composote given channel mask and flagtra --------
    25783049      int edgeSize = edge.size();
    25793050      std::vector<int> currentEdge;
     3051      currentEdge.clear();
    25803052      if (edgeSize >= 2) {
    25813053        int idx = 0;
     
    25913063        throw(AipsError("Wrong length of edge element"));
    25923064      }
    2593       lineFinder.setData(getSpectrum(whichrow));
     3065      lineFinder.setData(sp);
    25943066      lineFinder.findLines(getCompositeChanMask(whichrow, mask), currentEdge, whichrow);
    25953067      chanMask = lineFinder.getMask();
    2596       //-------------------------------------------------------
    2597 
    2598       fitBaseline(chanMask, whichrow, fitter);
    2599       setSpectrum((getResidual ? fitter.getResidual() : fitter.getFit()), whichrow);
    2600 
    2601       outputFittingResult(outLogger, outTextFile, csvFormat, chanMask, whichrow, coordInfo, hasSameNchan, ofs, "autoPolyBaseline()", fitter);
     3068      //-- composote given channel mask and flagtra END --------
     3069
     3070      std::vector<float> params(order+1);
     3071      int nClipped = 0;
     3072      std::vector<float> res = doPolynomialFitting(sp, chanMask, order, params, rms, finalChanMask, nClipped, thresClip, nIterClip, getResidual);
     3073
     3074      if (outBaselintTable) {
     3075        Vector<Int> fparam(1);
     3076        fparam[0] = order;
     3077        std::vector<int> finalMaskList0;
     3078        finalMaskList0.clear();
     3079        for (uInt i = 0; i < finalChanMask.size(); ++i) {
     3080          if (finalChanMask[i]) {
     3081            if ((i == 0)||(i == finalChanMask.size()-1)) {
     3082              finalMaskList0.push_back(i);
     3083            } else {
     3084              if ((finalChanMask[i])&&(!finalChanMask[i-1])) {
     3085                finalMaskList0.push_back(i);
     3086              }
     3087              if ((finalChanMask[i])&&(!finalChanMask[i+1])) {
     3088                finalMaskList0.push_back(i);
     3089              }
     3090            }
     3091          }
     3092        }
     3093        Vector<uInt> finalMaskList(finalMaskList0.size());
     3094        for (uInt i = 0; i < finalMaskList0.size(); ++i) {
     3095          finalMaskList[i] = (uInt)finalMaskList0[i];
     3096        }
     3097
     3098        Vector<uInt> cEdge(currentEdge.size());
     3099        for (uInt i = 0; i < currentEdge.size(); ++i) {
     3100          cEdge[i] = currentEdge[i];
     3101        }
     3102
     3103        bt->appenddata(uInt(getScan(whichrow)), uInt(getCycle(whichrow)), uInt(getBeam(whichrow)), uInt(getIF(whichrow)), uInt(getPol(whichrow)),
     3104                       uInt(0),
     3105                       timeSecCol[whichrow],
     3106                       Bool(true),
     3107                       STBaselineFunc::Polynomial,
     3108                       fparam,
     3109                       Vector<Float>(),
     3110                       finalMaskList,
     3111                       Vector<Float>(params),
     3112                       Float(rms),
     3113                       uInt(sp.size()),
     3114                       Float(thresClip),
     3115                       uInt(nIterClip),
     3116                       Float(threshold),
     3117                       uInt(chanAvgLimit),
     3118                       cEdge);
     3119      } else {
     3120        setSpectrum(res, whichrow);
     3121      }
     3122
     3123      outputFittingResult(outLogger, outTextFile, csvFormat, chanMask, whichrow, coordInfo, hasSameNchan, ofs, "autoChebyshevBaseline()", params, nClipped);
    26023124      showProgressOnTerminal(whichrow, nRow, showProgress, minNRow);
    26033125    }
     3126
     3127    //---
     3128    if (outBaselintTable) {
     3129      bt->save(bltable);
     3130    }
     3131    //---
     3132    delete bt;
    26043133
    26053134    if (outTextFile) ofs.close();
     
    26103139}
    26113140
    2612 void Scantable::chebyshevBaseline(const std::vector<bool>& mask, int order, float thresClip, int nIterClip, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile)
    2613 {
     3141void Scantable::chebyshevBaseline(const std::vector<bool>& mask, int order, float thresClip, int nIterClip, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile, const std::string& bltable)
     3142{
     3143  //
     3144  double TimeStart = mathutil::gettimeofday_sec();
     3145  //
     3146
    26143147  try {
    26153148    ofstream ofs;
     
    26413174
    26423175    //---
    2643     bool outBaselineParamTable = false;
     3176    bool outBaselintTable = (bltable != "");
    26443177    STBaselineTable* bt = new STBaselineTable(*this);
     3178    ROScalarColumn<Double> *tcol = new ROScalarColumn<Double>(table_, "TIME");
     3179    Vector<Double> timeSecCol = tcol->getColumn();
    26453180    //---
    26463181
     
    26503185      std::vector<float> params(order+1);
    26513186      int nClipped = 0;
    2652       std::vector<float> res = doChebyshevFitting(sp, chanMask, order, params, finalChanMask, rms, nClipped, thresClip, nIterClip, getResidual);
     3187      std::vector<float> res = doChebyshevFitting(sp, chanMask, order, params, rms, finalChanMask, nClipped, thresClip, nIterClip, getResidual);
    26533188
    26543189      //---
    2655       if (outBaselineParamTable) {
     3190      if (outBaselintTable) {
     3191        Vector<Int> fparam(1);
     3192        fparam[0] = order;
     3193        std::vector<int> finalMaskList0;
     3194        finalMaskList0.clear();
     3195        for (uInt i = 0; i < finalChanMask.size(); ++i) {
     3196          if (finalChanMask[i]) {
     3197            if ((i == 0)||(i == finalChanMask.size()-1)) {
     3198              finalMaskList0.push_back(i);
     3199            } else {
     3200              if ((finalChanMask[i])&&(!finalChanMask[i-1])) {
     3201                finalMaskList0.push_back(i);
     3202              }
     3203              if ((finalChanMask[i])&&(!finalChanMask[i+1])) {
     3204                finalMaskList0.push_back(i);
     3205              }
     3206            }
     3207          }
     3208        }
     3209        Vector<uInt> finalMaskList(finalMaskList0.size());
     3210        for (uInt i = 0; i < finalMaskList0.size(); ++i) {
     3211          finalMaskList[i] = (uInt)finalMaskList0[i];
     3212        }
     3213
    26563214        bt->appenddata(uInt(getScan(whichrow)), uInt(getCycle(whichrow)), uInt(getBeam(whichrow)), uInt(getIF(whichrow)), uInt(getPol(whichrow)),
    26573215                       uInt(0),
    2658                        Double(0.0), // <-- Double(getTime(whichrow, false)),
    2659                        uInt(nchan(whichrow)),
     3216                       timeSecCol[whichrow],
     3217                       Bool(true),
    26603218                       STBaselineFunc::Chebyshev,
    2661                        Vector<uInt>(1), // ==> MUST BE Vector<uInt> containing 'order'.
    2662                        Vector<Float>(), // ==> for ffpar. ** dummy **
     3219                       fparam,
     3220                       Vector<Float>(),
     3221                       finalMaskList,
     3222                       Vector<Float>(params),
     3223                       Float(rms),
     3224                       uInt(sp.size()),
     3225                       Float(thresClip),
    26633226                       uInt(nIterClip),
    2664                        Float(thresClip),
    2665                        Vector<uInt>(5), // <-- Vector<uInt>(finalChanMask),
    2666                        Vector<Float>(params),
    2667                        Float(rms));
     3227                       Float(0.0),
     3228                       uInt(0),
     3229                       Vector<uInt>());
    26683230      } else {
    26693231        setSpectrum(res, whichrow);
     
    26763238   
    26773239    //---
    2678     if (outBaselineParamTable) {
    2679       bt->save("chebyparamtable");
     3240    if (outBaselintTable) {
     3241      bt->save(bltable);
    26803242    }
    26813243    //---
     
    26873249    throw;
    26883250  }
     3251
     3252  double TimeEnd = mathutil::gettimeofday_sec();
     3253  double elapse1 = TimeEnd - TimeStart;
     3254  std::cout << "cheby   : " << elapse1 << " (sec.)" << endl;
     3255}
     3256
     3257void Scantable::autoChebyshevBaseline(const std::vector<bool>& mask, int order, float thresClip, int nIterClip, const std::vector<int>& edge, float threshold, int chanAvgLimit, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile, const std::string& bltable)
     3258{
     3259  try {
     3260    ofstream ofs;
     3261    String coordInfo = "";
     3262    bool hasSameNchan = true;
     3263    bool outTextFile = false;
     3264    bool csvFormat = false;
     3265
     3266    if (blfile != "") {
     3267      csvFormat = (blfile.substr(0, 1) == "T");
     3268      ofs.open(blfile.substr(1).c_str(), ios::out | ios::app);
     3269      if (ofs) outTextFile = true;
     3270    }
     3271
     3272    if (outLogger || outTextFile) {
     3273      coordInfo = getCoordInfo()[0];
     3274      if (coordInfo == "") coordInfo = "channel";
     3275      hasSameNchan = hasSameNchanOverIFs();
     3276    }
     3277
     3278    bool showProgress;
     3279    int minNRow;
     3280    parseProgressInfo(progressInfo, showProgress, minNRow);
     3281
     3282    int minEdgeSize = getIFNos().size()*2;
     3283    STLineFinder lineFinder = STLineFinder();
     3284    lineFinder.setOptions(threshold, 3, chanAvgLimit);
     3285
     3286    int nRow = nrow();
     3287    std::vector<bool> chanMask;
     3288    std::vector<bool> finalChanMask;
     3289    float rms;
     3290
     3291    //---
     3292    bool outBaselintTable = (bltable != "");
     3293    STBaselineTable* bt = new STBaselineTable(*this);
     3294    ROScalarColumn<Double> *tcol = new ROScalarColumn<Double>(table_, "TIME");
     3295    Vector<Double> timeSecCol = tcol->getColumn();
     3296    //---
     3297
     3298    for (int whichrow = 0; whichrow < nRow; ++whichrow) {
     3299      std::vector<float> sp = getSpectrum(whichrow);
     3300      //-- composote given channel mask and flagtra --------
     3301      int edgeSize = edge.size();
     3302      std::vector<int> currentEdge;
     3303      currentEdge.clear();
     3304      if (edgeSize >= 2) {
     3305        int idx = 0;
     3306        if (edgeSize > 2) {
     3307          if (edgeSize < minEdgeSize) {
     3308            throw(AipsError("Length of edge element info is less than that of IFs"));
     3309          }
     3310          idx = 2 * getIF(whichrow);
     3311        }
     3312        currentEdge.push_back(edge[idx]);
     3313        currentEdge.push_back(edge[idx+1]);
     3314      } else {
     3315        throw(AipsError("Wrong length of edge element"));
     3316      }
     3317      lineFinder.setData(sp);
     3318      lineFinder.findLines(getCompositeChanMask(whichrow, mask), currentEdge, whichrow);
     3319      chanMask = lineFinder.getMask();
     3320      //-- composote given channel mask and flagtra END --------
     3321
     3322      std::vector<float> params(order+1);
     3323      int nClipped = 0;
     3324      std::vector<float> res = doChebyshevFitting(sp, chanMask, order, params, rms, finalChanMask, nClipped, thresClip, nIterClip, getResidual);
     3325
     3326      if (outBaselintTable) {
     3327        Vector<Int> fparam(1);
     3328        fparam[0] = order;
     3329        std::vector<int> finalMaskList0;
     3330        finalMaskList0.clear();
     3331        for (uInt i = 0; i < finalChanMask.size(); ++i) {
     3332          if (finalChanMask[i]) {
     3333            if ((i == 0)||(i == finalChanMask.size()-1)) {
     3334              finalMaskList0.push_back(i);
     3335            } else {
     3336              if ((finalChanMask[i])&&(!finalChanMask[i-1])) {
     3337                finalMaskList0.push_back(i);
     3338              }
     3339              if ((finalChanMask[i])&&(!finalChanMask[i+1])) {
     3340                finalMaskList0.push_back(i);
     3341              }
     3342            }
     3343          }
     3344        }
     3345        Vector<uInt> finalMaskList(finalMaskList0.size());
     3346        for (uInt i = 0; i < finalMaskList0.size(); ++i) {
     3347          finalMaskList[i] = (uInt)finalMaskList0[i];
     3348        }
     3349
     3350        Vector<uInt> cEdge(currentEdge.size());
     3351        for (uInt i = 0; i < currentEdge.size(); ++i) {
     3352          cEdge[i] = currentEdge[i];
     3353        }
     3354
     3355        bt->appenddata(uInt(getScan(whichrow)), uInt(getCycle(whichrow)), uInt(getBeam(whichrow)), uInt(getIF(whichrow)), uInt(getPol(whichrow)),
     3356                       uInt(0),
     3357                       timeSecCol[whichrow],
     3358                       Bool(true),
     3359                       STBaselineFunc::Chebyshev,
     3360                       fparam,
     3361                       Vector<Float>(),
     3362                       finalMaskList,
     3363                       Vector<Float>(params),
     3364                       Float(rms),
     3365                       uInt(sp.size()),
     3366                       Float(thresClip),
     3367                       uInt(nIterClip),
     3368                       Float(threshold),
     3369                       uInt(chanAvgLimit),
     3370                       cEdge);
     3371      } else {
     3372        setSpectrum(res, whichrow);
     3373      }
     3374
     3375      outputFittingResult(outLogger, outTextFile, csvFormat, chanMask, whichrow, coordInfo, hasSameNchan, ofs, "autoChebyshevBaseline()", params, nClipped);
     3376      showProgressOnTerminal(whichrow, nRow, showProgress, minNRow);
     3377    }
     3378
     3379    //---
     3380    if (outBaselintTable) {
     3381      bt->save(bltable);
     3382    }
     3383    //---
     3384    delete bt;
     3385
     3386    if (outTextFile) ofs.close();
     3387
     3388  } catch (...) {
     3389    throw;
     3390  }
    26893391}
    26903392
    26913393double Scantable::calculateModelSelectionCriteria(const std::string& valname, const std::string& blfunc, int order, const std::vector<bool>& inMask, int whichrow, bool useLineFinder, const std::vector<int>& edge, float threshold, int chanAvgLimit)
    26923394{
     3395  std::vector<float> sp = getSpectrum(whichrow);
     3396  std::vector<bool> chanMask;
     3397  chanMask.clear();
     3398
    26933399  if (useLineFinder) {
    26943400    int minEdgeSize = getIFNos().size()*2;
    26953401
    2696 
    26973402    int edgeSize = edge.size();
    26983403    std::vector<int> currentEdge;
     3404    currentEdge.clear();
    26993405    if (edgeSize >= 2) {
    27003406      int idx = 0;
     
    27123418
    27133419    STLineFinder lineFinder = STLineFinder();
    2714     std::vector<float> sp = getSpectrum(whichrow);
    27153420    lineFinder.setData(sp);
    27163421    lineFinder.setOptions(threshold, 3, chanAvgLimit);
    27173422    lineFinder.findLines(getCompositeChanMask(whichrow, inMask), currentEdge, whichrow);
    2718     std::vector<bool> chanMask = lineFinder.getMask();
    2719    
    2720     return doCalculateModelSelectionCriteria(valname, sp, chanMask, blfunc, order);
     3423    chanMask = lineFinder.getMask();
    27213424
    27223425  } else {
    2723     return doCalculateModelSelectionCriteria(valname, getSpectrum(whichrow), getCompositeChanMask(whichrow, inMask), blfunc, order);
    2724   }
    2725 
     3426
     3427    chanMask = getCompositeChanMask(whichrow, inMask);
     3428  }
     3429
     3430  return doCalculateModelSelectionCriteria(valname, sp, chanMask, blfunc, order);
    27263431}
    27273432
     
    27333438  float rms;
    27343439  int nClipped = 0;
    2735   float thresClip = 0.0;
    2736   int nIterClip = 0;
    27373440  std::vector<float> res;
    2738   if (blfunc == "chebyshev") {
     3441  if (blfunc == "poly") {
    27393442    nparam = order + 1;
    2740     res = doChebyshevFitting(spec, mask, order, params, finalChanMask, rms, nClipped, thresClip, nIterClip, true);
     3443    res = doPolynomialFitting(spec, mask, order, params, rms, finalChanMask, nClipped);
     3444  } else if (blfunc == "chebyshev") {
     3445    nparam = order + 1;
     3446    res = doChebyshevFitting(spec, mask, order, params, rms, finalChanMask, nClipped);
     3447  } else if (blfunc == "cspline") {
     3448    std::vector<int> pieceEdges;//(order+1);  //order = npiece
     3449    nparam = order + 3;
     3450    //params.resize(4*order);
     3451    res = doCubicSplineFitting(spec, mask, order, false, pieceEdges, params, rms, finalChanMask, nClipped);
    27413452  } else if (blfunc == "sinusoid") {
    27423453    std::vector<int> nWaves;
     
    27463457    }
    27473458    nparam = 2*order + 1;  // order = nwave
    2748     res = doSinusoidFitting(spec, mask, nWaves, params, nClipped, thresClip, nIterClip, true);
    2749   } else if (blfunc == "cspline") {
    2750     std::vector<int> pieceEdges(order+1);  //order = npiece
    2751     nparam = order + 3;
    2752     params.resize(4*order);
    2753     res = doCubicSplineFitting(spec, mask, order, pieceEdges, params, nClipped, thresClip, nIterClip, true);
     3459    res = doSinusoidFitting(spec, mask, nWaves, params, rms, finalChanMask, nClipped);
    27543460  } else {
    2755     throw(AipsError("blfunc must be chebyshev, cspline or sinusoid."));
     3461    throw(AipsError("blfunc must be poly, chebyshev, cspline or sinusoid."));
    27563462  }
    27573463
     
    27773483    double aic = nusedchan * (log(2.0 * PI * msq) + 1.0) + 2.0 * nparam;
    27783484
    2779     // Corrected AIC by Sugiura(1978)
     3485    // Corrected AIC by Sugiura(1978) (AICc)
    27803486    if (valname == "aicc") {
    27813487      if (nusedchan - nparam - 1 <= 0) {
     
    28033509}
    28043510
    2805 void Scantable::autoChebyshevBaseline(const std::vector<bool>& mask, int order, float thresClip, int nIterClip, const std::vector<int>& edge, float threshold, int chanAvgLimit, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile)
    2806 {
    2807   try {
    2808     ofstream ofs;
    2809     String coordInfo = "";
    2810     bool hasSameNchan = true;
    2811     bool outTextFile = false;
    2812     bool csvFormat = false;
    2813 
    2814     if (blfile != "") {
    2815       csvFormat = (blfile.substr(0, 1) == "T");
    2816       ofs.open(blfile.substr(1).c_str(), ios::out | ios::app);
    2817       if (ofs) outTextFile = true;
    2818     }
    2819 
    2820     if (outLogger || outTextFile) {
    2821       coordInfo = getCoordInfo()[0];
    2822       if (coordInfo == "") coordInfo = "channel";
    2823       hasSameNchan = hasSameNchanOverIFs();
    2824     }
    2825 
    2826     int nRow = nrow();
    2827     std::vector<bool> chanMask;
    2828     int minEdgeSize = getIFNos().size()*2;
    2829     STLineFinder lineFinder = STLineFinder();
    2830     lineFinder.setOptions(threshold, 3, chanAvgLimit);
    2831 
    2832     bool showProgress;
    2833     int minNRow;
    2834     parseProgressInfo(progressInfo, showProgress, minNRow);
    2835 
    2836     std::vector<bool> finalChanMask;
    2837     float rms;
    2838 
    2839     for (int whichrow = 0; whichrow < nRow; ++whichrow) {
    2840       std::vector<float> sp = getSpectrum(whichrow);
    2841 
    2842       //-------------------------------------------------------
    2843       //chanMask = getCompositeChanMask(whichrow, mask, edge, minEdgeSize, lineFinder);
    2844       //-------------------------------------------------------
    2845       int edgeSize = edge.size();
    2846       std::vector<int> currentEdge;
    2847       if (edgeSize >= 2) {
    2848         int idx = 0;
    2849         if (edgeSize > 2) {
    2850           if (edgeSize < minEdgeSize) {
    2851             throw(AipsError("Length of edge element info is less than that of IFs"));
    2852           }
    2853           idx = 2 * getIF(whichrow);
    2854         }
    2855         currentEdge.push_back(edge[idx]);
    2856         currentEdge.push_back(edge[idx+1]);
    2857       } else {
    2858         throw(AipsError("Wrong length of edge element"));
    2859       }
    2860       //lineFinder.setData(getSpectrum(whichrow));
    2861       lineFinder.setData(sp);
    2862       lineFinder.findLines(getCompositeChanMask(whichrow, mask), currentEdge, whichrow);
    2863       chanMask = lineFinder.getMask();
    2864       //-------------------------------------------------------
    2865 
    2866 
    2867       //fitBaseline(chanMask, whichrow, fitter);
    2868       //setSpectrum((getResidual ? fitter.getResidual() : fitter.getFit()), whichrow);
    2869       std::vector<float> params(order+1);
    2870       int nClipped = 0;
    2871       std::vector<float> res = doChebyshevFitting(sp, chanMask, order, params, finalChanMask, rms, nClipped, thresClip, nIterClip, getResidual);
    2872       setSpectrum(res, whichrow);
    2873 
    2874       outputFittingResult(outLogger, outTextFile, csvFormat, chanMask, whichrow, coordInfo, hasSameNchan, ofs, "autoChebyshevBaseline()", params, nClipped);
    2875       showProgressOnTerminal(whichrow, nRow, showProgress, minNRow);
    2876     }
    2877 
    2878     if (outTextFile) ofs.close();
    2879 
    2880   } catch (...) {
    2881     throw;
    2882   }
    2883 }
    2884 
    2885   /*
    2886 double Scantable::getChebyshevPolynomial(int n, double x) {
    2887   if ((x < -1.0)||(x > 1.0)) {
    2888     throw(AipsError("out of definition range (-1 <= x <= 1)."));
    2889   } else if (n < 0) {
    2890     throw(AipsError("the order must be zero or positive."));
    2891   } else if (n == 0) {
     3511double Scantable::getNormalPolynomial(int n, double x) {
     3512  if (n == 0) {
    28923513    return 1.0;
    2893   } else if (n == 1) {
    2894     return x;
     3514  } else if (n > 0) {
     3515    double res = 1.0;
     3516    for (int i = 0; i < n; ++i) {
     3517      res *= x;
     3518    }
     3519    return res;
    28953520  } else {
    2896     return 2.0*x*getChebyshevPolynomial(n-1, x) - getChebyshevPolynomial(n-2, x);
    2897   }
    2898 }
    2899   */
     3521    if (x == 0.0) {
     3522      throw(AipsError("infinity result: x=0 given for negative power."));
     3523    } else {
     3524      return pow(x, (double)n);
     3525    }
     3526  }
     3527}
     3528
    29003529double Scantable::getChebyshevPolynomial(int n, double x) {
    29013530  if ((x < -1.0)||(x > 1.0)) {
     
    29393568}
    29403569
    2941 std::vector<float> Scantable::doChebyshevFitting(const std::vector<float>& data, const std::vector<bool>& mask, int order, std::vector<float>& params, std::vector<bool>& finalMask, float& rms, int& nClipped, float thresClip, int nIterClip, bool getResidual)
     3570std::vector<float> Scantable::doPolynomialFitting(const std::vector<float>& data, const std::vector<bool>& mask, int order, std::vector<float>& params, float& rms, std::vector<bool>& finalmask, float clipth, int clipn)
     3571{
     3572  int nClipped = 0;
     3573  return doPolynomialFitting(data, mask, order, params, rms, finalmask, nClipped, clipth, clipn);
     3574}
     3575
     3576std::vector<float> Scantable::doPolynomialFitting(const std::vector<float>& data, const std::vector<bool>& mask, int order, std::vector<float>& params, float& rms, std::vector<bool>& finalMask, int& nClipped, float thresClip, int nIterClip, bool getResidual)
     3577{
     3578  return doLeastSquareFitting(data, mask, &Scantable::getNormalPolynomial, order, params, rms, finalMask, nClipped, thresClip, nIterClip, getResidual);
     3579}
     3580
     3581std::vector<float> Scantable::doChebyshevFitting(const std::vector<float>& data, const std::vector<bool>& mask, int order, std::vector<float>& params, float& rms, std::vector<bool>& finalmask, float clipth, int clipn)
     3582{
     3583  int nClipped = 0;
     3584  return doChebyshevFitting(data, mask, order, params, rms, finalmask, nClipped, clipth, clipn);
     3585}
     3586
     3587std::vector<float> Scantable::doChebyshevFitting(const std::vector<float>& data, const std::vector<bool>& mask, int order, std::vector<float>& params, float& rms, std::vector<bool>& finalMask, int& nClipped, float thresClip, int nIterClip, bool getResidual)
     3588{
     3589  return doLeastSquareFitting(data, mask, &Scantable::getChebyshevPolynomial, order, params, rms, finalMask, nClipped, thresClip, nIterClip, getResidual);
     3590}
     3591
     3592std::vector<float> Scantable::doLeastSquareFitting(const std::vector<float>& data, const std::vector<bool>& mask, double (Scantable::*pfunc)(int, double), int order, std::vector<float>& params, float& rms, std::vector<bool>& finalMask, int& nClipped, float thresClip, int nIterClip, bool getResidual)
    29423593{
    29433594  if (data.size() != mask.size()) {
     
    29453596  }
    29463597  if (order < 0) {
    2947     throw(AipsError("maximum order of Chebyshev polynomial must not be negative."));
     3598    throw(AipsError("maximum order of polynomial must not be negative."));
    29483599  }
    29493600
     
    29713622  //          xArray.size() is nDOF and xArray[*].size() is nChan.
    29723623  //          Each xArray element are as follows:
     3624  //
     3625  //          (for normal polynomials)
     3626  //          xArray[0]   = {1.0,   1.0,   1.0,   ..., 1.0},
     3627  //          xArray[1]   = {0.0,   1.0,   2.0,   ..., (nChan-1)}
     3628  //          xArray[n-1] = ...,
     3629  //          xArray[n]   = {0.0^n, 1.0^n, 2.0^n, ..., (nChan-1)^n}
     3630  //          where (0 <= n <= order)
     3631  //
     3632  //          (for Chebyshev polynomials)
    29733633  //          xArray[0]   = {T0(-1), T0(2/(nChan-1)-1), T0(4/(nChan-1)-1), ..., T0(1)},
    29743634  //          xArray[n-1] = ...,
     
    29763636  //          where (0 <= n <= order),
    29773637  std::vector<std::vector<double> > xArray;
     3638  double xFactor, xShift;
     3639  if (pfunc == &Scantable::getChebyshevPolynomial) {
     3640    xFactor = 2.0/(double)(nChan - 1);
     3641    xShift  = -1.0;
     3642  } else {
     3643    xFactor = 1.0;
     3644    xShift  = 0.0;
     3645  }
    29783646  for (int i = 0; i < nDOF; ++i) {
    2979     double xFactor = 2.0/(double)(nChan - 1);
    29803647    std::vector<double> xs;
    29813648    xs.clear();
    29823649    for (int j = 0; j < nChan; ++j) {
    2983       xs.push_back(getChebyshevPolynomial(i, xFactor*(double)j-1.0));
     3650      xs.push_back((this->*pfunc)(i, xFactor*(double)j + xShift));
    29843651    }
    29853652    xArray.push_back(xs);
     
    30633730      }
    30643731    }
    3065     //compute a vector y which consists of the coefficients of the sinusoids forming the
    3066     //best-fit curves (a0,s1,c1,s2,c2,...), where a0 is constant and s* and c* are of sine
    3067     //and cosine functions, respectively.
     3732    //compute a vector y which consists of the coefficients of Chebyshev polynomials.
    30683733    std::vector<double> y;
    30693734    params.clear();
     
    31183783
    31193784  std::vector<float> result;
     3785  result.clear();
    31203786  if (getResidual) {
    31213787    for (int i = 0; i < nChan; ++i) {
     
    31313797}
    31323798
    3133 void Scantable::cubicSplineBaseline(const std::vector<bool>& mask, int nPiece, float thresClip, int nIterClip, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile)
    3134 {
    3135   /*************
    3136   double totTimeStart, totTimeEnd, blTimeStart, blTimeEnd, ioTimeStart, ioTimeEnd, msTimeStart, msTimeEnd, seTimeStart, seTimeEnd, otTimeStart, otTimeEnd, prTimeStart, prTimeEnd;
    3137   double elapseMs = 0.0;
    3138   double elapseSe = 0.0;
    3139   double elapseOt = 0.0;
    3140   double elapsePr = 0.0;
    3141   double elapseBl = 0.0;
    3142   double elapseIo = 0.0;
    3143   totTimeStart = mathutil::gettimeofday_sec();
    3144   *************/
    3145 
     3799void Scantable::cubicSplineBaseline(const std::vector<bool>& mask, int nPiece, float thresClip, int nIterClip, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile, const std::string& bltable)
     3800{
    31463801  try {
    31473802    ofstream ofs;
     
    31633818    }
    31643819
    3165     //Fitter fitter = Fitter();
    3166     //fitter.setExpression("cspline", nPiece);
    3167     //fitter.setIterClipping(thresClip, nIterClip);
    3168 
    31693820    bool showProgress;
    31703821    int minNRow;
     
    31733824    int nRow = nrow();
    31743825    std::vector<bool> chanMask;
    3175 
    3176     //--------------------------------
     3826    std::vector<bool> finalChanMask;
     3827    float rms;
     3828
     3829    //---
     3830    bool outBaselintTable = (bltable != "");
     3831    STBaselineTable* bt = new STBaselineTable(*this);
     3832    ROScalarColumn<Double> *tcol = new ROScalarColumn<Double>(table_, "TIME");
     3833    Vector<Double> timeSecCol = tcol->getColumn();
     3834    //---
     3835
     3836
    31773837    for (int whichrow = 0; whichrow < nRow; ++whichrow) {
    3178       /******************
    3179       ioTimeStart = mathutil::gettimeofday_sec();
    3180       **/
    31813838      std::vector<float> sp = getSpectrum(whichrow);
    3182       /**
    3183       ioTimeEnd = mathutil::gettimeofday_sec();
    3184       elapseIo += (double)(ioTimeEnd - ioTimeStart);
    3185       msTimeStart = mathutil::gettimeofday_sec();
    3186       ******************/
    3187 
    31883839      chanMask = getCompositeChanMask(whichrow, mask);
    3189 
    3190       /**
    3191       msTimeEnd = mathutil::gettimeofday_sec();
    3192       elapseMs += (double)(msTimeEnd - msTimeStart);
    3193       blTimeStart = mathutil::gettimeofday_sec();
    3194       **/
    3195 
    3196       //fitBaseline(chanMask, whichrow, fitter);
    3197       //setSpectrum((getResidual ? fitter.getResidual() : fitter.getFit()), whichrow);
    3198       std::vector<int> pieceEdges(nPiece+1);
    3199       std::vector<float> params(nPiece*4);
     3840      std::vector<int> pieceEdges;//(nPiece+1);
     3841      std::vector<float> params;//(nPiece*4);
    32003842      int nClipped = 0;
    3201       std::vector<float> res = doCubicSplineFitting(sp, chanMask, nPiece, pieceEdges, params, nClipped, thresClip, nIterClip, getResidual);
    3202 
    3203       /**
    3204       blTimeEnd = mathutil::gettimeofday_sec();
    3205       elapseBl += (double)(blTimeEnd - blTimeStart);
    3206       seTimeStart = mathutil::gettimeofday_sec();
    3207       **/
    3208 
    3209 
    3210       setSpectrum(res, whichrow);
    3211       //
    3212 
    3213       /**
    3214       seTimeEnd = mathutil::gettimeofday_sec();
    3215       elapseSe += (double)(seTimeEnd - seTimeStart);
    3216       otTimeStart = mathutil::gettimeofday_sec();
    3217       **/
     3843      std::vector<float> res = doCubicSplineFitting(sp, chanMask, nPiece, false, pieceEdges, params, rms, finalChanMask, nClipped, thresClip, nIterClip, getResidual);
     3844
     3845      //---
     3846      if (outBaselintTable) {
     3847        Vector<Int> fparam(nPiece);
     3848        for (uInt i = 0; i < fparam.size(); ++i) {
     3849          fparam[i] = pieceEdges[i];
     3850        }
     3851        std::vector<int> finalMaskList0;
     3852        finalMaskList0.clear();
     3853        for (uInt i = 0; i < finalChanMask.size(); ++i) {
     3854          if (finalChanMask[i]) {
     3855            if ((i == 0)||(i == finalChanMask.size()-1)) {
     3856              finalMaskList0.push_back(i);
     3857            } else {
     3858              if ((finalChanMask[i])&&(!finalChanMask[i-1])) {
     3859                finalMaskList0.push_back(i);
     3860              }
     3861              if ((finalChanMask[i])&&(!finalChanMask[i+1])) {
     3862                finalMaskList0.push_back(i);
     3863              }
     3864            }
     3865          }
     3866        }
     3867        Vector<uInt> finalMaskList(finalMaskList0.size());
     3868        for (uInt i = 0; i < finalMaskList0.size(); ++i) {
     3869          finalMaskList[i] = (uInt)finalMaskList0[i];
     3870        }
     3871
     3872        bt->appenddata(uInt(getScan(whichrow)), uInt(getCycle(whichrow)), uInt(getBeam(whichrow)), uInt(getIF(whichrow)), uInt(getPol(whichrow)),
     3873                       uInt(0),
     3874                       timeSecCol[whichrow],
     3875                       Bool(true),
     3876                       STBaselineFunc::CSpline,
     3877                       fparam,
     3878                       Vector<Float>(),
     3879                       finalMaskList,
     3880                       Vector<Float>(params),
     3881                       Float(rms),
     3882                       uInt(sp.size()),
     3883                       Float(thresClip),
     3884                       uInt(nIterClip),
     3885                       Float(0.0),
     3886                       uInt(0),
     3887                       Vector<uInt>());
     3888      } else {
     3889        setSpectrum(res, whichrow);
     3890      }
     3891      //---
    32183892
    32193893      outputFittingResult(outLogger, outTextFile, csvFormat, chanMask, whichrow, coordInfo, hasSameNchan, ofs, "cubicSplineBaseline()", pieceEdges, params, nClipped);
    3220 
    3221       /**
    3222       otTimeEnd = mathutil::gettimeofday_sec();
    3223       elapseOt += (double)(otTimeEnd - otTimeStart);
    3224       prTimeStart = mathutil::gettimeofday_sec();
    3225       **/
    3226 
    32273894      showProgressOnTerminal(whichrow, nRow, showProgress, minNRow);
    3228 
    3229       /******************
    3230       prTimeEnd = mathutil::gettimeofday_sec();
    3231       elapsePr += (double)(prTimeEnd - prTimeStart);
    3232       ******************/
    3233     }
    3234     //--------------------------------
     3895    }
    32353896   
     3897    //---
     3898    if (outBaselintTable) {
     3899      bt->save(bltable);
     3900    }
     3901    //---
     3902    delete bt;
     3903
    32363904    if (outTextFile) ofs.close();
    32373905
     
    32393907    throw;
    32403908  }
    3241   /***************
    3242   totTimeEnd = mathutil::gettimeofday_sec();
    3243   std::cout << "io    : " << elapseIo << " (sec.)" << endl;
    3244   std::cout << "ms    : " << elapseMs << " (sec.)" << endl;
    3245   std::cout << "bl    : " << elapseBl << " (sec.)" << endl;
    3246   std::cout << "se    : " << elapseSe << " (sec.)" << endl;
    3247   std::cout << "ot    : " << elapseOt << " (sec.)" << endl;
    3248   std::cout << "pr    : " << elapsePr << " (sec.)" << endl;
    3249   std::cout << "total : " << (double)(totTimeEnd - totTimeStart) << " (sec.)" << endl;
    3250   ***************/
    3251 }
    3252 
    3253 void Scantable::autoCubicSplineBaseline(const std::vector<bool>& mask, int nPiece, float thresClip, int nIterClip, const std::vector<int>& edge, float threshold, int chanAvgLimit, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile)
     3909}
     3910
     3911void Scantable::autoCubicSplineBaseline(const std::vector<bool>& mask, int nPiece, float thresClip, int nIterClip, const std::vector<int>& edge, float threshold, int chanAvgLimit, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile, const std::string& bltable)
    32543912{
    32553913  try {
     
    32723930    }
    32733931
    3274     //Fitter fitter = Fitter();
    3275     //fitter.setExpression("cspline", nPiece);
    3276     //fitter.setIterClipping(thresClip, nIterClip);
    3277 
    3278     int nRow = nrow();
    3279     std::vector<bool> chanMask;
     3932    bool showProgress;
     3933    int minNRow;
     3934    parseProgressInfo(progressInfo, showProgress, minNRow);
     3935
    32803936    int minEdgeSize = getIFNos().size()*2;
    32813937    STLineFinder lineFinder = STLineFinder();
    32823938    lineFinder.setOptions(threshold, 3, chanAvgLimit);
    32833939
    3284     bool showProgress;
    3285     int minNRow;
    3286     parseProgressInfo(progressInfo, showProgress, minNRow);
     3940    int nRow = nrow();
     3941    std::vector<bool> chanMask;
     3942    std::vector<bool> finalChanMask;
     3943    float rms;
     3944
     3945    //---
     3946    bool outBaselintTable = (bltable != "");
     3947    STBaselineTable* bt = new STBaselineTable(*this);
     3948    ROScalarColumn<Double> *tcol = new ROScalarColumn<Double>(table_, "TIME");
     3949    Vector<Double> timeSecCol = tcol->getColumn();
     3950    //---
    32873951
    32883952    for (int whichrow = 0; whichrow < nRow; ++whichrow) {
    32893953      std::vector<float> sp = getSpectrum(whichrow);
    3290 
    3291       //-------------------------------------------------------
    3292       //chanMask = getCompositeChanMask(whichrow, mask, edge, minEdgeSize, lineFinder);
    3293       //-------------------------------------------------------
     3954      //-- composote given channel mask and flagtra --------
    32943955      int edgeSize = edge.size();
    32953956      std::vector<int> currentEdge;
     3957      currentEdge.clear();
    32963958      if (edgeSize >= 2) {
    32973959        int idx = 0;
     
    33073969        throw(AipsError("Wrong length of edge element"));
    33083970      }
    3309       //lineFinder.setData(getSpectrum(whichrow));
    33103971      lineFinder.setData(sp);
    33113972      lineFinder.findLines(getCompositeChanMask(whichrow, mask), currentEdge, whichrow);
    33123973      chanMask = lineFinder.getMask();
    3313       //-------------------------------------------------------
    3314 
    3315 
    3316       //fitBaseline(chanMask, whichrow, fitter);
    3317       //setSpectrum((getResidual ? fitter.getResidual() : fitter.getFit()), whichrow);
    3318       std::vector<int> pieceEdges(nPiece+1);
    3319       std::vector<float> params(nPiece*4);
     3974      //-- composote given channel mask and flagtra END --------
     3975
     3976      std::vector<int> pieceEdges;//(nPiece+1);
     3977      std::vector<float> params;//(nPiece*4);
    33203978      int nClipped = 0;
    3321       std::vector<float> res = doCubicSplineFitting(sp, chanMask, nPiece, pieceEdges, params, nClipped, thresClip, nIterClip, getResidual);
    3322       setSpectrum(res, whichrow);
    3323       //
     3979      std::vector<float> res = doCubicSplineFitting(sp, chanMask, nPiece, false, pieceEdges, params, rms, finalChanMask, nClipped, thresClip, nIterClip, getResidual);
     3980
     3981      if (outBaselintTable) {
     3982        Vector<Int> fparam(nPiece);
     3983        for (uInt i = 0; i < fparam.size(); ++i) {
     3984          fparam[i] = pieceEdges[i];
     3985        }
     3986        std::vector<int> finalMaskList0;
     3987        finalMaskList0.clear();
     3988        for (uInt i = 0; i < finalChanMask.size(); ++i) {
     3989          if (finalChanMask[i]) {
     3990            if ((i == 0)||(i == finalChanMask.size()-1)) {
     3991              finalMaskList0.push_back(i);
     3992            } else {
     3993              if ((finalChanMask[i])&&(!finalChanMask[i-1])) {
     3994                finalMaskList0.push_back(i);
     3995              }
     3996              if ((finalChanMask[i])&&(!finalChanMask[i+1])) {
     3997                finalMaskList0.push_back(i);
     3998              }
     3999            }
     4000          }
     4001        }
     4002        Vector<uInt> finalMaskList(finalMaskList0.size());
     4003        for (uInt i = 0; i < finalMaskList0.size(); ++i) {
     4004          finalMaskList[i] = (uInt)finalMaskList0[i];
     4005        }
     4006
     4007        Vector<uInt> cEdge(currentEdge.size());
     4008        for (uInt i = 0; i < currentEdge.size(); ++i) {
     4009          cEdge[i] = currentEdge[i];
     4010        }
     4011
     4012        bt->appenddata(uInt(getScan(whichrow)), uInt(getCycle(whichrow)), uInt(getBeam(whichrow)), uInt(getIF(whichrow)), uInt(getPol(whichrow)),
     4013                       uInt(0),
     4014                       timeSecCol[whichrow],
     4015                       Bool(true),
     4016                       STBaselineFunc::CSpline,
     4017                       fparam,
     4018                       Vector<Float>(),
     4019                       finalMaskList,
     4020                       Vector<Float>(params),
     4021                       Float(rms),
     4022                       uInt(sp.size()),
     4023                       Float(thresClip),
     4024                       uInt(nIterClip),
     4025                       Float(threshold),
     4026                       uInt(chanAvgLimit),
     4027                       cEdge);
     4028      } else {
     4029        setSpectrum(res, whichrow);
     4030      }
    33244031
    33254032      outputFittingResult(outLogger, outTextFile, csvFormat, chanMask, whichrow, coordInfo, hasSameNchan, ofs, "autoCubicSplineBaseline()", pieceEdges, params, nClipped);
     
    33274034    }
    33284035
     4036    //---
     4037    if (outBaselintTable) {
     4038      bt->save(bltable);
     4039    }
     4040    //---
     4041    delete bt;
     4042
    33294043    if (outTextFile) ofs.close();
    33304044
     
    33344048}
    33354049
    3336 std::vector<float> Scantable::doCubicSplineFitting(const std::vector<float>& data, const std::vector<bool>& mask, int nPiece, std::vector<int>& idxEdge, std::vector<float>& params, int& nClipped, float thresClip, int nIterClip, bool getResidual)
     4050std::vector<float> Scantable::doCubicSplineFitting(const std::vector<float>& data, const std::vector<bool>& mask, std::vector<int>& idxEdge, std::vector<float>& params, float& rms, std::vector<bool>& finalmask, float clipth, int clipn)
     4051{
     4052  int nClipped = 0;
     4053  return doCubicSplineFitting(data, mask, idxEdge.size()-1, true, idxEdge, params, rms, finalmask, nClipped, clipth, clipn);
     4054}
     4055
     4056std::vector<float> Scantable::doCubicSplineFitting(const std::vector<float>& data, const std::vector<bool>& mask, int nPiece, std::vector<int>& idxEdge, std::vector<float>& params, float& rms, std::vector<bool>& finalmask, float clipth, int clipn)
     4057{
     4058  int nClipped = 0;
     4059  return doCubicSplineFitting(data, mask, nPiece, false, idxEdge, params, rms, finalmask, nClipped, clipth, clipn);
     4060}
     4061
     4062std::vector<float> Scantable::doCubicSplineFitting(const std::vector<float>& data, const std::vector<bool>& mask, int nPiece, bool useGivenPieceBoundary, std::vector<int>& idxEdge, std::vector<float>& params, float& rms, std::vector<bool>& finalMask, int& nClipped, float thresClip, int nIterClip, bool getResidual)
    33374063{
    33384064  if (data.size() != mask.size()) {
     
    33444070
    33454071  int nChan = data.size();
     4072
     4073  finalMask.clear();
     4074  finalMask.resize(nChan);
     4075
    33464076  std::vector<int> maskArray(nChan);
    33474077  std::vector<int> x(nChan);
     
    33534083      j++;
    33544084    }
     4085    finalMask[i] = mask[i];
    33554086  }
    33564087  int initNData = j;
     
    33624093  int nElement = (int)(floor(floor((double)(initNData/nPiece))+0.5));
    33634094  std::vector<double> invEdge(nPiece-1);
    3364   idxEdge[0] = x[0];
     4095
     4096  if (useGivenPieceBoundary) {
     4097    if ((int)idxEdge.size() != nPiece+1) {
     4098      throw(AipsError("pieceEdge.size() must be equal to nPiece+1."));
     4099    }
     4100  } else {
     4101    idxEdge.clear();
     4102    idxEdge.resize(nPiece+1);
     4103    idxEdge[0] = x[0];
     4104  }
    33654105  for (int i = 1; i < nPiece; ++i) {
    33664106    int valX = x[nElement*i];
    3367     idxEdge[i] = valX;
     4107    if (!useGivenPieceBoundary) {
     4108      idxEdge[i] = valX;
     4109    }
    33684110    invEdge[i-1] = 1.0/(double)valX;
    33694111  }
    3370   idxEdge[nPiece] = x[initNData-1]+1;
     4112  if (!useGivenPieceBoundary) {
     4113    idxEdge[nPiece] = x[initNData-1]+1;
     4114  }
     4115
     4116  params.clear();
     4117  params.resize(nPiece*4);
    33714118
    33724119  int nData = initNData;
     
    33954142    //           identity matrix (right).
    33964143    // the right part is used to calculate the inverse matrix of the left part.
     4144
    33974145    double xMatrix[nDOF][2*nDOF];
    33984146    double zMatrix[nDOF];
     
    34964244      }
    34974245    }
     4246
    34984247    //compute a vector y which consists of the coefficients of the best-fit spline curves
    34994248    //(a0,a1,a2,a3(,b3,c3,...)), namely, the ones for the leftmost piece and the ones of
     
    35454294      }
    35464295    }
     4296
    35474297    if (idxEdge[nPiece] < nChan) {
    35484298      int n = idxEdge[nPiece]-1;
     
    35624312    }
    35634313
     4314    double stdDev = 0.0;
     4315    for (int i = 0; i < nChan; ++i) {
     4316      stdDev += residual[i]*residual[i]*(double)maskArray[i];
     4317    }
     4318    stdDev = sqrt(stdDev/(double)nData);
     4319    rms = (float)stdDev;
     4320
    35644321    if ((nClip == nIterClip) || (thresClip <= 0.0)) {
    35654322      break;
    35664323    } else {
    3567       double stdDev = 0.0;
    3568       for (int i = 0; i < nChan; ++i) {
    3569         stdDev += residual[i]*residual[i]*(double)maskArray[i];
    3570       }
    3571       stdDev = sqrt(stdDev/(double)nData);
    35724324     
    35734325      double thres = stdDev * thresClip;
     
    35764328        if (abs(residual[i]) >= thres) {
    35774329          maskArray[i] = 0;
     4330          finalMask[i] = false;
    35784331        }
    35794332        if (maskArray[i] > 0) {
     
    35864339        nData = newNData;
    35874340      }
     4341
    35884342    }
    35894343  }
     
    36054359}
    36064360
    3607 void Scantable::selectWaveNumbers(const int whichrow, const std::vector<bool>& chanMask, const bool applyFFT, const std::string& fftMethod, const std::string& fftThresh, const std::vector<int>& addNWaves, const std::vector<int>& rejectNWaves, std::vector<int>& nWaves)
    3608 {
     4361void Scantable::selectWaveNumbers(const int whichrow, const std::vector<bool>& chanMask, const std::string& fftInfo, const std::vector<int>& addNWaves, const std::vector<int>& rejectNWaves, std::vector<int>& nWaves)
     4362//void Scantable::selectWaveNumbers(const int whichrow, const std::vector<bool>& chanMask, const bool applyFFT, const std::string& fftMethod, const std::string& fftThresh, const std::vector<int>& addNWaves, const std::vector<int>& rejectNWaves, std::vector<int>& nWaves)
     4363{
     4364  bool applyFFT;
     4365  std::string fftMethod;
     4366  std::string fftThresh;
     4367
    36094368  nWaves.clear();
    36104369
     4370  parseFFTInfo(fftInfo, applyFFT, fftMethod, fftThresh);
    36114371  if (applyFFT) {
    36124372    string fftThAttr;
     
    36184378
    36194379  addAuxWaveNumbers(whichrow, addNWaves, rejectNWaves, nWaves);
     4380}
     4381
     4382void Scantable::parseFFTInfo(const std::string& fftInfo, bool& applyFFT, std::string& fftMethod, std::string& fftThresh)
     4383{
     4384  istringstream iss(fftInfo);
     4385  std::string tmp;
     4386  std::vector<string> res;
     4387  while (getline(iss, tmp, ',')) {
     4388    res.push_back(tmp);
     4389  }
     4390  if (res.size() < 3) {
     4391    throw(AipsError("wrong value in 'fftinfo' parameter")) ;
     4392  }
     4393  applyFFT = (res[0] == "true");
     4394  fftMethod = res[1];
     4395  fftThresh = res[2];
    36204396}
    36214397
     
    37024478{
    37034479  std::vector<int> tempAddNWaves, tempRejectNWaves;
     4480  tempAddNWaves.clear();
     4481  tempRejectNWaves.clear();
     4482
    37044483  for (uInt i = 0; i < addNWaves.size(); ++i) {
    37054484    tempAddNWaves.push_back(addNWaves[i]);
     
    37454524void Scantable::setWaveNumberListUptoNyquistFreq(const int whichrow, std::vector<int>& nWaves)
    37464525{
    3747   if ((nWaves.size() == 2)&&(nWaves[1] == -999)) {
    3748     int val = nWaves[0];
    3749     int nyquistFreq = nchan(getIF(whichrow))/2+1;
    3750     nWaves.clear();
    3751     if (val > nyquistFreq) {  // for safety, at least nWaves contains a constant; CAS-3759
    3752       nWaves.push_back(0);
    3753     }
    3754     while (val <= nyquistFreq) {
    3755       nWaves.push_back(val);
    3756       val++;
    3757     }
    3758   }
    3759 }
    3760 
    3761 void Scantable::sinusoidBaseline(const std::vector<bool>& mask, const bool applyFFT, const std::string& fftMethod, const std::string& fftThresh, const std::vector<int>& addNWaves, const std::vector<int>& rejectNWaves, float thresClip, int nIterClip, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile)
     4526  int val = nWaves[0];
     4527  int nyquistFreq = nchan(getIF(whichrow))/2+1;
     4528  nWaves.clear();
     4529  if (val > nyquistFreq) {  // for safety, at least nWaves contains a constant; CAS-3759
     4530    nWaves.push_back(0);
     4531  }
     4532  while (val <= nyquistFreq) {
     4533    nWaves.push_back(val);
     4534    val++;
     4535  }
     4536}
     4537
     4538void Scantable::sinusoidBaseline(const std::vector<bool>& mask, const std::string& fftInfo, const std::vector<int>& addNWaves, const std::vector<int>& rejectNWaves, float thresClip, int nIterClip, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile, const std::string& bltable)
    37624539{
    37634540  try {
     
    37804557    }
    37814558
    3782     //Fitter fitter = Fitter();
    3783     //fitter.setExpression("sinusoid", nWaves);
    3784     //fitter.setIterClipping(thresClip, nIterClip);
     4559    bool showProgress;
     4560    int minNRow;
     4561    parseProgressInfo(progressInfo, showProgress, minNRow);
    37854562
    37864563    int nRow = nrow();
    37874564    std::vector<bool> chanMask;
    37884565    std::vector<int> nWaves;
    3789 
    3790     bool showProgress;
    3791     int minNRow;
    3792     parseProgressInfo(progressInfo, showProgress, minNRow);
     4566    std::vector<bool> finalChanMask;
     4567    float rms;
     4568
     4569    //---
     4570    bool outBaselintTable = (bltable != "");
     4571    STBaselineTable* bt = new STBaselineTable(*this);
     4572    ROScalarColumn<Double> *tcol = new ROScalarColumn<Double>(table_, "TIME");
     4573    Vector<Double> timeSecCol = tcol->getColumn();
     4574    //---
    37934575
    37944576    for (int whichrow = 0; whichrow < nRow; ++whichrow) {
     4577      std::vector<float> sp = getSpectrum(whichrow);
    37954578      chanMask = getCompositeChanMask(whichrow, mask);
    3796       selectWaveNumbers(whichrow, chanMask, applyFFT, fftMethod, fftThresh, addNWaves, rejectNWaves, nWaves);
    3797 
    3798       //FOR DEBUGGING------------
    3799       /*
    3800       if (whichrow < 0) {// == nRow -1) {
    3801         cout << "+++ i=" << setw(3) << whichrow << ", IF=" << setw(2) << getIF(whichrow);
    3802         if (applyFFT) {
    3803           cout << "[ ";
    3804           for (uInt j = 0; j < nWaves.size(); ++j) {
    3805             cout << nWaves[j] << ", ";
    3806           }
    3807           cout << " ]    " << endl;
    3808         }
    3809         cout << flush;
    3810       }
    3811       */
    3812       //-------------------------
    3813 
    3814       //fitBaseline(chanMask, whichrow, fitter);
    3815       //setSpectrum((getResidual ? fitter.getResidual() : fitter.getFit()), whichrow);
     4579      selectWaveNumbers(whichrow, chanMask, fftInfo, addNWaves, rejectNWaves, nWaves);
     4580
    38164581      std::vector<float> params;
    38174582      int nClipped = 0;
    3818       std::vector<float> res = doSinusoidFitting(getSpectrum(whichrow), chanMask, nWaves, params, nClipped, thresClip, nIterClip, getResidual);
    3819       setSpectrum(res, whichrow);
    3820       //
     4583      std::vector<float> res = doSinusoidFitting(sp, chanMask, nWaves, params, rms, finalChanMask, nClipped, thresClip, nIterClip, getResidual);
     4584
     4585      //---
     4586      if (outBaselintTable) {
     4587        uInt nparam = nWaves.size();
     4588        Vector<Int> fparam(nparam);
     4589        for (uInt i = 0; i < nparam; ++i) {
     4590          fparam[i] = nWaves[i];
     4591        }
     4592        std::vector<int> finalMaskList0;
     4593        finalMaskList0.clear();
     4594        for (uInt i = 0; i < finalChanMask.size(); ++i) {
     4595          if (finalChanMask[i]) {
     4596            if ((i == 0)||(i == finalChanMask.size()-1)) {
     4597              finalMaskList0.push_back(i);
     4598            } else {
     4599              if ((finalChanMask[i])&&(!finalChanMask[i-1])) {
     4600                finalMaskList0.push_back(i);
     4601              }
     4602              if ((finalChanMask[i])&&(!finalChanMask[i+1])) {
     4603                finalMaskList0.push_back(i);
     4604              }
     4605            }
     4606          }
     4607        }
     4608        Vector<uInt> finalMaskList(finalMaskList0.size());
     4609        for (uInt i = 0; i < finalMaskList0.size(); ++i) {
     4610          finalMaskList[i] = (uInt)finalMaskList0[i];
     4611        }
     4612
     4613        bt->appenddata(uInt(getScan(whichrow)), uInt(getCycle(whichrow)), uInt(getBeam(whichrow)), uInt(getIF(whichrow)), uInt(getPol(whichrow)),
     4614                       uInt(0),
     4615                       timeSecCol[whichrow],
     4616                       Bool(true),
     4617                       STBaselineFunc::Sinusoid,
     4618                       fparam,
     4619                       Vector<Float>(),
     4620                       finalMaskList,
     4621                       Vector<Float>(params),
     4622                       Float(rms),
     4623                       uInt(sp.size()),
     4624                       Float(thresClip),
     4625                       uInt(nIterClip),
     4626                       Float(0.0),
     4627                       uInt(0),
     4628                       Vector<uInt>());
     4629      } else {
     4630        setSpectrum(res, whichrow);
     4631      }
     4632      //---
    38214633
    38224634      outputFittingResult(outLogger, outTextFile, csvFormat, chanMask, whichrow, coordInfo, hasSameNchan, ofs, "sinusoidBaseline()", params, nClipped);
     
    38244636    }
    38254637
     4638    //---
     4639    if (outBaselintTable) {
     4640      bt->save(bltable);
     4641    }
     4642    //---
     4643    delete bt;
     4644
    38264645    if (outTextFile) ofs.close();
    38274646
     
    38314650}
    38324651
    3833 void Scantable::autoSinusoidBaseline(const std::vector<bool>& mask, const bool applyFFT, const std::string& fftMethod, const std::string& fftThresh, const std::vector<int>& addNWaves, const std::vector<int>& rejectNWaves, float thresClip, int nIterClip, const std::vector<int>& edge, float threshold, int chanAvgLimit, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile)
     4652void Scantable::autoSinusoidBaseline(const std::vector<bool>& mask, const std::string& fftInfo, const std::vector<int>& addNWaves, const std::vector<int>& rejectNWaves, float thresClip, int nIterClip, const std::vector<int>& edge, float threshold, int chanAvgLimit, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile, const std::string& bltable)
     4653//void Scantable::autoSinusoidBaseline(const std::vector<bool>& mask, const bool applyFFT, const std::string& fftMethod, const std::string& fftThresh, const std::vector<int>& addNWaves, const std::vector<int>& rejectNWaves, float thresClip, int nIterClip, const std::vector<int>& edge, float threshold, int chanAvgLimit, bool getResidual, const std::string& progressInfo, const bool outLogger, const std::string& blfile, const std::string& bltable)
    38344654{
    38354655  try {
     
    38524672    }
    38534673
    3854     //Fitter fitter = Fitter();
    3855     //fitter.setExpression("sinusoid", nWaves);
    3856     //fitter.setIterClipping(thresClip, nIterClip);
     4674    bool showProgress;
     4675    int minNRow;
     4676    parseProgressInfo(progressInfo, showProgress, minNRow);
     4677
     4678    int minEdgeSize = getIFNos().size()*2;
     4679    STLineFinder lineFinder = STLineFinder();
     4680    lineFinder.setOptions(threshold, 3, chanAvgLimit);
    38574681
    38584682    int nRow = nrow();
    38594683    std::vector<bool> chanMask;
    38604684    std::vector<int> nWaves;
    3861 
    3862     int minEdgeSize = getIFNos().size()*2;
    3863     STLineFinder lineFinder = STLineFinder();
    3864     lineFinder.setOptions(threshold, 3, chanAvgLimit);
    3865 
    3866     bool showProgress;
    3867     int minNRow;
    3868     parseProgressInfo(progressInfo, showProgress, minNRow);
     4685    std::vector<bool> finalChanMask;
     4686    float rms;
     4687
     4688    //---
     4689    bool outBaselintTable = (bltable != "");
     4690    STBaselineTable* bt = new STBaselineTable(*this);
     4691    ROScalarColumn<Double> *tcol = new ROScalarColumn<Double>(table_, "TIME");
     4692    Vector<Double> timeSecCol = tcol->getColumn();
     4693    //---
    38694694
    38704695    for (int whichrow = 0; whichrow < nRow; ++whichrow) {
    3871 
    3872       //-------------------------------------------------------
    3873       //chanMask = getCompositeChanMask(whichrow, mask, edge, minEdgeSize, lineFinder);
    3874       //-------------------------------------------------------
     4696      std::vector<float> sp = getSpectrum(whichrow);
     4697      //-- composote given channel mask and flagtra --------
    38754698      int edgeSize = edge.size();
    38764699      std::vector<int> currentEdge;
     4700      currentEdge.clear();
    38774701      if (edgeSize >= 2) {
    38784702        int idx = 0;
     
    38884712        throw(AipsError("Wrong length of edge element"));
    38894713      }
    3890       lineFinder.setData(getSpectrum(whichrow));
     4714      lineFinder.setData(sp);
    38914715      lineFinder.findLines(getCompositeChanMask(whichrow, mask), currentEdge, whichrow);
    38924716      chanMask = lineFinder.getMask();
    3893       //-------------------------------------------------------
    3894 
    3895       selectWaveNumbers(whichrow, chanMask, applyFFT, fftMethod, fftThresh, addNWaves, rejectNWaves, nWaves);
    3896 
    3897       //fitBaseline(chanMask, whichrow, fitter);
    3898       //setSpectrum((getResidual ? fitter.getResidual() : fitter.getFit()), whichrow);
     4717      //-- composote given channel mask and flagtra END --------
     4718      selectWaveNumbers(whichrow, chanMask, fftInfo, addNWaves, rejectNWaves, nWaves);
     4719
    38994720      std::vector<float> params;
    39004721      int nClipped = 0;
    3901       std::vector<float> res = doSinusoidFitting(getSpectrum(whichrow), chanMask, nWaves, params, nClipped, thresClip, nIterClip, getResidual);
    3902       setSpectrum(res, whichrow);
    3903       //
     4722      std::vector<float> res = doSinusoidFitting(sp, chanMask, nWaves, params, rms, finalChanMask, nClipped, thresClip, nIterClip, getResidual);
     4723
     4724      //---
     4725      if (outBaselintTable) {
     4726        uInt nparam = nWaves.size();
     4727        Vector<Int> fparam(nparam);
     4728        for (uInt i = 0; i < nparam; ++i) {
     4729          fparam[i] = nWaves[i];
     4730        }
     4731        std::vector<int> finalMaskList0;
     4732        finalMaskList0.clear();
     4733        for (uInt i = 0; i < finalChanMask.size(); ++i) {
     4734          if (finalChanMask[i]) {
     4735            if ((i == 0)||(i == finalChanMask.size()-1)) {
     4736              finalMaskList0.push_back(i);
     4737            } else {
     4738              if ((finalChanMask[i])&&(!finalChanMask[i-1])) {
     4739                finalMaskList0.push_back(i);
     4740              }
     4741              if ((finalChanMask[i])&&(!finalChanMask[i+1])) {
     4742                finalMaskList0.push_back(i);
     4743              }
     4744            }
     4745          }
     4746        }
     4747        Vector<uInt> finalMaskList(finalMaskList0.size());
     4748        for (uInt i = 0; i < finalMaskList0.size(); ++i) {
     4749          finalMaskList[i] = (uInt)finalMaskList0[i];
     4750        }
     4751
     4752        Vector<uInt> cEdge(currentEdge.size());
     4753        for (uInt i = 0; i < currentEdge.size(); ++i) {
     4754          cEdge[i] = currentEdge[i];
     4755        }
     4756
     4757        bt->appenddata(uInt(getScan(whichrow)), uInt(getCycle(whichrow)), uInt(getBeam(whichrow)), uInt(getIF(whichrow)), uInt(getPol(whichrow)),
     4758                       uInt(0),
     4759                       timeSecCol[whichrow],
     4760                       Bool(true),
     4761                       STBaselineFunc::Sinusoid,
     4762                       fparam,
     4763                       Vector<Float>(),
     4764                       finalMaskList,
     4765                       Vector<Float>(params),
     4766                       Float(rms),
     4767                       uInt(sp.size()),
     4768                       Float(thresClip),
     4769                       uInt(nIterClip),
     4770                       Float(threshold),
     4771                       uInt(chanAvgLimit),
     4772                       cEdge);
     4773      } else {
     4774        setSpectrum(res, whichrow);
     4775      }
     4776      //---
    39044777
    39054778      outputFittingResult(outLogger, outTextFile, csvFormat, chanMask, whichrow, coordInfo, hasSameNchan, ofs, "autoSinusoidBaseline()", params, nClipped);
     
    39074780    }
    39084781
     4782    //---
     4783    if (outBaselintTable) {
     4784      bt->save(bltable);
     4785    }
     4786    //---
     4787    delete bt;
     4788
    39094789    if (outTextFile) ofs.close();
    39104790
     
    39144794}
    39154795
    3916 std::vector<float> Scantable::doSinusoidFitting(const std::vector<float>& data, const std::vector<bool>& mask, const std::vector<int>& waveNumbers, std::vector<float>& params, int& nClipped, float thresClip, int nIterClip, bool getResidual)
     4796std::vector<float> Scantable::doSinusoidFitting(const std::vector<float>& data, const std::vector<bool>& mask, const std::vector<int>& waveNumbers, std::vector<float>& params, float& rms, std::vector<bool>& finalmask, float clipth, int clipn)
     4797{
     4798  int nClipped = 0;
     4799  return doSinusoidFitting(data, mask, waveNumbers, params, rms, finalmask, nClipped, clipth, clipn);
     4800}
     4801
     4802std::vector<float> Scantable::doSinusoidFitting(const std::vector<float>& data, const std::vector<bool>& mask, const std::vector<int>& waveNumbers, std::vector<float>& params, float& rms, std::vector<bool>& finalMask, int& nClipped, float thresClip, int nIterClip, bool getResidual)
    39174803{
    39184804  if (data.size() != mask.size()) {
     
    39394825
    39404826  int nChan = data.size();
     4827
     4828  finalMask.clear();
     4829  finalMask.resize(nChan);
     4830
    39414831  std::vector<int> maskArray;
    39424832  std::vector<int> x;
     
    39464836      x.push_back(i);
    39474837    }
     4838    finalMask[i] = mask[i];
    39484839  }
    39494840
     
    40864977    }
    40874978
     4979    double stdDev = 0.0;
     4980    for (int i = 0; i < nChan; ++i) {
     4981      stdDev += residual[i]*residual[i]*(double)maskArray[i];
     4982    }
     4983    stdDev = sqrt(stdDev/(double)nData);
     4984    rms = (float)stdDev;
     4985
    40884986    if ((nClip == nIterClip) || (thresClip <= 0.0)) {
    40894987      break;
    40904988    } else {
    4091       double stdDev = 0.0;
    4092       for (int i = 0; i < nChan; ++i) {
    4093         stdDev += residual[i]*residual[i]*(double)maskArray[i];
    4094       }
    4095       stdDev = sqrt(stdDev/(double)nData);
    4096      
     4989
    40974990      double thres = stdDev * thresClip;
    40984991      int newNData = 0;
     
    41004993        if (abs(residual[i]) >= thres) {
    41014994          maskArray[i] = 0;
     4995          finalMask[i] = false;
    41024996        }
    41034997        if (maskArray[i] > 0) {
     
    41105004        nData = newNData;
    41115005      }
     5006
    41125007    }
    41135008  }
Note: See TracChangeset for help on using the changeset viewer.