Description
Submission
class Solution { public: bool isNumber(string s) { if(s.empty()) return false; if(s[0] == ' ') return isNumber(s.substr(1, s.size() - 1)); if(s.back() == ' ') return isNumber(s.substr(0, s.size() - 1)); int aCount = 0, bCount = 0, cCount = 0; // a(.b) e c might be valid bool isExponent = false; bool isDecimal = false; bool isSignFound = false; for(int i = 0; i < s.size(); ++i) { char c = s[i]; if(!isdigit(c) && c != 'e' && c != '+' && c != '-' && c != '.') return false; if(c == '+' || c == '-') { if(s[0] == c && !isSignFound) { isSignFound = true; continue; } if(isExponent && s[i-1] == 'e') continue; return false; } if(c == '.') { if(isExponent || isDecimal) return false; isDecimal = true; } if(c == 'e') { if(isExponent) return false; isExponent = true; } if(isdigit(c)) { if(isExponent) { cCount++; continue; } if(isDecimal) { bCount++; continue; } aCount++; } } if(isDecimal || isExponent) { if(aCount == 0 && bCount == 0) return false; } if(isExponent) { if (cCount == 0) return false; } return true; } };
It’s about trial and error…
Local Tests
#include <iostream> using namespace std; class Solution { public: bool isNumber(string s) { if(s.empty()) return false; if(s[0] == ' ') return isNumber(s.substr(1, s.size() - 1)); if(s.back() == ' ') return isNumber(s.substr(0, s.size() - 1)); int aCount = 0, bCount = 0, cCount = 0; // a(.b) e c might be valid bool isExponent = false; bool isDecimal = false; bool isSignFound = false; for(int i = 0; i < s.size(); ++i) { char c = s[i]; if(!isdigit(c) && c != 'e' && c != '+' && c != '-' && c != '.') return false; if(c == '+' || c == '-') { if(s[0] == c && !isSignFound) { isSignFound = true; continue; } if(isExponent && s[i-1] == 'e') continue; return false; } if(c == '.') { if(isExponent || isDecimal) return false; isDecimal = true; } if(c == 'e') { if(isExponent) return false; isExponent = true; } if(isdigit(c)) { if(isExponent) { cCount++; continue; } if(isDecimal) { bCount++; continue; } aCount++; } } if(isDecimal || isExponent) { if(aCount == 0 && bCount == 0) return false; } if(isExponent) { if (cCount == 0) return false; } return true; } }; void assertEqual(string s, bool expected) { Solution sol; cout << s << "," << expected << ": "; cout << ((sol.isNumber(s) == expected) ? "successful" : "failed") << "\n"; } int main() { Solution sol; assertEqual("0", true); assertEqual(" 0.1 ", true); assertEqual("abc", false); assertEqual("1 a", false); assertEqual("2e10", true); assertEqual(" -90e3 ", true); assertEqual(" 1e", false); assertEqual("e3", false); assertEqual(" 6e-1", true); assertEqual(" 99e2.5 " , false); assertEqual("53.5e93", true); assertEqual(" --6 ", false); assertEqual("-+3", false); assertEqual("95a54e53", false); assertEqual(".2e81", true); assertEqual("e9", false); assertEqual(" 005047e+6", true); return 0; }
Submission 210617
class Solution { public: bool isNumber(string s) { vector<int> states(7, 0); states[0] = 1; int state = -1; for(auto ch: s) { if(ch == '+' || ch == '-') { if(state == -1 || state == 4) { ++state; } else { return false; } } else if(ch == '.') { if(state <= 1) { state = 2; } else { return false; } } else if(ch == 'e' || ch == 'E') { if(state < 4 && state >= 1) { state = 4; } else { return false; } } else if(isdigit(ch)) { if(state < 1) { state = 1; } if(state == 2 || state == 4 || state == 5) { ++state; } if(states[4]) state = 6; } else { return false; } if(state == -1) { state = 1; } states[state] = 1; } if(states[2] && !states[1] && !states[3]) return false; if(state == 4 || state == 5) return false; return true; } }; // 0 1 2 3 4 5 6 // +/- => optional(digits => (optional . => digits) => optional e( => +/- => digits )