Some Arduino users want to learn C/C++ programming, Some just want to get their project running reliably. SafeString improves reliability for string handling. They can choose to re-write the c-string handling with the necessary char counting, null termination and index bounds checking, from stratch, OR use a pre-written pre-tested library.
I agree array handling is a necessary technique, but c-string processing is very easy to code incorrectly and takes a lot of effort to continually get correct. SafeString avoids that extra work. Well worth the effort to learn the SafeString library. The detailed tutorial helps a lot.
J-M-L I don't agree that using a library deprives the user of gaining the same knowledge. In fact the opposite, the library provides the code that does the job and can be used as learning examples.
The parsing convention you are proposing is un-reliable and does not detect data or format errors see the examples below.
Re atoi() versus SafeString.toInt()
C/C++ programmers often ignore the function returns and that is the problem in this case.
SafeString.toInt() returns false if the conversion 'fails' See the code and code comments in my posting above. When SafeString.toInt() returns false the argument int is left unchanged.
If you don't check the return you won't know if the conversion failed or not.
I did not add an error msg for this error because it is not an error you can usually fix by increasing the char buffer size or changing the code. It is most commonly an input data error that needs to be caught and handled.
The problems with atoi() mean you cannot write robust code that detects bad data. Its deficiencies are mentioned in the SafeString tutorial and covered in detail in the SafeStringToNum.ino example sketch that comes with the library.
As per J-M-L's post to even consider using atoi(), your allowable data range must exclude 0.
So atoi() is not at all useful for general purpose coding.
Just because atoi() returns an answer in no way implies the input was that int
For example
if atoi() returns 0 you have no idea if the input was 0 or some non-int or just an empty string
if atoi() returns 5 you don't know if the input was 5 or 5a or 5somethings
if atoi() returns -7616 you don't know if the input was -7616 or 123456 (on Uno)
void setup() {
long v=0;
Serial.begin(115200);
Serial.println(F(" atoi() tests"));
v = atoi("");
Serial.print(F(" \"\" v=")); Serial.println(v);
v = atoi("5a");
Serial.print(F(" \"5a\" v=")); Serial.println(v);
v = atoi("123456");
Serial.print(F(" \"123456\" v=")); Serial.println(v);
}
void loop() {}
Not many people would consider 5a or 5a, to be a number.
SafeString toInt() returns false for all of these.
Why did you decide to only accept the conversion if there are just trailing spaces (or similar)?
atoi() ignores leading white space as does strtol() so it did not seem reasonable to complain about trailing white space. Also in Excel it does not cause number conversions to fail.
So as a general purpose method for the conversion of strings to ints, atoi() fails miserably.
Just because C/C++ provides a poorly coded method does not mean we should use it.
Arduino String toInt() is no better.
They should not be recommended to beginners as the way to do things. It will only cause them problems later.
It is possible to code a reliable conversion, which is what SafeString.toInt() does.
bool SafeString::toInt(int &i) {
cleanUp(); // does nothing if not wrapping a char[]
if (len == 0) {
return false; // not found
}
char* endPtr;
long result = strtol(buffer, &endPtr, 10);
if (result > INT_MAX) {
return false;
}
if (result < INT_MIN) {
return false;
}
// check endPtr to see if number valid 5a is invalid, 5. is valid
if (endPtr == buffer) { // no numbers found at all
return false;
} // else
// else check for trailing white space
while (*endPtr != '\0') {
if (!isspace(*endPtr)) { // number not terminated by white space
return false;
}
endPtr++;
}
// else all OK
i = result;
return true; // OK
}
I think is un-reasonable to expect beginners, or even experienced programmers, to have to code that when they want to do a conversion that reliably converts only valid ints. Using a pre-code, pre-tested library instead makes more sense.
C's c-string methods have a lot of acknowledged problems for coders, which is why C++ Strings were introduced. SafeString fixes the problems of using Strings on small micros and also fixes these problems with number conversions.