Skip to content
Snippets Groups Projects
Strings.cpp 37.7 KiB
Newer Older
#include "MantidKernel/Strings.h"
#include "MantidKernel/UnitLabel.h"

#include <Poco/StringTokenizer.h>
#include <Poco/Path.h>

#include <boost/algorithm/string.hpp>
#include <boost/lexical_cast.hpp>
#include <boost/shared_ptr.hpp>
#include <boost/make_shared.hpp>

#include <cmath>
namespace Mantid {
namespace Kernel {
namespace Strings {

//------------------------------------------------------------------------------------------------
/** Loads the entire contents of a text file into a string
 *
 * @param filename :: full path to file
 * @return string contents of text file
 */
std::string loadFile(const std::string &filename) {
  std::string retVal;
  std::string str;
  std::ifstream in;
  in.open(filename.c_str());
  getline(in, str);
  while (in) {
    retVal += str + "\n";
    getline(in, str);
  }
  in.close();
  return retVal;
}

//------------------------------------------------------------------------------------------------
/** Return a string with all matching occurence-strings
 *
 * @param input :: input string
 * @param find_what :: will search for all occurences of this string
 * @param replace_with :: ... and replace them with this.
 * @return the modified string.
 */
std::string replace(const std::string &input, const std::string &find_what,
                    const std::string &replace_with) {
  std::string output = input;
  std::string::size_type pos = 0;
  while ((pos = output.find(find_what, pos)) != std::string::npos) {
    output.erase(pos, find_what.length());
    output.insert(pos, replace_with);
    pos += replace_with.length();
  }
  return output;
}

/**
 * Return a string with all occurrences of the characters in the input replaced
 * by the replace string
 * @param input :: The input string to perform the replacement on
 * @param charStr :: Each occurrence of ANY character in this string within the
 * input string will be replaced by substitute
 * @param substitute :: A substitute string
 * @return A new string with the characters replaced
 */
MANTID_KERNEL_DLL std::string replaceAll(const std::string &input,
                                         const std::string &charStr,
                                         const std::string &substitute) {
  std::string replaced;
  replaced.reserve(input.size());
  std::string::const_iterator iend = input.end();
  for (std::string::const_iterator itr = input.begin(); itr != iend; ++itr) {
    char inputChar = (*itr);
    if (charStr.find_first_of(inputChar) == std::string::npos) // Input string
                                                               // char is not
                                                               // one of those
                                                               // to be replaced
      replaced.push_back(inputChar);
    } else {
      replaced.append(substitute);
    }
  }
  return replaced;
}

//------------------------------------------------------------------------------------------------
/**
 * Function to convert a number into hex
 * output (and leave the stream un-changed)
 * @param OFS :: Output stream
 * @param n :: Integer to convert
 * \todo Change this to a stream operator
 */
void printHex(std::ostream &OFS, const int n) {
  std::ios_base::fmtflags PrevFlags = OFS.flags();
  OFS << "Ox";
  OFS.width(8);
  OFS.fill('0');
  hex(OFS);
  OFS << n;
  OFS.flags(PrevFlags);
  return;
}

//------------------------------------------------------------------------------------------------
/**
 * Removes the multiple spaces in the line
 * @param Line :: Line to process
 * @return String with single space components
 */
std::string stripMultSpc(const std::string &Line) {
  std::string Out;
  int spc(1);
  int lastReal(-1);
  for (unsigned int i = 0; i < Line.length(); i++) {
    if (Line[i] != ' ' && Line[i] != '\t' && Line[i] != '\r' &&
        Line[i] != '\n') {
      lastReal = i;
      spc = 0;
      Out += Line[i];
    } else if (!spc) {
      spc = 1;
      Out += ' ';
    }
  }
  lastReal++;
  if (lastReal < static_cast<int>(Out.length()))
    Out.erase(lastReal);
  return Out;
}

//------------------------------------------------------------------------------------------------
//------------------------------------------------------------------------------------------------
/**
 *  Checks that as least cnt letters of
 *  works is part of the string. It is currently
 *  case sensitive. It removes the Word if found
 *  @param Line :: Line to process
 *  @param Word :: Word to use
 * @param cnt :: Length of Word for significants [default =4]
 *  @retval 1 on success (and changed Line)
 *  @retval 0 on failure
 */
int extractWord(std::string &Line, const std::string &Word, const int cnt) {
  if (Word.empty())
    return 0;

  size_t minSize(cnt > static_cast<int>(Word.size()) ? Word.size() : cnt);
  std::string::size_type pos = Line.find(Word.substr(0, minSize));
  if (pos == std::string::npos)
    return 0;
  // Pos == Start of find
  size_t LinePt = minSize + pos;
  for (; minSize < Word.size() && LinePt < Line.size() &&
             Word[minSize] == Line[LinePt];
       LinePt++, minSize++) {
  }

  Line.erase(pos, LinePt - (pos - 1));
  return 1;
}

//------------------------------------------------------------------------------------------------
/** If a word ends with a number representing a positive integer, return
 * the value of that int.
 *
 * @param word :: string possibly ending in a number
 * @return the number, or -1 if it does not end in a number
 */
int endsWithInt(const std::string &word) {
  if (word.empty())
    return -1;
  int out = -1;
  // Find the index of the first number in the string (if any)
  int firstNumber = int(word.size());
  for (int i = int(word.size()) - 1; i >= 0; i--) {
    char c = word[i];
    if ((c > '9') || (c < '0'))
      break;
    firstNumber = i;
  }
  // Convert the string of decimals to an int
  if (firstNumber < int(word.size())) {
    std::string part = word.substr(firstNumber, word.size() - firstNumber);
    if (!convert(part, out))
      return -1;
  }
  return out;
}

//------------------------------------------------------------------------------------------------
/**
 *  Check to see if S is the same as the
 *  first part of a phrase. (case insensitive)
 *  @param S :: string to check
Loading
Loading full blame...