matches - Diferencia entre coincidencias() y find() en Java Regex
find() java (5)
Estoy tratando de entender la diferencia entre matches()
y find()
.
De acuerdo con el Javadoc, (por lo que entiendo), matches()
buscará en toda la cadena incluso si encuentra lo que está buscando, y find()
se detendrá cuando encuentre lo que está buscando.
Si esa suposición es correcta, no puedo ver cuándo querría usar matches()
lugar de find()
, a menos que desee contar el número de coincidencias que encuentra.
En mi opinión, la clase String debería tener find()
lugar de matches()
como un método incorporado.
Para resumir:
- ¿Mi suposición es correcta?
- ¿Cuándo es útil usar
matches()
lugar defind()
?
find()
considerará la subcadena contra la expresión regular, mientras que matches()
considerará la expresión completa.
find()
devolverá verdadero solo si la subcadena de la expresión coincide con el patrón.
public static void main(String[] args) {
Pattern p = Pattern.compile("//d");
String candidate = "Java123";
Matcher m = p.matcher(candidate);
if (m != null){
System.out.println(m.find());//true
System.out.println(m.matches());//false
}
}
matches();
no almacena en búfer, pero find()
buffers. find()
busca primero el final de la cadena, indexa el resultado y devuelve el valor booleano y el índice correspondiente.
Es por eso que cuando tienes un código como
1:Pattern.compile("[a-z]");
2:Pattern.matcher("0a1b1c3d4");
3:int count = 0;
4:while(matcher.find()){
5:count++: }
En 4: el motor de expresiones regulares que utiliza la estructura del patrón leerá todo el código (índice a índice según lo especificado en la regex[single character]
para encontrar al menos una coincidencia. Si se encuentra dicha coincidencia, se indexará y luego se indexará el bucle se ejecutará según el resultado indexado; de lo contrario, si no realizó un cálculo anticipado como el que matches()
; no lo hace. La instrucción while nunca se ejecutaría, ya que el primer carácter de la cadena coincidente no es un alfabeto.
matches()
solo devolverá true si la cadena completa coincide. find()
intentará encontrar la siguiente aparición dentro de la subcadena que coincida con la expresión regular. Tenga en cuenta el énfasis en "el siguiente". Eso significa que el resultado de llamar a find()
varias veces podría no ser el mismo. Además, mediante el uso de find()
puede llamar a start()
para devolver la posición en la que se comparó la subcadena.
final Matcher subMatcher = Pattern.compile("//d+").matcher("skrf35kesruytfkwu4ty7sdfs");
System.out.println("Found: " + subMatcher.matches());
System.out.println("Found: " + subMatcher.find() + " - position " + subMatcher.start());
System.out.println("Found: " + subMatcher.find() + " - position " + subMatcher.start());
System.out.println("Found: " + subMatcher.find() + " - position " + subMatcher.start());
System.out.println("Found: " + subMatcher.find());
System.out.println("Found: " + subMatcher.find());
System.out.println("Matched: " + subMatcher.matches());
System.out.println("-----------");
final Matcher fullMatcher = Pattern.compile("^//w+$").matcher("skrf35kesruytfkwu4ty7sdfs");
System.out.println("Found: " + fullMatcher.find() + " - position " + fullMatcher.start());
System.out.println("Found: " + fullMatcher.find());
System.out.println("Found: " + fullMatcher.find());
System.out.println("Matched: " + fullMatcher.matches());
System.out.println("Matched: " + fullMatcher.matches());
System.out.println("Matched: " + fullMatcher.matches());
System.out.println("Matched: " + fullMatcher.matches());
Saldrá:
Found: false Found: true - position 4 Found: true - position 17 Found: true - position 20 Found: false Found: false Matched: false ----------- Found: true - position 0 Found: false Found: false Matched: true Matched: true Matched: true Matched: true
Por lo tanto, tenga cuidado al llamar a find()
varias veces si el objeto de Matcher
no se restableció, incluso cuando la expresión regular está rodeada por ^
y $
para que coincida con la cadena completa.
matches
devuelven verdadero si toda la cadena coincide con el patrón dado. find
intenta encontrar una subcadena que coincida con el patrón.
matches
intenta hacer coincidir la expresión con toda la cadena y agregar implícitamente una ^
al inicio y $
al final de tu patrón, lo que significa que no buscará una subcadena. De ahí la salida de este código:
public static void main(String[] args) throws ParseException {
Pattern p = Pattern.compile("//d//d//d");
Matcher m = p.matcher("a123b");
System.out.println(m.find());
System.out.println(m.matches());
p = Pattern.compile("^//d//d//d$");
m = p.matcher("123");
System.out.println(m.find());
System.out.println(m.matches());
}
/* output:
true
false
true
true
*/
123
es una subcadena de a123b
por lo que el método find()
produce un resultado verdadero. matches()
solo ''ve'' a123b
que no es lo mismo que 123
y, por lo tanto, da como resultado falso.