Czy możesz sprawić, aby wielkość liter nie była uwzględniana tylko w wyrażeniach regularnych?


101

Widziałem wiele przykładów rozróżniania wielkości liter w całym wyrażeniu regularnym. Zastanawiam się, czy tylko część wyrażenia nie rozróżnia wielkości liter.

Na przykład, powiedzmy, że mam taki ciąg:

fooFOOfOoFoOBARBARbarbarbAr

A jeśli chcę dopasować wszystkie wystąpienia „foo” niezależnie od wielkości liter, ale chcę dopasować tylko wielkie litery „BAR”?

Idealnym rozwiązaniem byłoby coś, co działa w różnych odmianach wyrażeń regularnych, ale interesuje mnie również słyszenie specyficznych dla języka (dzięki, Espo )

Edytować

Link podany przez Espo był bardzo pomocny. Jest tam dobry przykład włączania i wyłączania modyfikatorów w wyrażeniu.

W moim wymyślonym przykładzie mogę zrobić coś takiego:

(?i)foo*(?-i)|BAR

co sprawia, że ​​dopasowywanie nie rozróżnia wielkości liter tylko dla części foo dopasowania.

Wydawało się, że działa to w większości implementacji regexów z wyjątkiem Javascript, Python i kilku innych (jak wspomniano w Espo).

Te duże, nad którymi się zastanawiałem (Perl, PHP, .NET) obsługują zmiany w trybie inline.


To pytanie zostało dodane do często zadawanych pytań dotyczących wyrażeń regularnych przepełnienia stosu w sekcji „Modyfikatory”.
aliteralmind

Odpowiedzi:


88

Perl umożliwia rozróżnianie wielkości liter w wyrażeniach regularnych za pomocą modyfikatora wzorca (? I :).

Nowoczesne smaki wyrażeń regularnych umożliwiają stosowanie modyfikatorów tylko do części wyrażenia regularnego. Jeśli wstawisz modyfikator (? Ism) w środku wyrażenia regularnego, modyfikator zostanie zastosowany tylko do części wyrażenia regularnego na prawo od modyfikatora. Możesz wyłączyć tryby, poprzedzając je znakiem minus. Wszystkie tryby po znaku minusa zostaną wyłączone. Np. (? I-sm) włącza niewrażliwość na wielkość liter i wyłącza zarówno tryb jednoliniowy, jak i wieloliniowy.

Nie wszystkie odmiany wyrażeń regularnych to obsługują. JavaScript i Python stosują wszystkie modyfikatory trybu do całego wyrażenia regularnego. Nie obsługują składni (? -Ismx), ponieważ wyłączenie opcji jest bezcelowe, gdy modyfikatory trybu mają zastosowanie do całych wyrażeń regularnych. Wszystkie opcje są domyślnie wyłączone.

Możesz szybko sprawdzić, jak smak wyrażenia regularnego, którego używasz, obsługuje modyfikatory trybu uchwytów. Wyrażenie regularne (? I) te (? - i) st powinno pasować do testu i TEst, ale nie do teST lub TEST.

Źródło


6

Jakiego języka używasz? Standardowym sposobem byłoby coś takiego jak / ([Ff] [Oo] {2} | BAR) / z włączoną rozróżnianiem wielkości liter, ale na przykład w Javie istnieje modyfikator rozróżniania wielkości liter (? I), który sprawia, że ​​wszystkie znaki po prawej stronie nie rozróżniają wielkości liter i (? -i), co wymusza wrażliwość. Przykład tego modyfikatora wyrażeń regularnych Java można znaleźć tutaj .


+1 Po co robić to bez rozróżniania wielkości liter, skoro można dopasować oba przypadki
Nona Urbiz

11
@NonaUrbiz: Ponieważ wyrażenie (?i)foobarjest bardziej czytelne niż[Ff][Oo]{2}[Bb][Aa][Rr]
Thanatos

1
I dlatego może rosnąć sposób znacznie bardziej owłosione i złożone.
Chop

6

Niestety składnia dopasowywania bez rozróżniania wielkości liter nie jest powszechna. W .NET można użyć flagi RegexOptions.IgnoreCase lub modyfikatora ? I


4

Możesz użyć

(?:F|f)(?:O|o)(?:O|o)

?: W nawiasach w .Net oznacza, że ​​nie przechwytuje i służy tylko do grupowania terminów | (lub) oświadczenie.


26
Czy „[fF] [oO] [oO]” nie jest lepszą alternatywą? W podanym przykładzie możesz nawet posunąć się do „[fF] [oO] \ {2}” ;-)
Tomalak,

4

To prawda, że ​​można polegać na wbudowanych modyfikatorach, jak opisano w sekcji Włączanie i wyłączanie trybów tylko dla części wyrażenia regularnego :

Wyrażenie regularne (?i)te(?-i)stpowinno pasować do testu i TEst, ale nie do teSTlub TEST.

Jednak nieco bardziej obsługiwaną funkcją jest (?i:...)wbudowana grupa modyfikatorów (patrz Zakresy modyfikatorów ). Składnia jest taka (?i:, a następnie wzorzec, który ma być niewrażliwy na cas, a następnie plik ).

(?i:foo)|BAR

Odwrotna : Jeśli wzór jest skompilowany z opcją przypadku niewrażliwych i trzeba uczynić częścią przypadku regex wrażliwy, dodać -po ?: (?-i:...).

Przykładowe zastosowania w różnych językach (zawijanie dopasowań nawiasami ostrymi):

  • - preg_replace("~(?i:foo)|BAR~", '<$0>', "fooFOOfOoFoOBARBARbarbarbAr")( demo )
  • - re.sub(r'(?i:foo)|BAR', r'<\g<0>>', 'fooFOOfOoFoOBARBARbarbarbAr')( demo ) (uwaga, Python reobsługuje wbudowane grupy modyfikatorów od Pythona 3.6)
  • / / - Regex.Replace("fooFOOfOoFoOBARBARbarbarbAr", "(?i:foo)|BAR", "<$&>")( demo )
  • - "fooFOOfOoFoOBARBARbarbarbAr".replaceAll("(?i:foo)|BAR", "<$0>")( demo )
  • - $s =~ s/(?i:foo)|BAR/<$&>/g( demo )
  • - "fooFOOfOoFoOBARBARbarbarbAr".gsub(/(?i:foo)|BAR/, '<\0>')( demo )
  • - gsub("((?i:foo)|BAR)", "<\\1>", "fooFOOfOoFoOBARBARbarbarbAr", perl=TRUE)( demo )
  • - "fooFOOfOoFoOBARBARbarbarbAr".replacingOccurrences(of: "(?i:foo)|BAR", with: "<$0>", options: [.regularExpression])
  • - (używa RE2) - regexp.MustCompile(`(?i:foo)|BAR`).ReplaceAllString( "fooFOOfOoFoOBARBARbarbarbAr", `<${0}>`)( demo )

Nieobsługiwane w , , , std::regex, , .

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.