예제 #1
0
파일: Divide.cpp 프로젝트: mcvine/mantid
/** Carries out the binary operation IN-PLACE on a single EventList,
 * with another EventList as the right-hand operand.
 *
 *  @param lhs :: Reference to the EventList that will be modified in place.
 *  @param rhs :: Const reference to the EventList on the right hand side.
 */
void Divide::performEventBinaryOperation(DataObjects::EventList &lhs,
                                         const DataObjects::EventList &rhs) {
  // We must histogram the rhs event list to divide.
  MantidVec rhsY, rhsE;
  rhs.generateHistogram(rhs.constDataX(), rhsY, rhsE);
  lhs.divide(rhs.constDataX(), rhsY, rhsE);
}
예제 #2
0
/** Carries out the binary operation IN-PLACE on a single EventList,
 * with another EventList as the right-hand operand.
 *
 *  @param lhs :: Reference to the EventList that will be modified in place.
 *  @param rhs :: Const reference to the EventList on the right hand side.
 */
void Multiply::performEventBinaryOperation(DataObjects::EventList &lhs,
                                           const DataObjects::EventList &rhs) {
  // We must histogram the rhs event list to multiply.
  MantidVec rhsY, rhsE;
  rhs.generateHistogram(rhs.x().rawData(), rhsY, rhsE);
  lhs.multiply(rhs.x().rawData(), rhsY, rhsE);
}
예제 #3
0
/** Convert events to "fake" events as counts in outWS
 */
void CountEventsInPulses::convertEvents(DataObjects::EventWorkspace_sptr outWS,
                                        bool sumspectra) {
  // 1. Get run_start time
  std::string runstartstr = inpWS->run().getProperty("run_start")->value();
  Kernel::DateAndTime runstart(runstartstr);
  int64_t runstarttime = runstart.totalNanoseconds();

  // 2. Convert TOF and add to new event workspace
  double margin_sec = mPulseLength * 0.01;
  g_log.information() << "Pulse length = " << mPulseLength
                      << " (sec).  Margine = " << margin_sec
                      << " For safe binning. " << std::endl;

  PARALLEL_FOR2(inpWS, outWS)
  for (int wsindex = 0;
       wsindex < static_cast<int>(inpWS->getNumberHistograms()); wsindex++) {

    DataObjects::EventList realevents = inpWS->getEventList(wsindex);
    DataObjects::EventList *fakeevents;
    if (sumspectra) {
      fakeevents = outWS->getEventListPtr(0);
    } else {
      fakeevents = outWS->getEventListPtr(wsindex);
    }

    size_t numevents = realevents.getNumberEvents();
    for (size_t ie = 0; ie < numevents; ie++) {
      DataObjects::WeightedEvent event = realevents.getEvent(ie);
      // Swap TOF and pulse time and add to new event list
      // a) TOF (ms) -> Pulse Time
      double oldtof = event.tof();
      int64_t oldtofns = int64_t(oldtof * 1000);
      Kernel::DateAndTime newpulsetime(oldtofns);

      // b) Pulse Time (ns) -> TOF (ms) -> second
      int64_t oldpulsetime =
          event.pulseTime().totalNanoseconds() - runstarttime;
      double newtofinsecond = double(oldpulsetime) * 1.0E-9 + margin_sec;

      DataObjects::TofEvent fakeevent(newtofinsecond, newpulsetime);

      fakeevents->addEventQuickly(fakeevent);

    } // ENDFOR events

  } // END FOR: Per Spectrum

  g_log.debug() << "DBx505 Input Events = " << inpWS->getNumberEvents()
                << "; Output Events = " << outWS->getNumberEvents()
                << std::endl;

  return;
}
예제 #4
0
파일: Divide.cpp 프로젝트: mcvine/mantid
/** Carries out the binary operation IN-PLACE on a single EventList,
 * with another (histogrammed) spectrum as the right-hand operand.
 *
 *  @param lhs :: Reference to the EventList that will be modified in place.
 *  @param rhsX :: The vector of rhs X bin boundaries
 *  @param rhsY :: The vector of rhs data values
 *  @param rhsE :: The vector of rhs error values
 */
void Divide::performEventBinaryOperation(DataObjects::EventList &lhs,
                                         const MantidVec &rhsX,
                                         const MantidVec &rhsY,
                                         const MantidVec &rhsE) {
  // Divide is implemented at the EventList level.
  lhs.divide(rhsX, rhsY, rhsE);
}
예제 #5
0
/** Carries out the binary operation IN-PLACE on a single EventList,
 * with another (histogrammed) spectrum as the right-hand operand.
 *
 *  @param lhs :: Reference to the EventList that will be modified in place.
 *  @param rhsX :: The vector of rhs X bin boundaries
 *  @param rhsY :: The vector of rhs data values
 *  @param rhsE :: The vector of rhs error values
 */
