What is the best and shortest way to split String into two strings?
If i have:
String num = "54.124, 246.1";
And want to get varA and varB from it and get:
varA = "54.124";
varB = "243.1";
Please, don't ask why string.
What is the best and shortest way to split String into two strings?
If i have:
String num = "54.124, 246.1";
And want to get varA and varB from it and get:
varA = "54.124";
varB = "243.1";
Please, don't ask why string.
Find the indexOf() the comma and take the substring() that are before and after
I don't think the question is "why string?", but "why String?"
It is not a good idea to use the String (capital S) class on an Arduino as it can cause memory corruption in the small memory on an Arduino. This can happen after the program has been running perfectly for some time. Just use cstrings - char arrays terminated with '\0' (NULL).
For parsing a cstring have a look at the parse example in Serial Input Basics
...R
Actually it is ESP32, although it has a lot of memory, you are right for using a String.
Meanwhile i made it width substring(), and when came back here i saw J-M-L- suggested the same. Thank you, anyway.
I must say that i saw bunch of "It is not a good idea to use the String (capital S) class on an Arduino.." here, just as, it is copy/paste. I use a String for editing someone else code with LoRa modules. Not much space (and time) to get deeper in it.
Use c-strings aka char* or char[N], then use strtok to extract comma separated values.
Rewriting a big application to replace String objects with c-strings can be a lot of work; if one has a time constraint, I would also continue with String objects.
String the_list = "arduino/esp/raspberry/desktop/laptop";
String array[9]; byte y = 0 ;
for ( byte i = 0 ; i < the_list.length() ; i ++ ) {
if ( the_list.charAt(i) == '/' ) { y++; }
else { array[y] += the_list.charAt(i) ; }
}
// array[0] will return arduino , array[1] returns esp ,etc
sterretje:
Rewriting a big application to replace String objects with c-strings can be a lot of work; if one has a time constraint, I would also continue with String objects.
A time constraint as in a deadline, then I would agree. But a time constraint as in "this needs to run for several time and it must not crash", I would spend the time rewriting the code (depending on the usage of String of course). At least add checks if the allocation doesn't succeed. Just be aware of the consequences of using String (maybe reserve to max length and global scope (uh, uh, ... global)?).
EDIT: In this special case you can use strtok on the String's internal buffer (using c_str() with const_cast<char*>(), because strtok expects a null-terminated c-string). Keep in mind however, that the pointer to the internal buffer will be invalid, if the String goes out of scope and that strtok will modify the String's content (it'll replace the ',' with a '\0').
Sometimes you want to parse a string and process each entry without having to put them all into an array before processing.
This concept could be done using String class as done here or redone using the same concept using any storage method desired.
The main concept is the idea of using a callback to process each entry as it parses. Just another way of solving the problem of processing a string of delimited values for a process.
Sample Code: (int in the callback in 1 based in this example, so process 1 as the first entry in the list)
int parseUsingCallback(String data, char separator, void (*callback)(int, String)) {
String tmpPart = "";
int tmpParsePos = 0;
//--- Split string and run callback on each one found
for (int i = 0; i < data.length(); i++) {
if (data[i] == separator) {
tmpParsePos++;
callback(tmpParsePos, tmpPart);
tmpPart = "";
} else {
tmpPart.concat(data[i]);
}
}
//--- Always send the final chunk of the split data, even if just one
tmpParsePos++;
callback(tmpParsePos, tmpPart);
//return number of parts parsed
return tmpParsePos;
}
Use like this ..
void myProcessFunction(int thePos, String theVal) {
//--- Based on thePos, use theVal as needed
}
parseUsingCallback("some~values~here", '~', &myProcessFunction);