CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to support@ccsinfo.com

Convert part of a string to int

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
jd2833



Joined: 28 Mar 2011
Posts: 2

View user's profile Send private message

Convert part of a string to int
PostPosted: Mon Mar 28, 2011 12:49 pm     Reply with quote

I have a beginner problem that I'd like some help with.

My program reads in a directory listing from an SD card. The files found can have any file name, and are stored (one by one) in the string fname[]. E.g.:

Code:
file.txt
STC001.txt
STC004.txt
STC005.txt
thumbs.db


The program is looking for files starting with "STC", then 3 digits, and then the extension ".txt". It needs to find the last file in the list, irrespective of any gaps in the sequence (e.g. there is no file STC002.txt), increase the file number by one, and put the resulting filename in a string.

For example, the value of fname[] after processing the above file list should be "STC006.txt".

To detect if the filename matches my criteria, I was thinking of scanning through the filename string in three parts; one to detect if the filename starts with 'STC', another scan to read the digits, and another scan to check if the extension is '.txt'.

Code:
char const STC[] = "STC";     
char const DTXT[] = ".TXT";     
int8 x;

//check if file starts with "STC"
for (x = 0; (x < 3) && (STC[x] == toupper(finfo.fname[x])) && finfo.fname[x]; x++);
if (x == 3) { //filename starts with "STC"
   //check if next 3 characters are 0..9
   for (; (x < 6) && isdigit((finfo.fname[x])) && finfo.fname[x]; x++) {
      //put read values in int here
   }           
   if (x == 6) { //3 digits read
      //check if next 4 characters are the correct extension '.txt'
      for (; (x < 10) && (DTXT[x] == toupper(finfo.fname[x])) && finfo.fname[x]; x++);
      if (x != 10)
         FilenameValid = TRUE;
   }
}


This leaves me to devise a way to put the detected digits into an integer variable, and to check if the file number is higher than the previous one.

But I bet the more experienced programmers can whip up a smarter and more compact solution. Care to give it a go? Thanks in advance!
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Mon Mar 28, 2011 1:50 pm     Reply with quote

See this thread, which is about the C equivalent of MID$ in Basic:
http://www.ccsinfo.com/forum/viewtopic.php?t=27121
jd2833



Joined: 28 Mar 2011
Posts: 2

View user's profile Send private message

PostPosted: Tue Mar 29, 2011 3:37 am     Reply with quote

Thanks for the hints. I solved it in the following way:

Code:
char *FindLastFile(char *ptr) {
   DIR dir;
   FILINFO finfo;
   FRESULT result;      // FatFs function common result code
   BOOLEAN done;
   char tempstr[13];
   int8 x;
   char const CorrectFile[]="STC.TXT";
   int16 LastFile=0;
   
   //go through all files in directory
   for (done = FALSE;!done;) {
      result = f_readdir(&dir, &finfo);
      if (result != FR_OK) {
         printf(usb_cdc_putc, "FILE SYSTEM ERROR - \r\n");
         return 0;
      }

      // finished ?? (no more files in directory)
      if (!finfo.fname[0]) {
         done = TRUE;
      } else {
         //extract first 3 chars from filename (should match "STC")
         memcpy(tempstr, finfo.fname, 3);
         //extract last 4 chars from filename (should match ".TXT")
         memcpy(&tempstr[3], &finfo.fname[6], 4);
         //terminate string
         tempstr[7] = '\0';

         //check if tempstring == "STC.TXT"
         for (x=0; (x < 7) && (CorrectFile[x] == toupper(tempstr[x])) && tempstr[x]; x++);
         //if filename matches "STCxxx.TXT"
         if (x == 7) {
            //extract numbers from filename
            memcpy(&tempstr[0], &finfo.fname[3], 3);
            //terminate string
            tempstr[3] = '\0';
            //check if extracted characters are in fact digits
            for (x=0; isdigit(tempstr[x]); x++);
            if (x == 3) {
               if (atol(tempstr)>LastFile) {
                  LastFile=atol(tempstr);
               }
               printf(usb_cdc_putc, "isdigit! tempstr: %s, atol: %ld, LastFile: %ld\r\n",
                  tempstr, atol(tempstr), LastFile);
            } else {
               printf(usb_cdc_putc, "nodigit! tempstr: %s, atol: %ld\r\n", tempstr, atol(tempstr));
            }
         }
      }
   }
   sprintf(tempstr, "STC%03ld.TXT", LastFile+1);
   return tempstr;
}


If anything can be improved or done in a more efficient way then I'm always happy to hear feedback!
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group