/***************************************************************************
                          SIMPLY POWERFUL TOOLKIT (SPTK)
                          string_ext.cpp  -  description
                             -------------------
    begin                : Thu July 14 2005
    copyright            : (C) 2005 by Alexey Parshin
    email                : alexeyp@gmail.com
 ***************************************************************************/

/***************************************************************************
   This library is free software; you can redistribute it and/or modify it 
   under the terms of the GNU Library General Public License as published by
   the Free Software Foundation; either version 2 of the License, or (at 
   your option) any later version.

   This library is distributed in the hope that it will be useful, but 
   WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library
   General Public License for more details.

   You should have received a copy of the GNU Library General Public License
   along with this library; if not, write to the Free Software Foundation, 
   Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.

   Please report all bugs and problems to "alexeyp@gmail.com"
 ***************************************************************************/

#include <fstream>
#include <iostream>
#include <errno.h>
#include <sptk3/sptk.h>
#include <sptk3/string_ext.h>

using namespace std;

string upperCase(const string& str) {
   unsigned len = str.length();
   string result;
   result.resize(len);
   for (unsigned i = 0; i < len; i++) {
      result[i] = toupper(str[i]);
   }
   return result;
}

string lowerCase(const string& str) {
   unsigned len = str.length();
   string result;
   result.resize(len);
   for (unsigned i = 0; i < len; i++) {
      result[i] = tolower(str[i]);
   }
   return result;
}

string trim(const string& str) {
   unsigned len = str.length();
   if (!len) return "";
   const unsigned char *s = (const unsigned char *)str.c_str();
   int i, startpos = 0, endpos = len -1;
   bool found = false;
   for (i = endpos; i >= 0; i--) {
      if (s[i] > 32) {
         endpos = i;
         found = true;
         break;
      }
   }
   if (!found) return "";
   for (i = 0; i <= endpos; i++) {
      if (s[i] > 32) {
         startpos = i;
         break;
      }
   }
   return str.substr(startpos,endpos-startpos+1);
}

void join(string& dest, const vector<string> src, string separator) {
   dest = "";
   vector<string>::const_iterator itor = src.begin();
   for (; itor != src.end(); itor++) {
      dest += *itor + separator;
   }
}

void split(vector<string> dest, const string& src, string delimitter) {
   dest.clear();
   char *buffer = (char *)src.c_str();
   if (!strlen(buffer)) return;
   int dlen = delimitter.length();
   if (!dlen) return;
   char *p = buffer;
   for (;;) {
      char *end = strstr(p,delimitter.c_str());
      if (end) {
         //int len = end - p;
         char sc = *end;
         *end = 0;
         dest.push_back(p);
         *end = sc;
         p = end + dlen;
      } else {
         dest.push_back(p);
         break;
      }
   }
}

string int2string(int value) {
   char buff[32];
   sprintf(buff,"%i",value);
   return buff;
}

int string2int(const string& str,int defaultValue) {
   char *endptr;
   int result = strtol(str.c_str(),&endptr,10);
   if (errno) return defaultValue;
   return result;
}

string capitalizeWords(const std::string& str) {
   string s(str);
   char *current = (char *)s.c_str();
   char *wordStart = NULL;
   if (*current) {
      for (;;) {
         if (isalnum(*current)) {
            if (!wordStart)
               wordStart = current;
         } else {
            if (current - wordStart > 3) {
               if (wordStart)
                  *wordStart = toupper(*wordStart);
               else wordStart = current;
               for (char *ptr = wordStart + 1; ptr < current; ptr++)
                  *ptr = tolower(*ptr);
            }
            wordStart = NULL;
         }
         if (!*current)
            break;
         current++;
      }
   }
   return s;
}

string replaceAll(const string& src,const string& pattern,const string& replacement) {
   string str = src;

   if (pattern.empty()) return src;
   int patternLength = pattern.length();
   int replacementLength = replacement.length();
  
   unsigned long i = str.find(pattern);

   while (i != string::npos) { // While not at the end of the string
      str.replace(i,patternLength,replacement);
      i = str.find(pattern, i + replacementLength);
   }
   return str;
}

void stringToStringVector(const string& src,vector<string> dest,string delimitter) {
   string buffer(src);
   dest.clear();
   if (!buffer[0]) return;
   int dlen = delimitter.length();
   if (!dlen) return;
   char *p = (char *)buffer.c_str();
   for (;;) {
      char *end = strstr(p,delimitter.c_str());
      if (end) {
         char sc = *end;
         *end = 0;
         dest.push_back(p);
         *end = sc;
         p = end + dlen;
      } else {
         dest.push_back(p);
         break;
      }
   }
}
