I have a string like this:
char buffer[] = "blablabla$GPTXT->SOME CODES HERE<-\r\n$GPRMCblablabla";
It is sent from an external device and changes every 1 second.
The string length is over 1000 bytes and consisted of some standard sentences beginning with "$GPXXX" and ending with CRLF. I've written the following function to extract a specific sentence:
int findString(char *src, char *dst, int desLen, char *what2find, char termChar)
{
char *temp;
temp = strstr(src, what2find); ;
if (temp == NULL)
return 0;
else
temp += strlen(what2find);
int j = 0;
while (j<(desLen-1))
{
if (temp[j]==termChar)
break;
dst[j]= temp[j];
j++;
}
dst[j] = '\0';
return 1;
}
So:
int main()
{
char buffer[] =
"$GPGGA,123519,4807.038,N,01131.000,E,1,08,0.9,545.4,M,46.9,M,,*47\r\n
$GPGSA,A,3,04,05,,09,12,,,24,,,,,2.5,1.3,2.1*39\r\n
$GPGSV,2,1,08,01,40,083,46,02,17,308,41,12,07,344,39,14,22,228,45*75\r\n
$GPRMC,123519,A,4807.038,N,01131.000,E,022.4,084.4,230394,003.1,W*6A\r\n
$GPVTG,054.7,T,034.4,M,005.5,N,010.2,K*48\r\n";
char dst[50];
findString(buffer,dst,50,"$GPTXT",'$');
}
finds and return the desired sentence.
But this code has the following problems:
- It is very heuristic. I wonder if there exists some better solutions.
- It depends on a character (i.e. '$') for termination. It may terminate after finding a '$' but not "$GPXXX". The optimal solution may find the characters between two strings, e.g. "$GPTXT" and "$GPRMC". I don't know if it is optimally achievable.
Note that the host processor is a 4Mhz ARM MCU!
P.S: The above-mentioned function works fine in my project. I just want to widen my C programming knowledge!
P.S. 2: Both answers from Lundin and David C. Rankin are nice. Unfortunately I can not accept both of them as answer!
src
is 1000s long, provide details about pre-"blablabla", "SOME CODES HERE<", and post-"blablabla" lengths. Do they each vary in length from 0 to 1000s? 3) Are you familiar withconst
andrestrict
? \$\endgroup\$strstr
is your enemy because it returns a pointer to the beginning of the match, but you want the end (this would have saved you onestrlen
). Another problem: copying one character at a time, don't do this, if speed is important, usememcpy
instead. Also, everything that can be const needs to be const, this helps compilers generate faster code, in your case, thesrc
andwhat2find
should be const. \$\endgroup\$