2013-12-13 212 views
4

我想在Perl更換IP-地址與隨機數:區分正則表達式中的多個正則表達式?

while (my $line = <file>){ 
    $line =~ $regex{'ipadress'}; 

    my $rand0 = int(rand(256)); 
    my $rand1 = int(rand(256)); 
    my $rand2 = int(rand(256)); 
    my $rand3 = int(rand(256)); 

    $& = "$rand0.$rand1.$rand2.$rand3\n";` 
} 

的問題是,在某些情況下,有多個IP的地址在同一行。
如何避免他們都得到相同的隨機數字?

回答

4

那麼一開始$&是隻讀的,你不能分配給它這樣的修改目標字符串。

我也不確定你的散列鍵是否真的是ipadress(有一個d),但我相信如果沒有的話你可以修復它。

我會寫這樣的東西。替代運算符上的/e修飾符會導致替換字符串爲執行以確定替換匹配的內容。 join語句生成從0到255的四個字節值,並將它們用點連接以形成一個隨機地址。

while (my $line = <$fh>) { 
    $line =~ s{$regex{ipadress}}{ 
    join '.', map int(rand(256)), 0..3 
    }eg; 
    print $line; 
} 
+1

在那裏我想*替換爲'$&'賦值*是我錯過的一些新功能。 ;-) – Qtax

+0

@Qtax:不,我恐怕不是。有關使用'$&'*的警告依然存在。你可以使用'substr'作爲一個左值,而賦值給'$&'與分配給substr($ line,$ - [0],$ + [0] - $ - [0])是一樣的。 )'。 – Borodin

4

這可能會有所幫助:

sub rip { return join(".", map { int(rand(256)) } (1..4)) } 

open my $f, '<', 'input' or die($!); 
while (my $line = <$f>){ 
    $line =~ s/$regex{'ipadress'}/rip()/eg; 
} 
close($f); 
+0

你必須調用「perl -i」才能夠內聯編輯,不是嗎? – hcrudolph

1

這些答案是確保爲每個IP地址選擇新隨機數的好方法。但海報的主要問題是,「如何避免它們都得到相同的隨機數?」並且我不清楚他們是否意味着「爲每個IP地址獲得四個隨機數字」或「保證沒有兩個隨機選擇的IP地址是相同的。」

如果是後者:讓從rand(256)四次調用了同樣的結果連續兩次的概率是一個在2 ,這似乎根本不值得擔心,但如果你需要保證他們不同的是,你可以保留你已經選擇的地址的哈希值,並在每次生成新地址時更新它。從@ perreal的解決方案偷:

sub rip { 
    my $picked_addrs = shift; 
    my $new_addr; 
    do { 
     $new_addr = join(".", map { int(rand(256)) } (1..4)); 
    } while defined($picked_addrs->{$new_addr}); 
    $picked_addrs->{$new_addr} = 1; 
    return $new_addr; 
} 

open my $f, '<', 'input' or die($!); 
while (my $line = <$f>){ 
    my %picked_addrs; 
    $line =~ s/$regex{'ipadress'}/rip(\%picked_addrs)/eg; 
} 
close($f); 

如果你想確保你永遠不會選擇同一地址的文件中的任何地方兩次,只是聲明%picked_addrswhile外循環,所以它不會重置每行:

open my $f, '<', 'input' or die($!); 
my %picked_addrs; 
while (my $line = <$f>){ 
    $line =~ s/$regex{'ipadress'}/rip(\%picked_addrs)/eg; 
} 
close($f); 
相關問題