示例#1
0
void LoadDaveGrp::getData(std::vector<MantidVec *> &data,
    std::vector<MantidVec *> &errs)
{
  double data_val = 0.0;
  double err_val = 0.0;
  API::Progress progress(this, 0.0, 1.0, this->nGroups);
  for(int j = 0; j < this->nGroups; j++)
  {
    // Skip the group comment line
    this->readLine();
    // Read the data block
    MantidVec *d = new MantidVec();
    MantidVec *e = new MantidVec();
    for(std::size_t k = 0; k < static_cast<std::size_t>(this->xLength); k++)
    {
      this->readLine();
      std::istringstream is(this->line);
      is >> data_val >> err_val;
      d->push_back(data_val);
      e->push_back(err_val);
    }
    data.push_back(d);
    errs.push_back(e);
    progress.report();
  }
}
示例#2
0
/** Calculates Sn as estimator of scale for given vector
  *
  * This method implements a naive calculation of Sn, as defined by Rousseeuw
  *and Croux (http://dx.doi.org/10.2307%2F2291267).
  * In contrast to standard deviation, this is more robust towards outliers.
  *
  * @param begin :: Beginning of vector.
  * @param end :: End of vector.
  * @return Sn of supplied data.
  */
double PoldiPeakSearch::getSn(MantidVec::const_iterator begin,
                              MantidVec::const_iterator end) const {
  size_t numberOfPoints = std::distance(begin, end);
  MantidVec absoluteDifferenceMedians(numberOfPoints);

  PARALLEL_FOR_NO_WSP_CHECK()
  for (int i = 0; i < static_cast<int>(numberOfPoints); ++i) {
    double currentValue = *(begin + i);
    MantidVec temp;
    temp.reserve(numberOfPoints - 1);
    for (int j = 0; j < static_cast<int>(numberOfPoints); ++j) {
      if (j != i) {
        temp.push_back(fabs(*(begin + j) - currentValue));
      }
    }
    std::sort(temp.begin(), temp.end());

    absoluteDifferenceMedians[i] =
        getMedianFromSortedVector(temp.begin(), temp.end());
  }

  std::sort(absoluteDifferenceMedians.begin(), absoluteDifferenceMedians.end());

  return 1.1926 * getMedianFromSortedVector(absoluteDifferenceMedians.begin(),
                                            absoluteDifferenceMedians.end());
}
示例#3
0
/**
 * load vectors onto a Workspace2D with 3 bins (the three components of the
 * vectors)
 * dataX for the origin of the vector (assumed (0,0,0) )
 * dataY for the tip of the vector
 * dataE is assumed (0,0,0), no errors
 * @param h5file file identifier
 * @param gws pointer to WorkspaceGroup being filled
 * @param sorting_indexes permutation of qvmod indexes to render it in
 * increasing order of momemtum transfer
 */
