Leetcode: Valid Number
This question is asked a lot at Facebook. Here it is, and it has an extremely low acceptance submission rate around 15%, so this is an extremely difficult question.
A valid numbers can be split into:
1. A decimal number or an integer
2. An 'e' or an 'E' followed by an integer.
A decimal number can be split into:
1. (Optional) A sign character (either '+' or '-')
2. One of the following formats:
At least one digit followed by dot '.'
At least one digit followed by dot '.' followed by at least one digit.
A dot '.' followed by at least one digit.
An integer can be split into
1. A sign character
2. At Least one digit.
Given a string s, return if s is a valid number.
Here are the examples:
Example 1:
Input: s = "0"
Output: true
Example 2:
Input: s = "e"
Output: false
Example 3:
Input: s = "."
Output: false
Example 4:
Input: s = ".1"
Output: true
Constraints:
1 <= s.length <= 20
s consists of only English letters (both uppercase and lowercase), digits (0-9), plus '+', minus '-', or dot '.'.
And below I will enumerate the code to solve this type of problem.
According to the user balint, we need the number to match some sort of regular expression.
[-+]?(([0-9]+(.[0-9]*)?)|.[0-9]+)(e[-+]?[0-9]+)?.
The first part is obvious because we have a decimal place in the middle of the number or there can be a number before a decimal number, or none, either way works.
You either get a +- which is an optional or a integer + "." + another integer.
The second part has an E value and see if there is a +- value and a number from 0 to 9. There is also a method to do this in Javascript.
Here's the Java method:
public boolean isNumber(String s) {
s = s.trim();
if(s.length() == 0) return false;
boolean eSeen = false;
boolean dotSeen = false;
boolean numSeen = false;
for(int i = 0; i < s.length(); i++) {
char curr = s.charAt(i);
//first check if there is a digit, to ensure a number has been seen
if(Character.isDigit(curr)) {
numSeen = true;
continue;
}
switch(curr) {
case 'e':
case 'E':
//there has to be a digit before an 'e' or an 'E' character.
if(eSeen || !numSeen) return false;
if(i == s.length() - 1) return false;
eSeen = true;
continue;
//there should only be one dot and the e should be after the dot.
case '.' :
if(dotSeen) return false;
if(eSeen) return false;
dotSeen = true;
continue:
//either the character +- has to be in the beginning, or an e has to be after the character.
case '-':
case '+':
if(i > 0 && s.charAt(i - 1) != 'e' && s.charAt(i - 1) != 'e') return false;
if(i == s.length() - 1) return false;
continue;
default:
return false;
}
}
//pass all the cases first in the for loop and then we find a number.
return numSeen;
}
and here's the method in Javascript:
var isNumber = function(s) {
//regular expression [-+]?(([0-9]+(.[0-9]*)?)|.[0-9]+)(e[-+]?[0-9]+)?.
return /^[+-]?(\d+\.?|\d*\.\d+)(e[+-]?\d+)?$/i.test(s);
}


Comments
Post a Comment