2016-04-22 3 views
1

Я пытаюсь проанализировать имя файла в соответствии с заданным шаблоном, но не в состоянии улучшить соответствие. Вот это имя образец файла:Regex для разбора имени файла в Java

CRS-ISAU-RPV#3430_Dedalus_Conc.ok.erto_AOTreviglio.doc 

А вот мои требования:

сезам характера # имя файла может содержать что-либо, после #, я должен найти символ _ или символ - отделить строка. Строка между символом (необязательно _ или - - но не оба) может содержать любой другой символ. Поэтому в конце концов после символа # у меня должно быть ровно три (3) _ или - символов. Строка должна заканчиваться .doc или .docx или .odt, но NOT .ok.doc или .ok.docx или .ok.odt.

Вот что я пробовал:

(.*)#([^_-]+)[_-]([^_-]+)[_-]([^_-]+)[_-]([^_-]+)\.[doc|odt|docx].*(?<!\.ok)$ 

Но это заставляет меня закончить строку с .doc.ok или .docs.ok или .docx.ok и на самом деле я хочу, чтобы сохранить расширение файла в конце.

Если я попробовать это:

(.*)#([^_-]+)[_-]([^_-]+)[_-]([^_-]+)[_-]([^_-]+)\..*(?<!ok\.[doc|odt|docx])$ 

это не будет работать.

Любая помощь будет оценена по достоинству. Спасибо :)

+1

Синтаксис '[док | а.с. | DOCX]' не делать то, что вы, кажется, думаете, что он делает. Попробуйте заменить '[]' на неконвертирующую группу: '(? :)' – jsheeran

+1

Попробуйте ['"^([^ #] * # [^ -_] *) [-_] (. *) $ (?: (? <= (<\\ нормально) \\ DOCX $?!..) | (<= (<| (<= (<\\ нормально) \\ док $?!.).?! \\. ok) \\. odt $)) "'] (https://regex101.com/r/eH3wY2/1) –

+0

@ WiktorStribiżew http://www.ocpsoft.org/tutorials/regular-expressions/java -visual-regex-tester/эта ссылка выдает ошибку за то, что вы предлагаете. –

ответ

2

Кажется, вы можете использовать

^([^#]*#[^-_]*)[-_](.*)$(?<=(?<!\.ok)\.(?:docx?|odt)$) 

Объяснение:

  • ^ - начало строки (не требуется при использовании .matches(), но не вредный)
  • ([^#]*#[^-_]*) - Группа 1: любые 0+ символов, кроме # ([^#]*), а затем #, а затем любые символы 0+, кромеи _[-_])
  • (.*)$ - кроме символа новой строки (так как режим DOTALL не указан) матч 0+ символов до конца строки, НО ...
  • (?<=(?<!\.ok)\.(?:docx?|odt)$) - после достижения конца, проверьте .doc или .docx или .odt на конце (см. (?<=\.(?:docx?|odt)$)), которым не предшествует .ok (см. (?<!\.ok)). В PCRE эти условия должны быть разделены, Java regex, похоже, справляется с чередованием внутри lookbehind.

просмотр вперед на основе альтернативы:

^([^#]*#[^-_]*)[-_](?=.*(?<!\.ok)\.(?:docx?|odt)$)(.*)$ 

Смотрите regex101 demo. То же самое, но все проверки конца строки выполняются после сопоставления - или _.

Смотрите Java demo:

List<String> strs = Arrays.asList("CRS-ISAU-RPV#3430_Dedalus_Conc.ok.erto_AOTreviglio.doc", 
      "CRS-ISAU-RPV#3430_Dedalus_Conc.ok.erto_AOTreviglio.docx", 
      "CRS-ISAU-RPV#3430_Dedalus_Conc.ok.erto_AOTreviglio.odt", 
      "CRS-ISAU-RPV#3430_Dedalus_Conc.ok.erto_AOTreviglio.ok.docx", 
      "CRS-ISAU-RPV#3430_Dedalus_Conc.ok.erto_AOTreviglio.ok.odt" 
     ); 
for (String str : strs) { 
    System.out.println("----------\nMatching: " + str); 
    Matcher m = Pattern.compile("^([^#]*#[^-_]*)([-_])(.*)$(?<=(?<![.]ok)[.](?:docx?|odt)$)").matcher(str); 
    if (m.matches()) { 
     System.out.println(m.group(1)); 
     System.out.println(m.group(2)); 
     System.out.println(m.group(3)); 
    } else { System.out.println("No match"); } 
} 
+0

Цените свой ответ. Он пропускает одну вещь, хотя в вопросе: «У меня должно быть ровно три (3) _ или - символа вместе взятые». Это означает, что в совокупности должно быть 3 '_' или' -' Подведение итогов двух символов, они должны быть в целом 3. И между этими символами будут строки любого типа, но не содержащие '#'. Имя файла образца (String) показывает, что существует 3 '_', но вы можете заменить любой' _' на '-', и все же это должно быть совпадение. –

+0

Возможно [это] (https://regex101.com/r/cC2wF4/1)? '^ ([^ # \ П] * # [^ -_ \ п] *) [-_] (= (?:? [^ -_ \ п] * [_-]) {3} [^ -_ \ n] * $) (? =. * (?

+1

Я решил это с помощью вашего ответа. Я буду отмечать ваш ответ как правильно :) Спасибо большое! –

Смежные вопросы