2011-08-01 16 views
5

Mac 10.6.6'da Perl 5.10.6 kullanıyorum.Dizgemde bir '/' içeriyorsa 's ///' nasıl kullanabilirim?

my $searchAndReplaceCmd = "perl -pi -e 's/\\Q${localTestDir}\\E//g' ${testSuiteFile}"; 
system($searchAndReplaceCmd); 

ama sorun yukarıda değişken $localTestDir olan ("/") dizin ayırıcılar içerir ve bu vida yukarı düzenli ifade ...

: Ben denedim bu yüzden basit bir arama yürütmek ve bir dosyaya karşı değiştirmek istiyor

Bareword bulduğum yer yakın, -e hat 1 beklenen operatör "s/\ Q/home/selenyum"

yakın -e line 1 beklenen operatör, sözdizimi hatası "\ Canlı" nerede Backslash bulundu -de hat 1 Ben bir arama yapmak ve bir dosya üzerinde yerini almadığını nasıl "s/\ Q/home/selenyum" -e çizgisinde sona değil

Arama deseni 1.

söz konusu değişken içerdiğinde yakın düzenli ifade karakterleri? Teşekkürler.

cevap

2

meselesidir. şeyler yapmanın dolambaçlı bir yol gibi görünüyor ve siz kabuk interpolasyonlu sorunlarla edeceğiz.

\Q ... \E dizginizdeki özel karakterleri geçersiz kılmalı, yani / "sorun" olmamalıdır. perlre Gönderen:

\Q   quote (disable) pattern metacharacters till \E 

İşte bir alternatif (denenmemiş), bütün perl çözümdür. Eğer fazladan belli olmasını isterseniz, s### (bir ayırıcı olarak herhangi bir karakter kullanabilirsiniz) gibi başka bir şeye / sınırlayıcı alışverişinde.

use strict; 
use warnings; 
use File::Copy; 

open my $fh, '<', $testSuiteFile or die $!; 
open my $out, '>', $testSuiteFile . ".bak" or die $!; 

while (<$fh>) { 
    s/\Q${localTestDir}\E//g; 
    print $out $_; 
} 

move($testSuiteFile . ".bak", $testSuiteFile) or die $!; 

Veya kullanmak Tie::File

use strict; 
use warnings; 
use Tie::File; 

tie, my @file, 'Tie::File', $testSuiteFile or die $!; 

for (@file) { 
     s/\Q${localTestDir}\E//g; 
} 
untie @file; 
+0

Tüm Perl çözümlerine bayıldım! – Dave

+1

@Dave Perl çok sevilebilir;) sistem çağrıları kullanışlı olabilir, ancak saf perl IMO kullanmak neredeyse her zaman tercih edilir. – TLP

6

, / ile başlıyor gibi görünüyor. / dışında bir regex sınırlayıcı değiştirerek

Çözüm: perldoc perlrequick itibaren

my $searchAndReplaceCmd = "perl -pi -e 's!\\Q${localTestDir}\\E!!g' ${testSuiteFile}"; 

:

$x = "A 39% hit rate"; 
$x =~ s!(\d+)%!$1/100!e;  # $x contains "A 0.39 hit rate" 

son örneği s/// başka sınırlayıcılar gibi kullanabilirsiniz gösteriyor s!!! veolarakve hatta s{}//. Tek tırnak s''' kullanılırsa, o zaman regex ve yedek tek tırnaklı dize olarak kabul edilir.

+1

ama ne olursa '$ localTestDir' bir' içeriyor! '? – ErikR

+0

user5402 @ 'ın ###', 'nin ,,,', 'ın <><>', 'ın {} // ', vb – Zaid

+0

: kullanın perlrequick'' örneğin başka bir sınırlayıcı bak Benim amacım, "localTestDir" in ne olduğunu bilmeden önce bir sınırlayıcı seçmeniz gerektiğidir. Ne '$ localTestDir' tüm ASCII karakterlerini içeriyorsa? Şimdi napıyorsun? user5402 @ – ErikR

1

Sınırlayıcıların değiştirilmesi yararlıdır, ancak daha genel olarak, herhangi bir normal ifade karakterinin önüne özel olmayan bir ters eğik çizgi koyabilirsiniz.

Yani s/\/abc/\/xyz/çok okunabilir olmamasına rağmen, çalışacaktır. Eğer perl içinde, kabuk yoluyla, bir arama yapmak ve Perl içerisinden yerine neden

+1

aka 'leaning-toothpick-syndrome' :) – Zaid

0

sorun $localTestDir ikamesi çok yakında oluyor olmasıdır. Bu da kabuk tarafından yorumlanır olmaktan $suiteTestFile içeriğini koruduğunu

system('perl', '-pi', 
     '-e', 'BEGIN { $dir = shift(@ARGV) };', 
     '-e', 's/\\Q$dir\\E//g', 
     $localTestDir, 
     $suiteTestFile 
); 

Not: Burada

Eğer yeniden sınırlayıcı için / kullanmak sağlayan bir yaklaşımdır.

İlgili konular