You don't use strtok
the way it should:
char* text = strtok(s,":");
while(text != NULL){
text = strtok(NULL,":");
}
Your code just replaces, in s
, all occurrences of :
with 0
(i.e. a byte of value 0, not the ASCII value of '0'
), thus terminating each substring.
At the end of displayString(text)
call from loop()
, text
still points to the 1st character of the original string (in your post 4:288:18464:288:4
), but that string now terminates at the position of the first :
, which explains why Serial.println(text)
prints just 4
.
Now if you want to split the original string into an array of substrings, as asked in your question, you need to modify displayString
this way:
// Maximum number of substrings expected
const int MAX_SUBSTRINGS = 5;
// Array of pointers to each substring after displayString() has been called
static char* substrings[MAX_SUBSTRINGS];
void displayString(char* s) {
// First clear the array of substrings
for (int i = 0; i < MAX_SUBSTRINGS; i++)
substrings[i] = 0;
// Now split the input string
char* text = strtok(s,":");
int i = 0;
while (text != 0 && i < MAX_SUBSTRINGS) {
// A toekn was found: append it to the array of substrings
substrings[i++] = text;
text = strtok(0,":");
}
}
After calling displayString(text)
, you can use its result in loop()
as follows:
void loop()
{
if (Serial.available() > 0)
{
str = Serial.readStringUntil(',');
str.toCharArray(text,99);
}
displayString(text);
for (int i = 0; i < MAX_SUBSTRINGS; i++) {
if (substrings[i] != 0)
Serial.println(substrings[i]);
}
}
Note that this will work ONLY if the original string contains no more than 5 substrings delimited by :
. If the max number of substrings cannot be known at compile time, then you'll have to use dynamic allocation, which is generally not a very good idea on embedded platforms.