2010-02-23 15 views
10

İnsanlar bu soruyu sormaya devam ediyor ve ben de aynı cevabı perlfaq5 ile yanıtlamaya devam ediyorum. Şimdi Stackoverflow üzerinde gösterebileceğimiz bir şey.Dosyadaki bir satırı nasıl değiştirebilirim, silebilir veya ekleyebilirim veya Perl'deki bir dosyanın başına ekleyebilir miyim?

+0

Buradaki "perlfaqN" ifadesinin amacı nedir? "Perfaq5" için bir bağlantı veremez misiniz? Http://perldoc.perl.org/perlfaq5.html#How-do-I-change%2c-delete%2c-or-insert-a-line-in- a-file% 2c-veya-başında-so-a-file% 3f askerleri için? – codeholic

+2

Her zaman bağlantılardan nefret ederim. Web siteleri bayat git, URL'ler değişiyor, vb. Stackoverflow'un her zaman sahip olduğu bilgileri yakalaması gerektiğini düşünüyorum. Unutmayın, bu, cevabın şu anda olduğu gibi üç yıl içinde iyi olması gerektiği uzun vadeli bir projedir. Bir bağlantı bunu garanti etmez. Kaybolana kadar www.perldoc.com'un dokümanlar için tercih edilen site olduğunu hatırlayın. Bu herhangi bir siteye olabilir. –

+0

Ayrıca, tüm perlfaq'ı içe aktarma hakkında sorduğum meta parçacığına bakın: http://meta.stackexchange.com/questions/24244/can-we-import-the-perlfaq-into-stackoverflow –

cevap

13
perlfaq5 itibaren

:

bir metin dosyasından bir satır, ekleme, değiştirme veya silme temel fikri, daha sonra değişikliği yapmadan okuma, okuma ve değişiklik yapmak istediğiniz noktaya dosyayı yazdırmadan içerir ve dosyanın geri kalanını yazdırmak. Perl, Tie::File gibi modüllerin bunu yapabilmesine rağmen hatlara rastgele erişim sağlamaz (özellikle kayıt girişi ayırıcı, $/, değiştirilebilir). , Eklemek gerekir parçalar eklemek, o temel formda şu

open my $in, '<', $file  or die "Can't read old file: $!"; 
open my $out, '>', "$file.new" or die "Can't write new file: $!"; 

while(<$in>) 
    { 
    print $out $_; 
    } 

close $out; 

: Bu görevleri yapmak

Bir Perl programı dosyayı kapatırken, bir dosya açılırken kendi çizgilerini baskı temel halini alır satırları değiştirin veya silin.

Satırları en baştan başlatmak için, mevcut satırları yazdıran döngüye girmeden önce bu satırları yazdırın.

open my $in, '<', $file  or die "Can't read old file: $!"; 
open my $out, '>', "$file.new" or die "Can't write new file: $!"; 

print $out "# Add this line to the top\n"; # <--- HERE'S THE MAGIC 

while(<$in>) 
    { 
    print $out $_; 
    } 

close $out; 

, mevcut hatları değiştirmek while döngü içinde hatları değiştirmek için kod yerleştirin. Bu durumda, kod "perl" nin tüm indirgenmiş sürümlerini bulur ve bunları genişletir. Her satırda gerçekleşir, bu yüzden her satırda bunu yapacağınızdan emin olun!
open my $in, '<', $file  or die "Can't read old file: $!"; 
open my $out, '>', "$file.new" or die "Can't write new file: $!"; 

print $out "# Add this line to the top\n"; 

while(<$in>) 
    { 
    s/\b(perl)\b/Perl/g; 
    print $out $_; 
    } 

close $out; 

yalnızca belirli bir hat değiştirmek için, giriş hattı sayısı, $. yararlıdır. İlk olarak, değiştirmek istediğinize kadar olan çizgileri okuyun ve yazdırın. Ardından, değiştirmek, değiştirmek ve yazdırmak istediğiniz tek satırı okuyun. Bundan sonra satırların geri kalanını okuyun ve bunları yazdırın:

while(<$in>) # print the lines before the change 
    { 
    print $out $_; 
    last if $. == 4; # line number before change 
    } 

