Nie ma to nic wspólnego z flagą MULTILINE; to, co widzisz, to różnica między metodami find()
i matches()
. find()
powiedzie się, jeśli dopasowanie zostanie znalezione w dowolnym miejscu ciągu docelowego, natomiastoczekuje, że wyrażenie regularne będzie pasować do całego ciągu znaków.
Pattern p = Pattern.compile("xyz");
Matcher m = p.matcher("123xyzabc");
System.out.println(m.find()); // true
System.out.println(m.matches()); // false
Matcher m = p.matcher("xyz");
System.out.println(m.matches()); // true
Ponadto MULTILINE
nie znaczy to, co myślisz, że to robi. Wiele osób zdaje się przeskakiwać do wniosku, że musisz użyć tej flagi, jeśli twój docelowy ciąg zawiera znaki nowej linii - to znaczy, jeśli zawiera wiele linii logicznych. Widziałem tutaj kilka odpowiedzi na temat SO, ale w rzeczywistości wszystkie te flagi zmieniają zachowanie kotwic, ^
i $
.
Normalnie ^
pasuje do samego początku ciągu docelowego, a $
pasuje do samego końca (lub przed znakiem nowej linii na końcu, ale na razie zostawimy to na boku). Ale jeśli ciąg zawiera znaki nowej linii, możesz wybrać dla ^
i $
dopasowanie do początku i końca dowolnej linii logicznej, a nie tylko początek i koniec całego ciągu, przez ustawienie flagi MULTILINE.
więc zapomnieć o tym, co oznaczaMULTILINE
i po prostu pamiętać, co to robi: zmienia zachowanie ^
i $
kotwic. Tryb DOTALL
był pierwotnie nazywany "pojedynczą linią" (i nadal jest w niektórych smakach, w tym w Perlu i .NET), i zawsze powodował podobne zamieszanie. Mamy szczęście, że twórcy Javy poszli z bardziej opisową nazwą w tym przypadku, ale nie było rozsądnej alternatywy dla trybu "multiline".
W Perlu, gdzie zaczęło się to szaleństwo, przyznali się do błędu i pozbyli się zarówno trybów "wieloliniowych", jak i "jednoliniowych" w 6 wyrażeń regularnych Perla. Za następne dwadzieścia lat może reszta świata pójdzie w jego ślady.
Próbuję znaleźć wzorzec, który pasowałby do dowolnego ciągu rozpoczynającego się od "Komentarze użytkowników:". Po tym "Komentarze użytkownika:" jest coś, co użytkownik wprowadza w obszarze tekstowym, a zatem może zawierać * cokolwiek * - nawet nowe linie. Wygląda na to, że muszę się dużo nauczyć w regex ... – Nivas
To działa (dziękuję!) Próbowałem wzorca '(? S) Komentarze użytkownika: \ s * (. *)'. Z odpowiedzi na @Amarghosha otrzymałem wzorzec "Komentarze użytkownika: [\ \ s \\ S] *". Wśród nich jest * lepszy * lub * zalecany * sposób lub czy są to tylko dwa różne sposoby robienia tego samego? – Nivas
Obaj mają na myśli to samo; '[\ s \ S]' jest nieco bardziej jednoznaczne ("dopasuj dowolny znak, który jest albo spacji, albo spoza spacji"), '.' jest łatwiejsze do odczytania, ale musisz poszukać' (? s) ' lub modyfikator 'DOTALL' w celu ustalenia, czy nowe linie są włączone czy nie. Wolałbym '.' z zestawem flag' Pattern.DOTALL' (jest to łatwiejsze do odczytania i zapamiętania niż '(? S)', powinieneś użyć tego, co czujesz się najlepiej z. –