void Multiply::performEventBinaryOperation(DataObjects::EventList &lhs,
                                           const MantidVec &rhsX,
                                           const MantidVec &rhsY,
                                           const MantidVec &rhsE) {
  // Multiply is implemented at the EventList level.
  lhs.multiply(rhsX, rhsY, rhsE);
}
예제 #6
0
파일: Divide.cpp 프로젝트: mcvine/mantid
/** Carries out the binary operation IN-PLACE on a single EventList,
 * with a single (double) value as the right-hand operand.
 * Performs the multiplication by a scalar (with error)
 *
 *  @param lhs :: Reference to the EventList that will be modified in place.
 *  @param rhsY :: The rhs data value
 *  @param rhsE :: The rhs error value
 */
void Divide::performEventBinaryOperation(DataObjects::EventList &lhs,
                                         const double &rhsY,
                                         const double &rhsE) {
  // Multiply is implemented at the EventList level.
  lhs.divide(rhsY, rhsE);
}
예제 #7
0
/** Set up corrections with customized TOF correction input
  * The first column must be either DetectorID or Spectrum (from 0... as
 * workspace index)
  * The second column must be Correction or CorrectFactor, a number between 0
 * and 1, i.e, [0, 1]
  * The third column is optional as shift in unit of second
  */
void FilterEvents::setupCustomizedTOFCorrection() {
  // Check input workspace
  vector<string> colnames = m_detCorrectWorkspace->getColumnNames();
  bool hasshift = false;
  if (colnames.size() < 2)
    throw runtime_error("Input table workspace is not valide.");
  else if (colnames.size() >= 3)
    hasshift = true;

  bool usedetid;
  if (colnames[0].compare("DetectorID") == 0)
    usedetid = true;
  else if (colnames[0].compare("Spectrum") == 0)
    usedetid = false;
  else {
    usedetid = false;
    stringstream errss;
    errss << "First column must be either DetectorID or Spectrum. "
          << colnames[0] << " is not supported. ";
    throw runtime_error(errss.str());
  }

  // Parse detector and its TOF correction (i.e., offset factor and tof shift)
  // to a map
  map<detid_t, double> toffactormap;
  map<detid_t, double> tofshiftmap;
  size_t numrows = m_detCorrectWorkspace->rowCount();
  for (size_t i = 0; i < numrows; ++i) {
    TableRow row = m_detCorrectWorkspace->getRow(i);

    // Parse to map
    detid_t detid;
    double offset_factor;
    row >> detid >> offset_factor;
    if (offset_factor >= 0 && offset_factor <= 1) {
      // Valid offset (factor value)
      toffactormap.emplace(detid, offset_factor);
    } else {
      // Error, throw!
      stringstream errss;
      errss << "Correction (i.e., offset) equal to " << offset_factor
            << " of row "
            << "is out of range [0, 1].";
      throw runtime_error(errss.str());
    }

    // Shift
    if (hasshift) {
      double shift;
      row >> shift;
      tofshiftmap.emplace(detid, shift);
    }
  } // ENDFOR(row i)

  // Check size of TOF correction map
  size_t numhist = m_eventWS->getNumberHistograms();
  if (toffactormap.size() > numhist) {
    g_log.warning() << "Input correction table workspace has more detectors ("
                    << toffactormap.size() << ") than input workspace "
                    << m_eventWS->name() << "'s spectra number (" << numhist
                    << ".\n";
  } else if (toffactormap.size() < numhist) {
    stringstream errss;
    errss << "Input correction table workspace has more detectors ("
          << toffactormap.size() << ") than input workspace "
          << m_eventWS->name() << "'s spectra number (" << numhist << ".\n";
    throw runtime_error(errss.str());
  }

  // Apply to m_detTofOffsets and m_detTofShifts
  if (usedetid) {
    // Get vector IDs
    vector<detid_t> vecDetIDs(numhist, 0);
    // Set up the detector IDs to vecDetIDs and set up the initial value
    for (size_t i = 0; i < numhist; ++i) {
      // It is assumed that there is one detector per spectra.
      // If there are more than 1 spectrum, it is very likely to have problem
      // with correction factor
      const DataObjects::EventList events = m_eventWS->getEventList(i);
      auto detids = events.getDetectorIDs();
      if (detids.size() != 1) {
        // Check whether there are more than 1 detector per spectra.
        stringstream errss;
        errss << "The assumption is that one spectrum has one and only one "
                 "detector. "
              << "Error is found at spectrum " << i << ".  It has "
              << detids.size() << " detectors.";
        throw runtime_error(errss.str());
      }
      vecDetIDs[i] = *detids.begin();
    }

    // Map correction map to list
    map<detid_t, double>::iterator fiter;
    for (size_t i = 0; i < numhist; ++i) {
      detid_t detid = vecDetIDs[i];
      // correction (factor) map
      fiter = toffactormap.find(detid);
      if (fiter != toffactormap.end())
        m_detTofFactors[i] = fiter->second;
      else {
        stringstream errss;
        errss << "Detector "
              << "w/ ID << " << detid << " of spectrum " << i
              << " in Eventworkspace " << m_eventWS->name()
              << " cannot be found in input TOF calibration workspace. ";
        throw runtime_error(errss.str());
      }
      // correction shift map
      fiter = tofshiftmap.find(detid);
      if (fiter != tofshiftmap.end())
        m_detTofOffsets[i] = fiter->second;
    } // ENDFOR (each spectrum i)
  } else {
    // It is spectrum Number already
    map<detid_t, double>::iterator fiter;
    // correction factor
    for (fiter = toffactormap.begin(); fiter != toffactormap.end(); ++fiter) {
      size_t wsindex = static_cast<size_t>(fiter->first);
      if (wsindex < numhist)
        m_detTofFactors[wsindex] = fiter->second;
      else {
        stringstream errss;
        errss << "Workspace index " << wsindex << " is out of range.";
        throw runtime_error(errss.str());
      }
    }
    // correction shift
    for (fiter = tofshiftmap.begin(); fiter != tofshiftmap.end(); ++fiter) {
      size_t wsindex = static_cast<size_t>(fiter->first);
      if (wsindex < numhist)
        m_detTofOffsets[wsindex] = fiter->second;
      else {
        stringstream errss;
        errss << "Workspace index " << wsindex << " is out of range.";
        throw runtime_error(errss.str());
      }
    }
  }

  return;
}
예제 #8
0
  /** Write out an event list into an already-opened group
   * @param el :: reference to the EventList to write.
   * @param group_name :: group_name to create.
   * */
  int NexusFileIO::writeEventList( const DataObjects::EventList & el, std::string group_name) const
  {
    //write data entry
    NXstatus status=NXmakegroup(fileID, group_name.c_str(), "NXdata");
    if(status==NX_ERROR) return(2);
    NXopengroup(fileID, group_name.c_str(), "NXdata");

    // Copy the detector IDs to an array.
    const std::set<detid_t>& dets = el.getDetectorIDs();

    // Write out the detector IDs
    if (!dets.empty())
    {
      std::vector<detid_t> detectorIDs(dets.begin(),dets.end());
      int dims_array[1];
      NXwritedata("detector_IDs", NX_INT64, 1, dims_array, (void*)(detectorIDs.data()), false );
    }

    std::string eventType("UNKNOWN");
    size_t num = el.getNumberEvents();
    switch (el.getEventType())
    {
    case TOF:
      eventType = "TOF";
      writeEventListData( el.getEvents(), true, true, false, false );
      break;
    case WEIGHTED:
      eventType = "WEIGHTED";
      writeEventListData( el.getWeightedEvents(), true, true, true, true );
      break;
    case WEIGHTED_NOTIME:
      eventType = "WEIGHTED_NOTIME";
      writeEventListData( el.getWeightedEventsNoTime(), true, false, true, true );
      break;
    }

    // --- Save the type of sorting -----
    std::string sortType;
    switch (el.getSortType())
    {
    case TOF_SORT:
      sortType = "TOF_SORT";
      break;
    case PULSETIME_SORT:
      sortType = "PULSETIME_SORT";
      break;
    case UNSORTED:
    default:
      sortType = "UNSORTED";
      break;
    }
    NXputattr (fileID, "sort_type",  reinterpret_cast<void*>(const_cast<char*>(sortType.c_str())), static_cast<int>(sortType.size()), NX_CHAR);

    // Save an attribute with the type of each event.
    NXputattr (fileID, "event_type",  reinterpret_cast<void*>(const_cast<char*>(eventType.c_str())), static_cast<int>(eventType.size()), NX_CHAR);
    // Save an attribute with the number of events
    NXputattr (fileID, "num_events", (void*)(&num), 1, NX_INT64);

    // Close it up!
    status=NXclosegroup(fileID);
    return((status==NX_ERROR)?3:0);
  }