00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 #ifndef __STRING_HPP
00014 #define __STRING_HPP
00015 #include <basix/type_props.hpp>
00017 
00018 namespace mmx {
00019 
00020 
00021 
00022 
00023 
00024 class string;
00025 class string_rep REP_STRUCT {
00026 private:
00027   char* a;  
00028   nat   n;  
00029   nat   l;  
00030 
00031 public:
00032   inline string_rep (nat n2): a ((char*) mmx_malloc (n2)), n(n2), l(n2) {}
00033   inline ~string_rep () { mmx_free ((void*) a, l); }
00034   void resize (nat n);
00035   void extend (nat n);
00036 
00037   friend class string;
00038   friend inline nat N (const string& s);
00039   friend inline bool busy (const string& s);
00040   friend inline char* S (string& s);
00041   friend inline const char* S (const string& s);
00042   friend inline char read (const string& s, nat i);
00043   friend string copy (const string& s);
00044   friend string operator * (const string& s, const string& t);
00045   friend int as_int (const string& s);
00046   friend double as_double (const string& s);
00047   friend inline char* inside (const string& s, nat pos);
00048 };
00049 
00050 class string {
00051 INDIRECT_PROTO (string, string_rep)
00052 public:
00053   inline string (nat n=0): rep (new string_rep (n)) {}
00054   string (char c);
00055   string (const char *s);
00056   string (const char *s, nat n);
00057 
00059   friend inline nat N (const string& s) { return s.rep->n; }
00061   friend inline bool busy (const string& s) { return s.rep->n != 0; }
00063   friend inline char* S (string& s) { s.secure (); return s.rep->a; }
00065   friend inline const char* S (const string& s) { return s.rep->a; }
00067   friend inline char read (const string& s, nat i) { return s.rep->a[i]; }
00069   inline char operator [] (nat i) const { return rep->a[i]; }
00070   inline char& operator [] (nat i) { secure (); return rep->a[i]; }
00072   string operator () (nat start, nat end) const;
00074   string& operator << (char c);
00076   string& operator << (const string& t);
00078   string& operator >> (char& c);
00079   bool operator == (const char* s) const;
00080   bool operator != (const char* s) const;
00081   bool operator == (const string& s) const;
00082   bool operator != (const string& s) const;
00083   friend nat hash (const string& s);
00084   friend string copy (const string& s);
00085   friend string operator * (const string& s, const string& t);
00086   friend string as_string (void* ptr);
00087   friend string as_string (short int i);
00088   friend string as_string (short unsigned int i);
00089   friend string as_string (int i);
00090   friend string as_string (unsigned int i);
00091   friend string as_string (long int i);
00092   friend string as_string (long unsigned int i);
00093   friend string as_string (long long int i);
00094   friend string as_string (long long unsigned int i);
00095   friend string as_string (float x);
00096   friend string as_string (double x);
00097   friend string as_string_hexa (int i);
00098   friend int as_int (const string& s);
00099   friend double as_double (const string& s);
00100   friend string unescape (const string& s);
00101   friend char* inside (const string& s, nat pos);
00102 
00103   friend class string_rep;
00104 };
00105 INDIRECT_IMPL (string, string_rep)
00106 
00107 TRUE_TO_EXACT_IDENTITY_SUGAR(,string)
00108 template<> inline string duplicate (const string& s) { return copy (s); }
00109 
00110 inline char* inside (const string& s, nat pos) {
00111   return s.rep->a + pos; }
00112 inline void mem_copy (char* d, char* s, nat n) {
00113   for (nat i=0; i<n; i++) d[i]= s[i]; }
00114 
00115 
00116 
00117 
00118 
00119 string as_string (int i);
00120 string as_string (unsigned int i);
00121 string as_string (void* ptr);
00122 inline string as_string (short int i) {
00123   return as_string ((int) i); }
00124 inline string as_string (short unsigned int i) {
00125   return as_string ((unsigned int) i); }
00126 inline string as_string (signed char i) {
00127   return as_string ((int) i); }
00128 inline string as_string (unsigned char i) {
00129   return as_string ((unsigned int) i); }
00130 string as_string (long int i);
00131 string as_string (long unsigned int i);
00132 string as_string (long long int i);
00133 string as_string (long long unsigned int i);
00134 string as_string (float x);
00135 string as_string (double x);
00136 string as_string (long double x);
00137 
00138 inline string as_string_hexa (ulong i) {
00139   static char buf[sizeof(ulong)*2+1];
00140   snprintf (buf, sizeof(buf), "%lx", i);
00141   return buf; }
00142 int as_int (const string& s);
00143 double as_double (const string& s);
00144 inline string charcode_as_string (int i) {
00145   return string ((char) i); }
00146 inline int string_as_charcode (const string& s) {
00147   ASSERT (N(s) == 1, "single character expected");
00148   return (int) s[0]; }
00149 
00150 
00151 
00152 
00153 
00154 bool is_integer_string (const string& s);
00155 bool is_floating_string (const string& s);
00156 
00157 template<typename C> void
00158 numeric_to_string (const C& x, string& s) {
00159   if (x == 0) s << '0';
00160   else if (x <= 0) { 
00161     s << '-';
00162     numeric_to_string (-x, s);
00163   }
00164   else {
00165     if (x >= 10) numeric_to_string (x/10, s);
00166     s << (char) (((char) '0') + ((char) ((int) (x%10))));
00167   }
00168 }
00169 
00170 template<typename C> bool
00171 string_to_numeric (const string& s, C& val) {
00172   nat i= 0, n= N(s);
00173   val= 0;
00174   if (n == 0) return false;
00175   C eps= 1;
00176   bool ok= true;
00177   if (s[0] == '-') {
00178     i++;
00179     eps= -1;
00180     if (eps > 0) ok= false;
00181   }
00182   if (i == n) return false;
00183   while (i < n) {
00184     if (s[i] < '0' || s[i] > '9') return false;
00185     C c= (C) (s[i] - '0');
00186     C r= 10 * val + (eps * c);
00187     if (val != (r / 10)) ok= false;
00188     val= r;
00189   }
00190   return ok;
00191 }
00192 
00193 STMPL void numeric_to_string (const float& x, string& s);
00194 STMPL void numeric_to_string (const double& x, string& s);
00195 STMPL void numeric_to_string (const long double& x, string& s);
00196 STMPL bool string_to_numeric (const string& s, float& val);
00197 STMPL bool string_to_numeric (const string& s, double& val);
00198 STMPL bool string_to_numeric (const string& s, long double& val);
00199 
00200 template<typename C> bool
00201 is_numeric_string (const string& s) {
00202   C val;
00203   return string_to_numeric<C> (s, val);
00204 }
00205 
00206 template<typename C> string
00207 numeric_as_string (const C& x) {
00208   string s;
00209   numeric_to_string<C> (x, s);
00210   return s;
00211 }
00212 
00213 template<typename C> C
00214 string_as_numeric (const string& s) {
00215   C val;
00216   (void) string_to_numeric<C> (s, val);
00217   return val;
00218 }
00219 
00220 
00221 
00222 
00223 
00224 bool operator <  (const string& s, const string& t);
00225 bool operator <= (const string& s, const string& t);
00226 bool operator >  (const string& s, const string& t);
00227 bool operator >= (const string& s, const string& t);
00230 char* as_charp (const string& s);
00232 void free_charp (char* s);
00234 string escape (const string& s);
00236 string unescape (const string& s);
00238 bool is_quoted (const string& s);
00240 string quote (const string& s);
00242 string unquote (const string& s);
00244 string locase (const string& s);
00246 string upcase (const string& s);
00248 string locase_first (const string& s);
00250 string upcase_first (const string& s);
00252 bool starts (const string& s, const string& what);
00254 bool ends (const string& s, const string& what);
00256 string replace (const string& s, const string& what, const string& by);
00258 int search_forwards (const string& s, const string& what, const int& pos);
00260 int search_backwards (const string& s, const string& what, const int& pos);
00262 string reverse (const string& s);
00264 vector<string> tokenize (const string& s, const string& sep, bool keep=false);
00266 string recompose (const vector<string>& v, const string& sep, bool last=true);
00267 
00268 } 
00269 #endif // __STRING_HPP