Main Page   Class Hierarchy   Alphabetical List   Compound List   File List   Compound Members   File Members  

lStr.cpp

Go to the documentation of this file.
00001 /******************************************************************************/
00002 /*                                                                            */
00003 /* POLiTe - Persistent Object Library Test                                    */
00004 /*                                        Ph.D. Thesis by Mgr. Michal Kopecky */
00005 /*                                                                            */
00006 /* Charles University Prague                                                  */
00007 /*                                                                            */
00008 /******************************************************************************/
00009 /*                                                                            */
00010 /* File name: ...                                                             */
00011 /* Module: ......                                                             */
00012 /*                                                                            */
00013 /******************************************************************************/
00014 
00015 // Standard Header(s)
00016 #include <malloc.h>
00017 #include <stdio.h>
00018 #include <string.h>
00019 #include <ctype.h>
00020 
00021 // Common POLiTe Header(s)
00022 #include <lDefs.h>
00023 
00024 // Own Header
00025 #include <lStr.h>
00026 
00027 int StrLen(const char * const src) {
00028 //counts number of chars in src, returns 0 if src == NULL
00029         return src == NULL ? 0 : strlen(src);
00030         };
00031 
00032 char *StrCpy(char * (&dst), const char * const src)
00033 //copies the source "src" into destination dst
00034 //frees previously allocated memory for dst
00035 //aloocates memory for dst
00036 {
00037         if (dst)
00038                 free(dst);
00039         return (!src /*|| !*src*/)
00040                 ?(dst = NULL)
00041                 :(dst = strcpy((char *)malloc(strlen(src)+1),src));
00042 };
00043 
00044 char *StrCpy(const char * const src)
00045 //copies the source "src" and returns the copy
00046 //aloocates memory for it
00047 {
00048         char *dst = NULL;
00049         return StrCpy(dst,src);
00050 };
00051 
00052 
00053 char *StrExp(char * dst, const char * src, int len)
00054 //copies the source "src" into destination dst, maximum of copied character
00055 //is "len". copy is terminated by \0 char, so the buffer must be at least
00056 //"len+1" characters long
00057 //buffer must exists before calling this method!!!
00058 {
00059         char *aux = dst;
00060         if (src)
00061                 while (len-- && *src)
00062                         *dst++ = *src++;
00063         *dst = '\0';
00064         return aux;
00065 };
00066 
00067 int StrCmp(const char * const dst, const char * const src)
00068 //compares the source "src" with the destination dst
00069 {
00070         if (dst == src)
00071                 return 0;
00072         if (!dst)
00073                 return -1;
00074         if (!src)
00075                 return 1;
00076         return strcmp(dst,src);
00077 };
00078 
00079 int StrCmpUp(const char * const dst, const char * const src)
00080 //compares the source "src" with the destination "dst" in upper case
00081 {
00082         if (dst == src)
00083                 return 0;
00084         if (!dst)
00085                 return -1;
00086         if (!src)
00087                 return 1;
00088         const char *s = dst;
00089         const char *t = src;
00090         while (*s && *t && (toupper(*s) == toupper(*t)))
00091         {
00092                 ++s; ++t;
00093         };
00094         return toupper(*s) - toupper(*t);
00095 };
00096 
00097 char *StrFree(char * (&dst)) {
00098 //frees dynamically allocated string
00099         if (dst)
00100                 free(dst);
00101         return (dst = NULL);
00102         };
00103 
00104 char *StrCat(char * (&dst), const char * const src) {
00105 //concatenates dst and src in given order
00106 //free previously allocated memory for dst
00107 //allocates memory for the result
00108   char *_dst = dst;
00109   if (!src)
00110          return(dst);
00111   dst = (char *)malloc(StrLen(src)+StrLen(dst)+1);
00112   if (_dst) {
00113          strcpy(dst,_dst);
00114          strcat(dst,src);
00115          }
00116   else
00117          strcpy(dst,src);
00118   StrFree(_dst);
00119   return(dst);
00120 };
00121 
00122 char *StrCat(char * (&dst), const int n, const char * const src, ...) {
00123 //concatenates dst_1, ... , dst_n to src in given order
00124 //concatenates src and dst in given order
00125 //free previously allocated memory for dst
00126 //allocates memory for the result
00127   char *_dst = NULL;
00128   int i;
00129   StrCat(_dst, dst);
00130   for (i = 0; i < n; i++)
00131          StrCat(_dst,(&src)[i]);
00132   free(dst);
00133   dst = _dst;
00134   return dst;
00135   };
00136 
00137 char *StrAnd(char * (&dst), const char * const src) {
00138 //returns "(dst) AND (src)"
00139 //free previously allocated memory for dst
00140 //allocates memory for the result
00141   char *_res = NULL;
00142   if (!dst)
00143          return StrCpy(dst,src);
00144   if (!src)
00145          return dst;
00146   StrCat(_res,5,"(",dst,") AND (",src,")");
00147   free(dst);
00148   return dst = _res;
00149   };
00150 
00151 char *StrOr(char * (&dst), const char * const src) {
00152 //returns "(dst) OR (src)"
00153 //free previously allocated memory for dst
00154 //allocates memory for the result
00155   char *_res = NULL;
00156   if (!dst)
00157          return StrCpy(dst,src);
00158   if (!src)
00159          return dst;
00160   StrCat(_res,5,"(",dst,") OR (",src,")");
00161   free(dst);
00162   return dst = _res;
00163   };
00164 
00165 char *StrNot(char * (&dst)) {
00166 //returns "NOT(dst)"
00167 //free previously allocated memory for dst
00168 //allocates memory for the result
00169   char *_res = NULL;
00170   if (!dst)
00171          return dst;
00172   StrCat(_res,3,"NOT(",dst,")");
00173   free(dst);
00174   return dst = _res;
00175   };
00176 
00177 char *StrClause(char * (&dst), const char * const prf) {
00178 //returns "prf dst " if dst is not empty
00179 //if dst is the empty string, returns NULL
00180 //examples:
00181 //              StrClause("ID = 100", "WHERE ") == "WHERE ID = 100 "
00182 //              StrClause(NULL,"WHERE ") == NULL
00183 //free previously allocated memory for dst
00184 //allocates memory for the result
00185   char *_res = NULL;
00186   if (!dst || !*dst)
00187          return dst;
00188   StrCat(_res,4,prf," ",dst," ");
00189   free(dst);
00190   return dst = _res;
00191   };
00192 
00193 void StrSwap(const char * (&s1), const char * (&s2)) {
00194 //Swaps two strings
00195         const char *pom;
00196         pom = s1;
00197         s1 = s2;
00198         s2 = pom;
00199         };
00200 
00201 char *StrSplit(char * (&src), const char delim, char * (&dst)) {
00202 //splits src in form "<dst> <delim> <rest_of_string>"
00203 //returns dst = <dst>, src = <rest_of_string>
00204 //free previously allocated memory for dst and src
00205 //allocates memory for the results
00206         char *Start = src;                      //start of dst inside src
00207         char *End;                                              //end of dst inside src
00208         char *OrgSrc = src;                     //Original src
00209         char *pom;
00210         bool InString = false;          //searching delimiter inside a string
00211         bool WasBackslash = false;      //previous char was backslash
00212         bool NoDelim;                    //there is no delimiter in the src
00213 
00214         StrFree(dst);
00215         if (!src)
00216                 return dst;
00217         while ((*Start == ' ') || (*Start == '\t'))
00218                 Start++;
00219         pom = Start;
00220         while (*pom && ((*pom != delim) || InString || WasBackslash)) {
00221                 if (WasBackslash)
00222                         WasBackslash = false;
00223                 else if (*pom == '\'')
00224                         InString = !InString;
00225                 else if (*pom == '\\')
00226                         WasBackslash = !WasBackslash;
00227                 pom++;
00228                 };
00229         End = pom-1;
00230         NoDelim = (*pom++ == '\0');
00231         while ((End >= Start) && ((*End == ' ') || (*End == '\t')))
00232                 End--;
00233         *++End = '\0';
00234         if (Start <= End)
00235                 StrCpy(dst,Start);
00236         if (NoDelim)
00237                 StrFree(src);
00238         else {
00239                 StrCpy(src = NULL, pom);
00240                 StrFree(OrgSrc);
00241                 }
00242         return dst;
00243         };
00244 
00245 char *StrPrefix(char * (&src), const char delim, char * (&dst)) {
00246 //like StrSplit() function
00247 //if no delimiter is found in the string, return <dst> == NULL,
00248 //meanwhile StrSplit() returns <src> == NULL
00249         StrSplit(src,delim,dst);
00250         if (src == NULL)
00251                 StrSwap((const char *&)src,(const char *&)dst);
00252         return dst;
00253         };
00254 
00255 char *StrPrefixCut(char * (&src), const char delim) {
00256 //like StrPrefix() function
00257 //Prefix - if exists is cut off
00258         char *_Prefix = NULL;
00259         StrPrefix(src,delim,_Prefix);
00260         StrFree(_Prefix);
00261         return src;
00262         };
00263 
00264 char *LongToStr(const long n) {
00265 //returns long number n as a char*, allocates space for the result.
00266         char *_buf = (char *)malloc(33);
00267         char *_res = NULL;
00268 
00269         sprintf(_buf,"%ld",n);
00270         StrCpy(_res,_buf);
00271         StrFree(_buf);
00272         return _res;
00273         };
00274 
00275 char *ULongToStr(const unsigned long n) {
00276 //returns long number n as a char*, allocates space for the result.
00277         char *_buf = (char *)malloc(33);
00278         char *_res = NULL;
00279 
00280         sprintf(_buf,"%lu",n);
00281         StrCpy(_res,_buf);
00282         StrFree(_buf);
00283         return _res;
00284         };
00285 
00286 char *FloatToStr(const double x) {
00287 //returns float number x as a char*, allocates space for the result.
00288         char *_buf = (char *)malloc(33);
00289         char *_res = NULL;
00290 
00291         sprintf(_buf,"%lf",x);
00292         StrCpy(_res,_buf);
00293         StrFree(_buf);
00294         return _res;
00295         };
00296 
00297 long StrToLong(const char *s) {
00298 //returns a char* converted to long.
00299   long result;
00300   sscanf(s,"%l",&result);
00301   return result;
00302   };
00303 
00304 static char *_StrMergeLists(
00305         char * (&dst),
00306         char * (&list1),
00307         char * (&list2),
00308         const char l_delim,
00309         const char *const sep_begin,
00310         const char *const sep_values,
00311         const char *const sep_middle,
00312         const char *const sep_end,
00313         const bool cut_off_prefixes,
00314         const char p_delim
00315         )
00316 {
00317         StrFree(dst);
00318         char * value1 = NULL;
00319         char * value2 = NULL;
00320         const char *separator = sep_begin;
00321 
00322         while (StrSplit(list1,l_delim,value1) && StrSplit(list2,l_delim,value2)) {
00323                 if (cut_off_prefixes) {
00324                         StrPrefixCut(value1,p_delim);
00325                         };
00326                 StrCat(dst,4,separator,value1,sep_values,value2);
00327                 StrFree(value1);
00328                 StrFree(value2);
00329                 separator = sep_middle;
00330                 };
00331         separator = sep_end;
00332         StrCat(dst,separator);
00333         StrFree(list1);
00334         StrFree(list2);
00335         return dst;
00336         };
00337 
00338 char *StrMergeLists(
00339         char * (&dst),
00340         char * (&list1),
00341         char * (&list2),
00342         const char l_delim,
00343         const char *const sep_begin,
00344         const char *const sep_values,
00345         const char *const sep_middle,
00346         const char *const sep_end
00347         )
00348 {
00349         return _StrMergeLists(
00350                 dst,
00351                 list1, list2, l_delim,
00352                 sep_begin, sep_values, sep_middle, sep_end,
00353                 false, ' '
00354                 );
00355         };
00356 
00357 char *StrMergeLists(
00358         char * (&dst),
00359         char * (&list1),
00360         char * (&list2),
00361         const char l_delim,
00362         const char p_delim,
00363         const char *const sep_begin,
00364         const char *const sep_values,
00365         const char *const sep_middle,
00366         const char *const sep_end
00367         )
00368 {
00369         return _StrMergeLists(
00370                 dst,
00371                 list1, list2, l_delim,
00372                 sep_begin, sep_values, sep_middle, sep_end,
00373                 true, p_delim
00374                 );
00375         };
00376 
00377 char *AliasR(int i)
00378 //Returns alias of i-th relation- "r$_i", allocates space for the result.
00379 {
00380         char *dst = StrCpy(dst=NULL, R_PREFIX);
00381         char *stri = LongToStr(i);
00382         StrCat (dst, stri);
00383         StrFree (stri);
00384         return dst;
00385 };
00386 
00387 char *AliasT(int i, int j)
00388 //Returns alias of j-th table of i-th DatabaseObject - "t$_i_j",
00389 //allocates space for the result.
00390 {
00391         char *dst = StrCpy(dst=NULL, T_PREFIX);
00392         char *stri = LongToStr(i);
00393         char *strj = LongToStr(j);
00394                 StrCat (dst, 3, stri, "_", strj);
00395         StrFree (stri);
00396         StrFree (strj);
00397         return dst;
00398 };
00399 
00400 char *AliasQ(int i)
00401 //Returns alias prefix of table aliases of tables for i-th inner query - "t$_i_",
00402 //allocates space for the result.
00403 {
00404         char *dst = StrCpy(dst=NULL, T_PREFIX);
00405         char *stri = LongToStr(i);
00406                 StrCat (dst, 2, stri, "_");
00407         StrFree (stri);
00408         return dst;
00409 };
00410 
00411 char *StrAddPrefix(char * &dst, const char * const src, const char * const delim)
00412 //Adds prefix src to dst-returns src delim dst
00413 //Example:src="ALIAS_1",delim=".",dst="TABLE_1"-result is "ALIAS1.TABLE"
00414 {
00415   char * _res=NULL;
00416   StrCat(_res,3,src,delim,dst);
00417   StrFree(dst);
00418   dst=_res;
00419   return dst;
00420 }
00421 
00422 char * RealiasR(char * &fragment, int begin, int end, int incr)
00423 // Increases the numbers of relation aliases beginning i and ending number j
00424 // of incr
00425 {
00426         if (incr > 0)
00427                 for (int i=end; i>=begin; i--)
00428                 {
00429                         char * _oldalias=AliasR(i);
00430                         char * _newalias=AliasR(i+incr);
00431                         StrReplaceAll(fragment,_oldalias,_newalias,true,true);
00432                         StrFree(_oldalias);
00433                         StrFree(_newalias);
00434                 };
00435         return fragment;
00436 };
00437 
00438 char * RealiasQ(char * &fragment, int begin, int end, int incr)
00439 // Increases the numbers of queries aliases beginning i and ending number j
00440 // of incr
00441 {
00442         if (incr > 0)
00443                 for (int i=end; i>=begin; i--)
00444                 {
00445                         char * _oldalias=AliasQ(i);
00446                         char * _newalias=AliasQ(i+incr);
00447                         StrReplaceAll(fragment,_oldalias,_newalias,true);
00448                         StrFree(_oldalias);
00449                         StrFree(_newalias);
00450                 };
00451         return fragment;
00452 };
00453 
00454 bool StrIsIdentChar(const char c)
00455 {
00456         return ((c>='a')&&(c<='z'))||((c>='A')&&(c<='Z'))||((c>='0')&&(c<='9'))||(c=='_')||(c=='#')||(c=='$');
00457 };
00458 
00459 long StrPos(
00460         const char * const dst,
00461         const char * const oldstr,
00462         bool lwb = false, //left-side word boundary required
00463         bool rwb = false //right-side word boundary required
00464         )
00465 //Finds position of oldstr in dst
00466 //Returns -1 if not successful
00467 {
00468         const char * start;
00469         const char * occur;
00470         bool found = false;
00471         long oldstrlen = StrLen(oldstr);
00472         if (dst==NULL)
00473                 return -1;
00474         start = dst;
00475         // start search from begining of the string
00476         while ((!found) && ((occur=strstr(start,oldstr))!=NULL))
00477         {
00478                 // string was found at occur position
00479                 // check, if it is not enclosed in  apostrophes
00480                 bool in_apo=false; // inside apostrophes
00481                 bool in_quo=false; // inside quotas
00482                 const char *s = start;
00483                 for( ; s < occur; s++)
00484                         if (*s=='"')
00485                         {
00486                                 if (!in_apo)
00487                                         in_quo = !in_quo;
00488                         }
00489                         else if (*s=='\'')
00490                         {
00491                                 if (!in_quo)
00492                                         in_apo = !in_apo;
00493                         };
00494                 if (in_apo)
00495                 {
00496                         while (*s && (*s != '\''))
00497                                 s++;
00498                         start = s;
00499                 }
00500                 else if (in_quo)
00501                 {
00502                         while (*s && (*s != '"'))
00503                                 s++;
00504                         start = s;
00505                 }
00506                 else if (lwb && StrIsIdentChar(*s) && (s>start) && StrIsIdentChar(*(s-1)))
00507                         start = s+1;
00508                 else if (rwb && StrIsIdentChar(*(s+oldstrlen)) && ((s+oldstrlen)>start) && StrIsIdentChar(*(s+oldstrlen-1)))
00509                         start = s+1;
00510                 else
00511                         found=true;
00512         };
00513         if (found)
00514                 return occur-dst;
00515         else
00516                 return -1;
00517 };
00518 
00519 bool StrReplace(
00520         char * &dst,
00521         const char * const oldstr,
00522         const char * const newstr,
00523         bool lwb, //left-side word boundary required
00524         bool rwb //right-side word boundary required
00525         )
00526 //Replaces first occurence of oldstr in dst with newstr
00527 //Returns true if succees
00528 {
00529         char * start;
00530         char * occur;
00531         start = dst;
00532         // start search from begining of the string
00533         long prefixlen = StrPos(dst,oldstr,lwb,rwb);
00534         if (prefixlen>=0)
00535         {
00536                 occur=start+prefixlen;
00537                 char *rest=occur+StrLen(oldstr);
00538                 char *result=(char *)malloc(prefixlen+1);
00539                 StrExp(result,dst,prefixlen);
00540                 StrCat(result,2,newstr,rest);
00541                 StrFree(dst);
00542                 dst=result;
00543                 return true;
00544         }
00545         else return false;
00546 };
00547 
00548 char * StrReplaceAll(
00549         char * &dst,
00550         const char * const oldstr,
00551         const char * const newstr,
00552         bool lwb, //left-side word boundary required
00553         bool rwb //right-side word boundary required
00554         )
00555 //Replaces all occurences of oldstr in dst with newstr
00556 //Returns dst
00557 {
00558         char * start;
00559         char * result=NULL;
00560         long prefixlen;
00561         start = dst;
00562         prefixlen = StrPos(start,oldstr,lwb,rwb);
00563         while(prefixlen>=0)
00564         {
00565                 char c=start[prefixlen];
00566                 start[prefixlen]='\0';
00567                 StrCat(result,2,start,newstr);
00568                 start[prefixlen]=c;
00569                 start=start+prefixlen+StrLen(oldstr);
00570                 prefixlen = StrPos(start,oldstr,lwb,rwb);
00571         };
00572         StrCat(result,start);
00573         StrFree(dst);
00574         dst=result;
00575         return dst;
00576 };
00577 
00578 char *StrAndOnly(char * (&dst), const char * const src) {
00579 //returns "dst AND src"
00580 //free previously allocated memory for dst
00581 //allocates memory for the result
00582   if (!dst)
00583          return StrCpy(dst,src);
00584   if (!src)
00585          return dst;
00586   return StrCat(dst,2," AND ",src);
00587   };
00588 
00589 char *StrEncode(char * (&dst), const char * const src)
00590 // encodes string by inserting backslash before each
00591 // comma, backslash and apostroph character
00592 // allocates new space for the result
00593 // needed to find it in the comma-separated lists
00594 {
00595         int newlen = 0; // for enclosing apostrophs
00596         const char *s;
00597         char *d;
00598         if (src)
00599                 for(s=src; *s; s++)
00600                 {
00601                         newlen++;
00602                         if ((*s=='\\') || (*s=='\'') || (*s==','))
00603                                 newlen++;
00604                 };
00605         StrFree(dst);
00606         if (newlen)
00607         {
00608                 dst = (char *)malloc(newlen+1);
00609                 d = dst;
00610                 for(s=src; *s; s++)
00611                 {
00612                         if ((*s=='\\') || (*s=='\'') || (*s==','))
00613                                 *d++ = '\\';
00614                         *d++ = *s;
00615                 };
00616                 *d = '\0';
00617         };
00618         return dst;
00619 };
00620 
00621 char *StrEncode(char * (&src))
00622 {
00623         char *dst = NULL;
00624         StrEncode(dst,src);
00625         StrFree(src);
00626         src=dst;
00627         return src;
00628 };
00629 
00630 char *StrDecode(char * (&dst), const char * const src)
00631 // takes encoded string and return original one
00632 // by eliminating of backslashes
00633 {
00634         int newlen = 0;
00635         const char *s;
00636         char *d;
00637         if (src && *src)
00638                 for(s=src; *s; s++)
00639                 {
00640                         if (*s=='\\')
00641                                 *s++;
00642                         newlen++;
00643                 };
00644         StrFree(dst);
00645         if (newlen)
00646         {
00647                 dst = (char *)malloc(newlen+1);
00648                 d = dst;
00649                 for(s=src; *s; s++)
00650                 {
00651                         if (*s=='\\')
00652                                 *s++;
00653                         *d++ = *s;
00654                 };
00655                 *d = '\0';
00656         };
00657         return dst;
00658 };
00659 
00660 char *StrDecode(char * (&src))
00661 {
00662         char *dst = NULL;
00663         StrDecode(dst,src);
00664         StrFree(src);
00665         src=dst;
00666         return src;
00667 };

Generated on Sun Jul 14 20:51:15 2002 for POLiTe by doxygen1.2.16