Różne narzędzia i ich wersje obsługują różne warianty wyrażeń regularnych. Dokumentacja każdego powie ci, co obsługuje.
Istnieją standardy, dzięki którym można polegać na minimalnym zestawie funkcji, które są dostępne we wszystkich zgodnych aplikacjach.
Na przykład wszystkie współczesne implementacje sed
i grep
implementacje podstawowych wyrażeń regularnych określonych przez POSIX (co najmniej jedna wersja standardu, ale ten standard nie ewoluował pod tym względem wiele w ciągu ostatnich kilku dekad).
W POSIX BRE i ERE masz [:alnum:]
klasę znaków. To pasuje do liter i cyfr w twoim języku (pamiętaj, że często zawiera o wiele więcej niż a-zA-Z0-9
chyba, że język to C).
Więc:
grep -x '[[:alnum:]_]\{1,\}'
pasuje do jednej lub więcej alnums lub _.
[\w]
jest wymagany przez POSIX, aby pasował do ukośnika odwrotnego lub w
. Więc nie będzie znaleźć grep
lub sed
wdrożenie gdzie to jest dostępne (chyba poprzez niestandardowe opcje).
Zachowanie dla \w
samego nie jest określone przez POSIX, więc implementacje mogą robić to, co chcą. GNU grep
dodało to dawno temu.
GNU grep
kiedyś posiadało własny silnik wyrażenia regularnego, jednak teraz używa silnika GNU libc (choć osadza własną kopię).
Ma to na celu dopasowanie alnumów i podkreślników w Twoim regionie. Jednak obecnie ma błąd polegający na tym, że dopasowuje tylko znaki jednobajtowe (na przykład nie é w ustawieniach regionalnych UTF-8, nawet jeśli jest to wyraźnie litera i mimo że pasuje do é we wszystkich lokalizacjach, w których é jest pojedynczym postać).
Istnieje również \w
operator wyrażeń regularnych w wyrażeniach regularnych Perla i PCRE. PCRE / perl nie są wyrażeniami regularnymi POSIX, to po prostu kolejna rzecz.
Teraz, gdy GNU grep -P
używa PCRE, ma ten sam problem, co bez niego -P
. Można go jednak obejść, używając (*UCP)
(chociaż ma to również skutki uboczne w lokalizacjach innych niż UTF8).
GNU sed
używa także wyrażeń regularnych GNU libc do własnych wyrażeń regularnych. Używa go w taki sposób, że nie ma tego samego błędu co GNU grep
.
GNU sed
nie obsługuje PCRE. Kod zawiera pewne dowody, że próbowano go już wcześniej, ale wydaje się, że nie jest już w porządku obrad.
Jeśli chcesz mieć wyrażenia regularne Perla, po prostu użyj perl
.
W przeciwnym razie powiedziałbym, że zamiast próbować polegać na fałszywej niestandardowej funkcji twojej konkretnej implementacji sed
/ grep
, lepiej trzymać się standardu i używać [_[:alnum:]]
.
[_[:alnum:]]
Jest to miłe obejście, które pozwala mi przedłużyć go tak jak[\w/]
([_[:alnum:]/]
w tym przypadku).grep
.Masz rację -
\w
jest częścią wyrażeń regularnych kompatybilnych z PCRE. Nie jest to jednak część „standardowego” wyrażenia regularnego. http://www.regular-expressions.info/posix.htmlNiektóre wersje
sed
mogą go wspierać, ale sugeruję najprostszym sposobem jest po prostu użyćperl
wsed
trybie określając-p
flagę. (Wraz z-e
). (Więcej szczegółów wperlrun
)Ale nie potrzebujesz
[]
tego w tym przykładzie - dotyczy to grup ważnych rzeczy.Lub w systemie Windows:
Zobacz
perlre
więcej materiałów PCRE.Możesz pobrać perl tutaj: http://www.activestate.com/activeperl/downloads
źródło
\w
i[\w]
na moje pytanie. Zaktualizuję go o dane wyjściowe każdego polecenia, aby wyjaśnić, które z nich działa, a które nie. W szczególnoścised
rozumie\w
, ale nie[\w]
. Ponadto muszę[\w]
pracować, ponieważ chcę[\w/]
na przykład używać .perl
można to zrobić :).\w
był w GNU grep (w latach 80.) zanim był w perlu, a w GNU emacs prawdopodobnie nawet wcześniej.Podejrzewam, że
grep
ised
inaczej decyduję, kiedy zastosować,[]
a kiedy rozwinąć\w
. W perl regex\w
oznacza dowolny znak słowa i[]
zdefiniuj grupę, aby zastosować dowolny ze znaków jako dopasowanie. Jeśli „rozszerzysz”\w
poprzednią[]
, będzie to klasa znaków wszystkich znaków słownych. Jeśli zamiast tego zrobisz[]
najpierw, będziesz mieć klasę znaków z dwoma znakami,\
aw
więc będzie pasować do dowolnego wzoru zawierającego jeden lub więcej z tych dwóch znaków.Tak więc wydaje się, że
sed
jest widząc[]
i traktując ją jako zawierającą dokładnie dopasować znaki zamiast cześć specjalną sekwencję\w
, jakperl
igrep
zrobić. Oczywiście,[]
w tym przykładzie są całkowicie niepotrzebne, ale można sobie wyobrazić przypadki, w których byłoby to ważne, ale wtedy można sprawić, że będzie działać z parens i ors.źródło
\
jest kodem ucieczkowym i można go użyć do zmiany znaczenia separatorów. Z natury oznacza to, że musi mieć wyższy priorytet niż jakakolwiek inna rzecz. Myślę, że bardziej prawdopodobne jest to, że nie został zaimplementowany, ponieważ\w
nie jest częścią specyfikacji wyrażeń regularnychecho whe\\ere | sed -r 's/[\w]+/gone/g
daje migonehegoneere
to, jakby pasowało do każdego z w` and
'i dokonywało zamiany