[英]Perl. Simultaneous match and substitution
我試圖找到特定的模式並在其中進行替換。 並將結果分配給另一個變量。
例如:我有一個帶有文本的變量$ text,我試圖在其中查找諸如“ Date:\\ s + \\ d {4}。\\ d \\ d。\\ d \\ d”之類的模式,用點號代替破折號,然后將結果分配給$ result。
此版本適用:
($result) = $text =~ /Date:\s+(\d{4}\.\d\d\.\d\d)/igs;
$result =~ s/\./-/g;
但是我試圖通過一項手術做到這一點。 就像是:
($result) = $text =~ s/Date:\s+(\d{4})\.(\d\d)\.(\d\d)/$1-$2-$3/igs;
但這給了我結果“ 1”。 因此,問題是:是否可以在一個操作中執行此操作? 還是最好的選擇是這樣做並最小化代碼?
my $result;
$text =~ s/Date:\s+(\d{4})\.(\d\d)\.(\d\d)/ $result= "$1-$2-$3" /ei;
如果移動括號,以便首先將$text
分配給$result
,則可以將替換應用於$result
而不是$text
,這樣就可以去除所有不需要的多余文本,並使用原始文本建設有破折號日期的想法-
而不是點:
(my $result = $text) =~ s/.*Date:\s+(\d{4})\.(\d\d)\.(\d\d).*/$1-$2-$3/igs;
請注意,在字符串的開頭和結尾使用.*
,這將占用所有文本,因此剩下的唯一內容就是日期。 這行代碼實際上是兩個操作合而為一,如下所示:
my $result = $text;
$result =~ s/..../;
另一個版本是使用后腳本for
循環,它將利用$_
別名為list參數這一事實:
tr/./-/ for ((my $result) = $text =~ /Date:\s+([\d.]+)/);
這會將日期分配給$result
,然后將$result
傳遞給for
的參數列表,對其應用音譯。 它會影響實變量$result
因為$_
在循環中具有別名。
另外請注意,我認為這確實是一個學術問題。 我不建議在生產代碼中使用它,並且您的原始版本要好得多且可讀性強。 盡管我將使用音譯而不是替換:
$result =~ tr/./-/;
請嘗試一下($ result = $ text)=〜s / Date:\\ s +(\\ d {4})。(\\ d \\ d)。(\\ d \\ d)/ $ 1- $ 2- $ 3 / igs
您不應該太熱衷於在單個語句中編寫多個操作:它只會破壞代碼的可讀性。 但是我建議你寫這樣的東西。
在原始模式匹配項上使用/s
修飾符沒有意義,因為它僅影響.
元字符,並且您的模式中沒有這些字符。 另外,使用/g
沒有意義,因為您只對單個匹配感興趣。
不要試圖將兩個語句合並為一行,因為if
語句修飾符也將應用於my
聲明,這會產生非常奇怪的效果。
use strict;
use warnings;
use 5.010;
my $text = 'Date: 1994.04.04';
my $result;
$result = $1 =~ tr/./-/r if $text =~ /Date:\s+(\d{4}\.\d\d\.\d\d)/i;
say $text;
say $result;
產量
Date: 1994.04.04
1994-04-04
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.