Мета-символ (.) І звичайна крапка Java RegEx?


150

В Java RegEx, як з’ясувати різницю між .(крапкою) мета-символом і звичайною крапкою, як ми використовуємо в будь-якому реченні. Як впоратися з такою ситуацією для інших персонажів мета теж як ( *, +, \d, ...)

Відповіді:


276

Якщо ви хочете, щоб крапка або інші символи з особливим значенням у регулярних виразах були нормальним символом, вам доведеться уникати її з нахилом. Оскільки регулярні вирази на Java - це звичайні рядки Java, вам потрібно уникнути самої косої риски, тому вам потрібні дві зворотні косої риси, наприклад\\.



18
Майте на увазі, що відмови від зворотної косої риси залежить від того, як ви постачаєте регулярний вираз. якщо з жорстким кодом вам потрібно використовувати: "\\." , якщо читаючи з необробленого джерела (наприклад, текстовий файл), ви використовуєте лише одну зворотну косу рису: \.
Пол

25

Рішення, запропоновані іншими членами, не працюють для мене.

Але я виявив це:

щоб уникнути крапки в java regexp write [.]


2
Те ж, \\.не працювало для мене: \.скаржився, що .не потрібно уникати, \\.змусив подумати, що це \.замість цього ., \\\.а будівельник кинув помилку, [.]було єдиним, що спрацювало.
mithunc

1
@mithunc Це не дивно, \\.усередині рядка-літералу ви отримуєте \.те, що саме регулярному вираженню потрібно бачити крапку як буквальну крапку замість відповідника будь-якого символу.
klaar

16

Регулярні вирази стилю Perl (на яких більш чи менш базується двигун regex Java) трактують такі символи як особливі символи:

.^$|*+?()[{\мають особливе значення поза класами символів,

]^-\мають особливе значення всередині класів символів ( [...]).

Тому вам потрібно уникати цих (і тільки тих) символів залежно від контексту (або, у випадку класів символів, розміщувати їх у положеннях, де їх не можна неправильно трактувати).

Потрібно уникати інших символів, але деякі двигуни регулярних виразів трактуватимуть це як синтаксичні помилки, наприклад \_, спричинить помилку в .NET.

Деякі інші призведуть до помилкових результатів, наприклад \<, інтерпретується як буквальне <в Perl, але egrepце означає "межа слова".

Так пишуть -?\d+\.\d+\$в матчі 1.50$, і -2.00$т.д. , і [(){}[\]]для класу символів , який відповідає всі види дужок / фігурні дужки / круглі дужки.

Якщо вам потрібно перетворити рядок введення користувача в безпечну для регулярних виразів форму, скористайтеся java.util.regex.Pattern.quote.

Подальше читання: Блог RegexGuru Яна Гойварта про ті, що уникають метахарактерів


4

Уникнути спеціальних символів за допомогою нахилу. \., \*, \+, \\d, І так далі. Якщо ви не впевнені, ви можете уникнути будь-якого неабеткового символу, будь то спеціальний чи ні. Див . Javadoc для java.util.regex.Pattern для отримання додаткової інформації.


Уникнення неспеціальних символів зайве може працювати на деяких мовах, а в інших може виходити з ладу, тому краще не вдаватися до звички.
Тім Піцкер

1
Це питання стосується конкретно Java, а в docs.oracle.com/javase/6/docs/api/java/util/regex/… йдеться про те, що "зворотна косою рисою може бути використана раніше, ніж алфавітний символ незалежно від того, чи є цей символ частина незбудованої конструкції ".
Крістофер Хаммарстрем

2

Ось код, який можна безпосередньо скопіювати:

String imageName = "picture1.jpg";
String [] imageNameArray = imageName.split("\\.");
for(int i =0; i< imageNameArray.length ; i++)
{
   system.out.println(imageNameArray[i]);
}

А що робити, якщо помилково залишилися пробіли до або після "". в таких випадках? Завжди найкращою практикою є розгляд і цих просторів.

String imageName = "picture1  . jpg";
String [] imageNameArray = imageName.split("\\s*.\\s*");
    for(int i =0; i< imageNameArray.length ; i++)
    {
       system.out.println(imageNameArray[i]);
    }

Тут \\ s * є, щоб розглянути пробіли та дати вам лише потрібні розбиті рядки.


1

Я хотів відповідати рядок, який закінчується на ". *" Для цього мені довелося використовувати наступне:

"^.*\\.\\*$"

Якесь дурне, якщо ви задумаєтесь: D Ось що це означає. На початку рядка може бути будь-який символ, нульовий або більше разів, після якого крапка "". слідом за зіркою (*) в кінці рядка.

Я сподіваюся, що це стане в нагоді для когось. Дякуємо за зворотний нахил Фабіану.


Просто використовуйте "\\.\\*$"тоді. Не потрібно відповідати початку рядка, якщо це не має для вас значення.
Ophidian

Так, ви праві. Якщо чесно, я не можу згадати випадок використання для цього: /
Atspulgs

Не було на самому ділі , щоб допомогти вам , але і допомагати іншим , дивлячись на ваш пост: P
Ophidian

0

Якщо ви хочете закінчити, перевірте, чи закінчується ваше речення на ". ", Тоді вам слід додати [\. \ ] $ До кінця шаблону.


0

Я робив базовий масив у JGrasp і виявив, що за допомогою методу accessor для масиву char [] [] використовувати ('.'), Щоб розмістити одну крапку.

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.