eg_io.c

Go to the documentation of this file.
00001 /* EGlib "Efficient General Library" provides some basic structures and
00002  * algorithms commons in many optimization algorithms.
00003  *
00004  * Copyright (C) 2005 Daniel Espinoza and Marcos Goycoolea.
00005  * 
00006  * This library is free software; you can redistribute it and/or modify it
00007  * under the terms of the GNU Lesser General Public License as published by the
00008  * Free Software Foundation; either version 2.1 of the License, or (at your
00009  * option) any later version.
00010  *
00011  * This library is distributed in the hope that it will be useful, but 
00012  * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 
00013  * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public 
00014  * License for more details.
00015  *
00016  * You should have received a copy of the GNU Lesser General Public License
00017  * along with this library; if not, write to the Free Software Foundation,
00018  * Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA 
00019  * */
00020 #include "eg_io.h"
00021 void EGmvar (char *str,
00022              int nind,
00023              const char *header,
00024              ...)
00025 {
00026 
00027   /* local variables */
00028   char lstr[4096];
00029   va_list largs;
00030 
00031   /* first we put the header in the destination */
00032   str[0] = '\0';
00033   strcat (str, header);
00034   strcat (str, "(");
00035 
00036   /* now we initialize the va_list */
00037   va_start (largs, nind);
00038   while (--nind)
00039   {
00040     snprintf (lstr, (size_t)4095, "%d", va_arg (largs, int));
00041     strncat (str, lstr, (size_t)4095);
00042     strncat (str, ",", (size_t)4095);
00043   }
00044   snprintf (lstr, (size_t)4095, "%d", va_arg (largs, int));
00045   strncat (str, lstr, (size_t)4095);
00046   strncat (str, ")", (size_t)4095);
00047 
00048 
00049   /*end */
00050   va_end (largs);
00051   return;
00052 }
00053 
00054 /* Given a string 'input' this function uses EGioParse to separate
00055  * up to N words in it, we assume that argc is an array of pointers to strings
00056  * of size N, and note that the input array will be changed. */
00057 void EGioNParse (char *input,
00058                  int max_argc,
00059                  const char *delim,
00060                  const char *comment,
00061                  int *argc,
00062                  char **argv)
00063 {
00064 
00065   char *next;
00066 
00067   for ((*argc) = 0, next = input; ((*argc) < max_argc) && next; (*argc)++)
00068   {
00069     EGioParse (&next, &input, delim, comment);
00070     if (next == 0)
00071       break;
00072     argv[(*argc)] = next;
00073   }
00074 
00075   return;
00076 }
00077 
00078 /* given two *pointers 'next' and 'current' and a constant set  
00079  * of strings (parse delimiters), it store in 'next the next 
00080  * meaningfull string, and in current the rest of the secuence, 
00081  * the idea is to iterate over 'next' while it is not true; 
00082  * you have to store the original pointer to the string stream 
00083  * elsewere; also, we assume that the original stream is 
00084  * terminated with '\0'; also, it will discaard any sub-string 
00085  * that start with #, that is inteded for discard comments.
00086  * NOTE: this function WILL change the original string!!!!!
00087  * There is no guarantee on how it will be changed. */
00088 void EGioParse (char **next,
00089                 char **current,
00090                 const char *delim,
00091                 const char *comment)
00092 {
00093 
00094   /* local variables */
00095   int i;
00096   char *ctmp;
00097   char *curchar = *current;
00098 
00099   /* if the current line is NULL we stop */
00100   if (*current == 0)
00101   {
00102     *next = 0;
00103     return;
00104   }
00105 
00106   /* first try to find a meaningful caracter */
00107   while ((((*curchar < 32) || (*curchar > 126))) && (*curchar != '\0'))
00108     curchar++;
00109 
00110   /* we check for sequences of delimiters */
00111   while (index (delim, *curchar) && (*curchar != '\0'))
00112     curchar++;
00113 
00114   /* if we are at the end, we stop */
00115   if ((*curchar) == '\0')
00116   {
00117     *next = *current = 0;
00118     return;
00119   }
00120 
00121   /* now we see if it is a comment, and if it is we discard everything */
00122   if (index (comment, *curchar))
00123   {
00124     *next = *current = 0;
00125     return;
00126   }
00127 
00128   /* now we know that we have a meaningful token, we only need to find 
00129    * the next delimiter */
00130   *next = curchar;
00131   /* we look at the end of this stream */
00132   *current = index (curchar, 0);
00133   i = strlen (delim);
00134   while (i)
00135   {
00136     i--;
00137     ctmp = index (curchar, delim[i]);
00138     if (ctmp && (ctmp < *current) && (ctmp > *next))
00139       *current = ctmp;
00140   }
00141 
00142   /* now we assume that all non-printable characters are also delimiters */
00143   i = 32;
00144   while (i)
00145   {
00146     i--;
00147     ctmp = index (curchar, i);
00148     if (ctmp && (ctmp < *current) && (ctmp > *next))
00149       *current = ctmp;
00150   }
00151 
00152 
00153   /* at this stage *current point to the next delimiter or \0 */
00154   if (index (curchar, 0) == *current)
00155   {
00156     *current = 0;
00157     return;
00158   }
00159 
00160   /* otherwise there is going to be a non null current and we have to 
00161    * add the \0 to the end of next */
00162   **current = 0;
00163   (*current)++;
00164 
00165   /* ending */
00166   return;
00167 }
00168 
00169 /* this discard all lines starting with comments and stores the next 
00170  * leading line in current and the next token in next, we assume that next 
00171  * does not contain data, and that current store the remainings of the
00172  * current line */
00173 void EGioDisCom (char **next,
00174                  char **current,
00175                  const char *delim,
00176                  const char *comment,
00177                  char *store,
00178                  unsigned int storeSize,
00179                  FILE * in)
00180 {
00181 
00182   /* local variables */
00183   int status = 1;
00184 
00185   /* if no current line we read it from the file */
00186   if (!(*current))
00187   {
00188     status = (store == fgets (store, (int) storeSize, in));
00189     *current = store;
00190   }
00191   /* we process the current line, and while the line does
00192    * not have a token we look the next line */
00193   EGioParse (next, current, delim, comment);
00194   while (!(*next) && status)
00195   {
00196     status = (store == fgets (store, (int) storeSize, in));
00197     *current = store;
00198     EGioParse (next, current, delim, comment);
00199   }
00200   /* ending */
00201   return;
00202 }
00203 
00204 /* ========================================================================= */
00205 void EGdisplayString (void *str,
00206                       FILE * file)
00207 {
00208   fprintf (file, "%s", (char *) str);
00209 }
00210 
00211 /* ========================================================================= */
00212 int EGioReadLine(char*const str,size_t const max_len, FILE*file)
00213 {
00214   char c=0;
00215   size_t len = max_len ;
00216   while(((c=getc(file))!=EOF) && (c!='\n') && --len)
00217   {
00218     str[max_len-1-len] = c;
00219   }
00220   str[max_len-len] = '\0';
00221   TEST((max_len - len)==0 && c!= '\n',"Nothing to be read"); 
00222   return 0;
00223 }

Generated on Wed Nov 21 09:38:13 2007 for MTgomory by  doxygen 1.4.6