2011-09-14 18 views
6

Próbuję dopasować wyrażenie regularne w języku Perl. Mój kod wygląda następująco:Uciekające znaki specjalne w języku Perl regex

my $source = "Hello_[version]; Goodbye_[version]"; 
my $pattern = "Hello_[version]"; 
if ($source =~ m/$pattern/) { 
    print "Match found!" 
} 

Problem pojawia się, że nawiasy oznaczają klasę postaci (tak czytałem), gdy Perl próbuje dopasować regex, a kończy mecz się niepowodzeniem. Wiem, że mogę uciec z nawiasami przy pomocy \[ lub \], ale wymagałoby to kolejnego bloku kodu, aby przejść przez ciąg i wyszukać nawiasy. Czy istnieje sposób na automatyczne ignorowanie nawiasów bez unikania ich pojedynczo?

Szybka uwaga: nie mogę po prostu dodać ukośnika odwrotnego, ponieważ jest to tylko przykład. W moim prawdziwym kodzie, $source i $pattern pochodzą zarówno spoza kodu Perla (URIEncoded lub z pliku).

Odpowiedz

10

Używasz Wrong Tool dla zadania.

Nie masz wzoru! Brak znaków regex w $ wzór!

Masz ciąg literowy.

index() służy do pracy z dosłownych strun ...

my $source = "Hello_[version]; Goodbye_[version]"; 
my $pattern = "Hello_[version]"; 
if (index($source, $pattern) != -1) { 
    print "Match found!"; 
} 
+0

+1 Do korzystania z indeksu() – sln

+0

Co to jest "znak regex"? Miałem wrażenie, że regex jest po prostu środkiem dopasowywania ciągów lub wzorów w strunach, a nie określonym zbiorem znaków, chyba że jest inny sens, którego nie jestem świadomy? Chociaż, dziękuję za indeks(). Zrobię to, gdy jutro będę przy moim serwerze; Myślę, że index() będzie działał lepiej i będzie czystszy niż dopasowanie do wyrażenia regularnego. – CoV

+0

"regex character" był literówką, chciałem napisać "regex metacharacter". – tadmc

11

Zastosowanie quotemeta():

my $source = "Hello_[version]; Goodbye_[version]"; 
my $pattern = quotemeta("Hello_[version]"); 
if ($source =~ m/$pattern/) { 
    print "Match found!" 
} 
11

\Q wyłączy metaznaki aż \E zostanie znaleziony lub koniec wzorca.

my $source = "Hello_[version]; Goodbye_[version]"; 
my $pattern = "Hello_[version]"; 
if ($source =~ m/\Q$pattern/) { 
    print "Match found!" 
} 

http://www.anaesthetist.com/mnm/perl/Findex.htm

+0

Dzięki Wiedziałem, że to proste rozwiązanie, które działało idealnie – CoV

+0

Zmienione moja "zaakceptowana odpowiedź", przepraszam, ale podczas gdy twoja działała dobrze, myślę, że 'index()' było naprawdę tym czego szukałem. Dzięki jednak! – CoV

-1

Cytując $pattern celowość wyrażeń regularnych, chyba że jej wykorzystanie jako znany dosłowny i dumpingu w prawdziwy regex.

edit
W przeciwnym razie po prostu używać index() znaleźć położenie podciągu. Dzięki tym informacjom wystarczy użyć substr(), aby wyodrębnić otaczające dane, jeśli to konieczne.

+0

użyć substr() do czego? – tadmc

+0

Chciałbym użyć index(), aby uzyskać position, następnie substr() (opcjonalnie) w celu wyodrębnienia danych resztkowych. – sln

0

można uciec zestaw znaków specjalnych w wyrażeniu za pomocą następującego polecenia.

expression1 = 'tekst ze znakami specjalnymi jak $%()';

expression1 = ~ s/[\? * + \^\ $ [] \() {} \ | -]/"\ $ &"/eg;

To ucieczka wszystkie znaki specjalne

print „wyrażenie1' ;! # Tekstową z znaków specjalnych, takich jak \ $ \%()