stringutil.cpp
Go to the documentation of this file.
00001 // -*- C++ -*-
00020 #include <algorithm>
00021 #include <iostream>
00022 #include <cstring>
00023 #include <stdio.h>
00024 #include <stdarg.h>
00025 #include <limits.h>
00026 #include <coil/stringutil.h>
00027 #include <string.h>
00028 #include <cctype>
00029 #include <cstdio>
00030 
00031 namespace coil
00032 {
00040   std::wstring string2wstring(std::string str)
00041   {
00042     std::wstring wstr(str.length(), L' ');
00043     std::copy(str.begin(),str.end(),wstr.begin());
00044     return wstr;
00045   }
00046 
00054   std::string wstring2string(std::wstring wstr)
00055   {
00056     std::string str(wstr.length(), ' ');
00057     std::copy(wstr.begin(), wstr.end(), str.begin());
00058     return str;
00059   }
00060 
00068   void toUpper(std::string& str)
00069   {
00070     std::transform(str.begin(), str.end(), str.begin(),
00071                    (int (*)(int))std::toupper); 
00072   }
00073 
00081   void toLower(std::string& str)
00082   {
00083     std::transform(str.begin(), str.end(), str.begin(),
00084                    (int (*)(int))std::tolower); 
00085   }
00086 
00094   int getlinePortable(std::istream& istr, std::string& line)
00095   {
00096     char c;
00097     std::stringstream s;
00098     
00099     while (istr.get(c))
00100       {
00101         if (c == '\n')
00102           {
00103             break;
00104           }
00105         else if (c == '\r')
00106           {
00107             if (istr.peek() == '\n')
00108               {
00109                 istr.ignore();
00110               }
00111             break;
00112           }
00113         else
00114           {
00115             s << c;
00116           }
00117       }
00118     line = s.str();
00119     return static_cast<int>(line.size());
00120   }
00121   
00129   bool isEscaped(const std::string& str, std::string::size_type pos)
00130   {
00131     --pos;
00132     unsigned int i;
00133     for (i = 0; (pos >= 0) && str[pos] == '\\'; --pos, ++i) ;
00134     // If the number of \ is odd, delimiter is escaped.
00135     return (i % 2) == 1;
00136   }
00137   
00145   struct escape_functor
00146   {
00147     escape_functor() {};
00148     void operator()(const char c)
00149     {
00150       if      (c == '\t')  str += "\\t";
00151       else if (c == '\n')  str += "\\n";
00152       else if (c == '\f')  str += "\\f";
00153       else if (c == '\r')  str += "\\r";
00154       else if (c == '\\')  str += "\\\\";
00155       //    else if (c == '\"')  str += "\\\"";
00156       //    else if (c == '\'')  str += "\\\'";
00157       else str.push_back(c);
00158     }
00159     std::string str;
00160   };
00161   
00169   std::string escape(const std::string str)
00170   {
00171     return for_each(str.begin(), str.end(), escape_functor()).str;
00172   }
00173   
00181   struct unescape_functor
00182   {
00183     unescape_functor() : count(0) {};
00184     void operator()(char c)
00185     {
00186       if (c == '\\')
00187         {
00188           ++count;
00189           if (!(count % 2))
00190             {
00191               str.push_back(c);
00192             }
00193         }
00194       else
00195         {
00196           if (count > 0 && (count % 2))
00197             {
00198               count = 0;
00199               if      (c == 't')  str.push_back('\t');
00200               else if (c == 'n')  str.push_back('\n');
00201               else if (c == 'f')  str.push_back('\f');
00202               else if (c == 'r')  str.push_back('\r');
00203               else if (c == '\"') str.push_back('\"');
00204               else if (c == '\'') str.push_back('\'');
00205               else str.push_back(c);
00206             }
00207           else
00208             {
00209               count = 0;
00210               str.push_back(c);
00211             }
00212         }
00213     }
00214     std::string str;
00215     int count;
00216   };
00217   
00225   std::string unescape(const std::string str)
00226   {
00227     return for_each(str.begin(), str.end(), unescape_functor()).str;
00228   }
00229 
00237   void eraseBlank(std::string& str)
00238   {
00239     std::string::iterator it(str.begin());
00240 
00241     while (it != str.end())
00242       {
00243         if (*it == ' ' || *it == '\t')
00244           {
00245             it = str.erase(it);
00246           }
00247         else
00248           {
00249             ++it;
00250           }
00251       }
00252 
00253   }
00254   
00262   void eraseHeadBlank(std::string& str)
00263   {
00264     if (str.empty()) return;
00265     while (str[0] == ' ' || str[0] == '\t') str.erase(0, 1);
00266   }
00267   
00275   void eraseTailBlank(std::string& str)
00276   {
00277     if (str.empty()) return;
00278     while ((str[str.size() - 1] == ' ' || str[str.size() - 1] == '\t') &&
00279            !isEscaped(str, str.size() - 1))
00280       str.erase(str.size() - 1, 1);
00281   }
00282 
00290   void eraseBothEndsBlank(std::string& str)
00291   {
00292     eraseHeadBlank(str);
00293     eraseTailBlank(str);
00294   }
00295 
00303   std::string normalize(std::string& str)
00304   {
00305     eraseBothEndsBlank(str);
00306     toLower(str);
00307     return str;
00308   }
00309   
00317   unsigned int replaceString(std::string& str, const std::string from,
00318                      const std::string to)
00319   {
00320     std::string::size_type pos(0);
00321     unsigned int cnt(0);
00322 
00323     while (pos != std::string::npos)
00324       {
00325         pos = str.find(from, pos);
00326         if (pos == std::string::npos) break;
00327         str.replace(pos, from.size(), to);
00328         pos += to.size();
00329         ++cnt;
00330       }
00331     return cnt;
00332   }
00333   
00341   vstring split(const std::string& input,
00342                 const std::string& delimiter,
00343                 bool ignore_empty)
00344   {
00345     typedef std::string::size_type size;
00346     vstring results;
00347     size delim_size = delimiter.size();
00348     size found_pos(0), begin_pos(0), pre_pos(0), substr_size(0);
00349     
00350     if (input.empty()) return results;
00351     
00352     //  if (input.substr(0, delim_size) == delimiter)
00353     //    begin_pos = pre_pos = delim_size;
00354     
00355     while (1)
00356       {
00357         //    REFIND:
00358         found_pos = input.find(delimiter, begin_pos);
00359         if (found_pos == std::string::npos) 
00360           {
00361             std::string substr(input.substr(pre_pos));
00362             eraseHeadBlank(substr);
00363             eraseTailBlank(substr);
00364             if (!(substr.empty() && ignore_empty)) results.push_back(substr);
00365             break;
00366           }
00367         /*
00368           if (isEscaped(input, found_pos))
00369           {
00370           begin_pos = found_pos + delim_size;
00371           goto REFIND;
00372           }
00373         */
00374         substr_size = found_pos - pre_pos;
00375         if (substr_size >= 0)
00376           {
00377             std::string substr(input.substr(pre_pos, substr_size));
00378             eraseHeadBlank(substr);
00379             eraseTailBlank(substr);
00380             if (!(substr.empty() && ignore_empty)) results.push_back(substr);
00381           }
00382         begin_pos = found_pos + delim_size;
00383         pre_pos   = found_pos + delim_size;
00384       }
00385     return results;
00386   }
00387   
00395   struct Toupper
00396   {
00397     void operator()(char &c)
00398     {
00399       c = toupper(c);
00400     }
00401   };
00402   
00410   bool toBool(std::string str, std::string yes, std::string no, 
00411               bool default_value)
00412   {
00413     std::for_each(str.begin(), str.end(), Toupper());
00414     std::for_each(yes.begin(), yes.end(), Toupper());
00415     std::for_each(no.begin(),  no.end(),  Toupper());
00416     
00417     if (str.find(yes) != std::string::npos)
00418       return true;
00419     else if (str.find(no) != std::string::npos)
00420       return false;
00421     else
00422       return default_value;
00423   }
00424 
00432   bool includes(const vstring& list, std::string value, bool ignore_case)
00433   {
00434     if (ignore_case) { toLower(value); }
00435 
00436     for (int i(0), len(static_cast<int>(list.size())); i < len; ++i)
00437       {
00438         std::string str(list[i]);
00439         if (ignore_case) { toLower(str); }
00440         if (str == value) return true;
00441       }
00442     return false;
00443   }
00444 
00452   bool includes(const std::string& list, std::string value, bool ignore_case)
00453   {
00454     vstring vlist(split(list, ","));
00455     return includes(vlist, value, ignore_case);
00456   }
00457   
00465   bool isAbsolutePath(const std::string& str)
00466   {
00467     // UNIX absolute path is begun from '/'
00468     if (str[0] == '/') return true;
00469     // Windows absolute path is begun from '[a-zA-Z]:\'
00470     if (isalpha(str[0]) && (str[1] == ':') && str[2] == '\\') return true;
00471     // Windows network file path is begun from '\\'
00472     if (str[0] == '\\' && str[1] == '\\') return true;
00473     
00474     return false;
00475   }
00476   
00484   bool isURL(const std::string& str)
00485   {
00486     typedef std::string::size_type size;
00487     size pos;
00488     if (str.empty()) return false;
00489     pos = str.find(":");
00490     if ((pos != 0) &&
00491         (pos != std::string::npos) &&
00492         (str[pos + 1] == '/') &&
00493         (str[pos + 2] == '/'))
00494       return true;
00495     return false;
00496   }
00497   
00505   struct unique_strvec
00506   {
00507     void operator()(const std::string& s)
00508     {
00509       if (std::find(str.begin(), str.end(), s) == str.end())
00510         return str.push_back(s);
00511     }
00512     vstring str;
00513   };
00514 
00522   template<>
00523   bool stringTo<std::string>(std::string& val, const char* str)
00524   {
00525     if (str == 0) { return false; }
00526     val = str;
00527     return true;
00528   }
00529   
00537   vstring unique_sv(vstring sv)
00538   {
00539     return std::for_each(sv.begin(), sv.end(), unique_strvec()).str;
00540   }
00541   
00549   std::string flatten(vstring sv)
00550   {
00551     if (sv.size() == 0) return "";
00552     
00553     std::string str;
00554     for (size_t i(0), len(sv.size() - 1); i < len; ++i)
00555       {
00556         str += sv[i] + ", ";
00557       }
00558     return str + sv.back();
00559   }
00560   
00568   char** toArgv(const vstring& args)
00569   {
00570     char** argv;
00571     size_t argc(args.size());
00572     
00573     argv = new char*[argc + 1];
00574     
00575     for (size_t i(0); i < argc; ++i)
00576       {
00577         size_t sz(args[i].size());
00578         argv[i] = new char[sz + 1];
00579         strncpy(argv[i], args[i].c_str(), sz);
00580         argv[i][sz] = '\0';
00581       }
00582     argv[argc] = NULL;
00583     return argv;
00584   }
00585 
00593   std::string sprintf(char const * __restrict fmt, ...)
00594   {
00595 #ifndef LINE_MAX
00596 #define LINE_MAX 1024
00597 #endif
00598     char str[LINE_MAX];
00599     va_list ap;
00600     
00601     va_start(ap, fmt);
00602 #ifdef WIN32
00603     _vsnprintf(str, LINE_MAX - 1, fmt, ap);
00604 #else
00605     vsnprintf(str, LINE_MAX - 1, fmt, ap);
00606 #endif
00607     va_end(ap);
00608     return std::string(str);
00609   }
00610 
00611 }; // namespace coil


openrtm_aist
Author(s): Noriaki Ando
autogenerated on Thu Aug 27 2015 14:16:39