const MantidVec LoadSassena::loadQvectors(const hid_t &h5file,
                                          API::WorkspaceGroup_sptr gws,
                                          std::vector<int> &sorting_indexes) {

  const std::string gwsName = this->getPropertyValue("OutputWorkspace");
  const std::string setName("qvectors");

  hsize_t dims[3];
  if (dataSetInfo(h5file, setName, dims) < 0) {
    throw Kernel::Exception::FileError(
        "Unable to read " + setName + " dataset info:", m_filename);
  }
  int nq = static_cast<int>(dims[0]); // number of q-vectors
  double *buf = new double[nq * 3];
  this->dataSetDouble(h5file, "qvectors", buf);

  MantidVec qvmod; // store the modulus of the vector
  double *curr = buf;
  for (int iq = 0; iq < nq; iq++) {
    qvmod.push_back(
        sqrt(curr[0] * curr[0] + curr[1] * curr[1] + curr[2] * curr[2]));
    curr += 3;
  }

  if (getProperty("SortByQVectors")) {
    std::vector<mypair> qvmodpair;
    for (int iq = 0; iq < nq; iq++)
      qvmodpair.push_back(mypair(qvmod[iq], iq));
    std::sort(qvmodpair.begin(), qvmodpair.end(), compare);
    for (int iq = 0; iq < nq; iq++)
      sorting_indexes.push_back(qvmodpair[iq].second);
    std::sort(qvmod.begin(), qvmod.end());
  } else
    for (int iq = 0; iq < nq; iq++)
      sorting_indexes.push_back(iq);

  DataObjects::Workspace2D_sptr ws =
      boost::dynamic_pointer_cast<DataObjects::Workspace2D>(
          API::WorkspaceFactory::Instance().create("Workspace2D", nq, 3, 3));
  std::string wsName = gwsName + std::string("_") + setName;
  ws->setTitle(wsName);

  for (int iq = 0; iq < nq; iq++) {
    MantidVec &Y = ws->dataY(iq);
    const int index = sorting_indexes[iq];
    curr = buf + 3 * index;
    Y.assign(curr, curr + 3);
  }
  delete[] buf;

  ws->getAxis(0)->unit() = Kernel::UnitFactory::Instance().create(
      "MomentumTransfer"); // Set the Units

  this->registerWorkspace(
      gws, wsName, ws, "X-axis: origin of Q-vectors; Y-axis: tip of Q-vectors");
  return qvmod;
}
示例#4
0
/** Retrieves a vector with all counts that belong to the background
  *
  * In this method, a vector is assembled which contains all count data that is
  *considered to be background.
  * Whether a point is considered background depends on its distance to the
  *given peak positions.
  *
  * @param peakPositions :: Peak positions.
  * @param correlationCounts :: Vector with the complete correlation spectrum.
  * @return Vector only with counts that belong to the background.
  */