my $line = <$in>; 
$line =~ s/\b(perl)\b/Perl/g; 
print $out $line; 

while(<$in>) # print the rest of the lines 
    { 
    print $out $_; 
    } 

Satırları atlamak için döngü kontrollerini kullanın. Bu örnekte next, yorum satırlarını atlar ve last, __END__ veya __DATA__ ile karşılaştığında tüm işlemeyi durdurur.

while(<$in>) 
    { 
    next if /^\s+#/;    # skip comment lines 
    last if /^__(END|DATA)__$/; # stop at end of code marker 
    print $out $_; 
    } 

çıktıda görünmesini istemediğiniz satırları atlamak için next kullanarak belirli bir çizgiyi silmek için benzer şeyler yapın. senin kadar uzun

while(<$in>) 
    { 
    next unless $. % 5; 
    print $out $_; 
    } 

bazı garip nedenle, gerçekten bütün dosyasına bakın seferde ziyade çizgi-by-line işlem istiyorum varsa, (bunu höpürdet diyorum: Bu örnek her beşinci satır atlıyor bellekteki her şeyi sığabilecek):! böyle File::Slurp ve Tie::File olarak

open my $in, '<', $file  or die "Can't read old file: $!" 
open my $out, '>', "$file.new" or die "Can't write new file: $!"; 

my @lines = do { local $/; <$in> }; # slurp! 

    # do your magic here 

print $out @lines; 

Modüller da uyacaktır yardımcı olabilir. Bununla birlikte, tüm dosyayı bir defada okumaktan kaçının. Perl, işlem bitene kadar bu belleği işletim sistemine geri vermez.

Ayrıca, yerinde bir dosyayı değiştirmek için Perl one-liner'ı da kullanabilirsiniz. Aşağıdakiler, inFile.txt numaralı telefondan 'Barbar' olan tüm 'Fred'leri değiştirerek, dosyanın yeni içeriğin üzerine yazılmasını sağlar.-p anahtarıyla Perl, -e ile belirttiğiniz kod etrafına while döngüsünü sarar ve yerinde düzenleme özelliğini etkinleştirmek için -i döner. Geçerli hat $_'dadır. -p ile Perl, döngü sonunda $_ değerini otomatik olarak yazdırır. Daha fazla ayrıntı için bkz. perlrun.

perl -pi -e 's/Fred/Barney/' inFile.txt 

, inFile.txt yedeğini bir dosyayı -i eklemek için uzantıyı vermek için:

perl -pi.bak -e 's/Fred/Barney/' inFile.txt 

sadece beşinci çizgisini değiştirmek için, daha sonra, $., giriş hattı numarasını kontrol test ekleyebilir Test geçtiğinde sadece işlemi gerçekleştirmek: (! veya çizgiler)

perl -pi -e 's/Fred/Barney/ if $. == 5' inFile.txt 

bir çizgi ekleyebilir, belirli bir satırdan önce satırları eklemek için önce Perl $_ yazdırır:

perl -pi -e 'print "Put before first line\n" if $. == 1' inFile.txt 

zaten birinden sonra bir satır eklemek için:

perl -pi -e 'print "Put before third line\n" if $. == 3' inFile.txt 

Hatta döngünün sonunda mevcut hat baskılar beri, bir dosyanın başlangıcına satırı ekleyebilirsiniz Dosyada, -n anahtarını kullanın. Döngünün sonunda $_ yazmaması dışında -p gibidir, bu yüzden bunu kendiniz yapmanız gerekir. Bu durumda, önce $_ yazıp, ardından eklemek istediğiniz çizgiyi yazdırın.

perl -ni -e 'print; print "Put after fifth line\n" if $. == 5' inFile.txt 

Satırları silmek için yalnızca istediğinizleri yazdırın.

perl -ni -e 'print unless /d/' inFile.txt 

    ... or ... 

perl -pi -e 'next unless /d/' inFile.txt 
+0

Sadece merak ediyorum, ne zaman biz 'perl yazarken çalışmıyor? pasta ... '? – Zaid

+0

-pie işe yaramaz çünkü -i bir argüman bekler ve 'e' nin kendisine ait olduğunu düşünür. –

İlgili konular