MantidVec PoldiPeakSearch::getBackground(
    std::list<MantidVec::const_iterator> peakPositions,
    const MantidVec &correlationCounts) const {
  size_t backgroundPoints =
      getNumberOfBackgroundPoints(peakPositions, correlationCounts);

  MantidVec background;
  background.reserve(backgroundPoints);

  for (MantidVec::const_iterator point = correlationCounts.begin() + 1;
       point != correlationCounts.end() - 1; ++point) {
    if (distanceToPeaksGreaterThanMinimum(peakPositions, point)) {
      background.push_back(*point);
    }
  }

  return background;
}
void GoniometerAnglesFromPhiRotation::exec() {

  PeaksWorkspace_sptr PeaksRun1 = getProperty("PeaksWorkspace1");
  PeaksWorkspace_sptr PeaksRun2 = getProperty("PeaksWorkspace2");

  double Tolerance = getProperty("Tolerance");

  Kernel::Matrix<double> Gon1(3, 3);
  Kernel::Matrix<double> Gon2(3, 3);
  if (!CheckForOneRun(PeaksRun1, Gon1) || !CheckForOneRun(PeaksRun2, Gon2)) {
    g_log.error("Each peaks workspace MUST have only one run");
    throw std::invalid_argument("Each peaks workspace MUST have only one run");
  }

  Kernel::Matrix<double> UB1;

  bool Run1HasOrientedLattice = true;
  if (!PeaksRun1->sample().hasOrientedLattice()) {

    Run1HasOrientedLattice = false;

    const std::string fft("FindUBUsingFFT");
    API::IAlgorithm_sptr findUB = this->createChildAlgorithm(fft);
    findUB->initialize();
    findUB->setProperty<PeaksWorkspace_sptr>("PeaksWorkspace",
                                             getProperty("PeaksWorkspace1"));
    findUB->setProperty("MIND", static_cast<double>(getProperty("MIND")));
    findUB->setProperty("MAXD", static_cast<double>(getProperty("MAXD")));
    findUB->setProperty("Tolerance", Tolerance);

    findUB->executeAsChildAlg();

    if (!PeaksRun1->sample().hasOrientedLattice()) {
      g_log.notice(std::string("Could not find UB for ") +
                   std::string(PeaksRun1->getName()));
      throw std::invalid_argument(std::string("Could not find UB for ") +
                                  std::string(PeaksRun1->getName()));
    }
  }
  //-------------get UB raw :No goniometer----------------

  UB1 = PeaksRun1->sample().getOrientedLattice().getUB();

  UB1 = getUBRaw(UB1, Gon1);

  int N1;
  double avErrIndx, avErrAll;
  IndexRaw(PeaksRun1, UB1, N1, avErrIndx, avErrAll, Tolerance);

  if (N1 < .6 * PeaksRun1->getNumberPeaks()) {
    g_log.notice(std::string("UB did not index well for ") +
                 std::string(PeaksRun1->getName()));
    throw std::invalid_argument(std::string("UB did not index well for ") +
                                std::string(PeaksRun1->getName()));
  }

  //----------------------------------------------

  Geometry::OrientedLattice lat2 = PeaksRun1->sample().getOrientedLattice();

  lat2.setUB(UB1);
  PeaksRun2->mutableSample().setOrientedLattice(&lat2);

  if (!Run1HasOrientedLattice)
    PeaksRun1->mutableSample().setOrientedLattice(nullptr);

  double dphi = static_cast<double>(getProperty("Phi2")) -
                static_cast<double>(getProperty("Run1Phi"));
  Kernel::Matrix<double> Gon22(3, 3, true);

  for (int i = 0; i < PeaksRun2->getNumberPeaks(); i++) {
    PeaksRun2->getPeak(i).setGoniometerMatrix(Gon22);
  }

  int RunNum = PeaksRun2->getPeak(0).getRunNumber();
  std::string RunNumStr = std::to_string(RunNum);
  int Npeaks = PeaksRun2->getNumberPeaks();

  // n indexed, av err, phi, chi,omega
  std::array<double, 5> MinData = {{0., 0., 0., 0., 0.}};
  MinData[0] = 0.0;
  std::vector<V3D> directionList = IndexingUtils::MakeHemisphereDirections(50);

  API::FrameworkManager::Instance();

  for (auto dir : directionList)
    for (int sgn = 1; sgn > -2; sgn -= 2) {
      dir.normalize();
      Quat Q(sgn * dphi, dir);
      Q.normalize();
      Kernel::Matrix<double> Rot(Q.getRotation());

      int Nindexed;
      double dummyAvErrIndx, dummyAvErrAll;
      IndexRaw(PeaksRun2, Rot * UB1, Nindexed, dummyAvErrIndx, dummyAvErrAll,
               Tolerance);

      if (Nindexed > MinData[0]) {
        MinData[0] = Nindexed;
        MinData[1] = sgn;
        MinData[2] = dir[0];

        MinData[3] = dir[1];
        MinData[4] = dir[2];
      }
    }

  g_log.debug() << "Best direction unOptimized is ("
                << (MinData[1] * MinData[2]) << "," << (MinData[1] * MinData[3])
                << "," << (MinData[1] * MinData[4]) << ")\n";

  //----------------------- Optimize around best----------------------------

  auto ws = createWorkspace<Workspace2D>(1, 3 * Npeaks, 3 * Npeaks);

  MantidVec Xvals;

  for (int i = 0; i < Npeaks; ++i) {
    Xvals.push_back(i);
    Xvals.push_back(i);
    Xvals.push_back(i);
  }

  ws->setPoints(0, Xvals);

  //--------------------Set up other Fit function arguments------------------
  V3D dir(MinData[2], MinData[3], MinData[4]);
  dir.normalize();
  Quat Q(MinData[1] * dphi, dir);
  Q.normalize();
  Kernel::Matrix<double> Rot(Q.getRotation());

  Goniometer Gon(Rot);
  std::vector<double> omchiphi = Gon.getEulerAngles("yzy");
  MinData[2] = omchiphi[2];
  MinData[3] = omchiphi[1];
  MinData[4] = omchiphi[0];

  std::string FunctionArgs =
      "name=PeakHKLErrors, PeakWorkspaceName=" + PeaksRun2->getName() +
      ",OptRuns=" + RunNumStr + ",phi" + RunNumStr + "=" +
      boost::lexical_cast<std::string>(MinData[2]) + ",chi" + RunNumStr + "=" +
      boost::lexical_cast<std::string>(MinData[3]) + ",omega" + RunNumStr +
      "=" + boost::lexical_cast<std::string>(MinData[4]);

  std::string Constr = boost::lexical_cast<std::string>(MinData[2] - 5) +
                       "<phi" + RunNumStr + "<" +
                       boost::lexical_cast<std::string>(MinData[2] + 5);
  Constr += "," + boost::lexical_cast<std::string>(MinData[3] - 5) + "<chi" +
            RunNumStr + "<" + boost::lexical_cast<std::string>(MinData[3] + 5) +
            ",";

  Constr += boost::lexical_cast<std::string>(MinData[4] - 5) + "<omega" +
            RunNumStr + "<" + boost::lexical_cast<std::string>(MinData[4] + 5);

  std::string Ties = "SampleXOffset=0.0,SampleYOffset=0.0,SampleZOffset=0.0,"
                     "GonRotx=0.0,GonRoty=0.0,GonRotz=0.0";

  boost::shared_ptr<Algorithm> Fit = createChildAlgorithm("Fit");

  Fit->initialize();
  Fit->setProperty("Function", FunctionArgs);
  Fit->setProperty("Ties", Ties);
  Fit->setProperty("Constraints", Constr);
  Fit->setProperty("InputWorkspace", ws);
  Fit->setProperty("CreateOutput", true);

  std::string outputName = "out";

  Fit->setProperty("Output", outputName);

  Fit->executeAsChildAlg();

  boost::shared_ptr<API::ITableWorkspace> results =
      Fit->getProperty("OutputParameters");
  double chisq = Fit->getProperty("OutputChi2overDoF");

  MinData[0] = chisq;
  MinData[2] = results->Double(6, 1);
  MinData[3] = results->Double(7, 1);
  MinData[4] = results->Double(8, 1);

  g_log.debug() << "Best direction Optimized is (" << (MinData[2]) << ","
                << (MinData[3]) << "," << (MinData[4]) << ")\n";

  //          ---------------------Find number indexed -----------------------
  Quat Q1 = Quat(MinData[4], V3D(0, 1, 0)) * Quat(MinData[3], V3D(0, 0, 1)) *
            Quat(MinData[2], V3D(0, 1, 0));

  int Nindexed;
  Kernel::Matrix<double> Mk(Q1.getRotation());
  IndexRaw(PeaksRun2, Mk * UB1, Nindexed, avErrIndx, avErrAll, Tolerance);

  //------------------------------------ Convert/Save Results
  //-----------------------------

  double deg, ax1, ax2, ax3;
  Q1.getAngleAxis(deg, ax1, ax2, ax3);
  if (dphi * deg < 0) {
    deg = -deg;
    ax1 = -ax1;
    ax2 = -ax2;
    ax3 = -ax3;
  }

  double phi2 = static_cast<double>(getProperty("Run1Phi")) + dphi;
  double chi2 = acos(ax2) / M_PI * 180;
  double omega2 = atan2(ax3, -ax1) / M_PI * 180;

  g_log.notice()
      << "============================ Results ============================\n";
  g_log.notice() << "     phi,chi, and omega= (" << phi2 << "," << chi2 << ","
                 << omega2 << ")\n";
  g_log.notice() << "     #indexed =" << Nindexed << '\n';
  g_log.notice()
      << "              ==============================================\n";

  setProperty("Phi2", phi2);
  setProperty("Chi2", chi2);
  setProperty("Omega2", omega2);

  setProperty("NIndexed", Nindexed);

  setProperty("AvErrIndex", avErrIndx);

  setProperty("AvErrAll", avErrAll);

  Q1 = Quat(omega2, V3D(0, 1, 0)) * Quat(chi2, V3D(0, 0, 1)) *
       Quat(phi2, V3D(0, 1, 0));
  Kernel::Matrix<double> Gon2a(Q1.getRotation());
  for (int i = 0; i < PeaksRun2->getNumberPeaks(); i++) {
    PeaksRun2->getPeak(i).setGoniometerMatrix(Gon2a);
  }

  OrientedLattice latt2(PeaksRun2->mutableSample().getOrientedLattice());
  // Kernel::Matrix<double> UB = latt2.getUB();
  Rot.Invert();
  Gon2a.Invert();
  latt2.setUB(Gon2a * Mk * UB1);

  PeaksRun2->mutableSample().setOrientedLattice(&latt2);
}