Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Perl: adding a string to $_ is producing strange results

Tags:

string

perl

I wrote a super simple script:

 #!/usr/bin/perl -w
 use strict;
 open (F, "<ids.txt") || die "fail: $!\n";
 my @ids = <F>;
 foreach my $string (@ids) {
 chomp($string);
 print "$string\n";
 }
 close F;

This is producing an expected output of all the contents of ids.txt:

hello

world

these

annoying

sourcecode

lines

Now I want to add a file-extension: .txt for every line. This line should do the trick:

 #!/usr/bin/perl -w
 use strict;
 open (F, "<ids.txt") || die "fail: $!\n";
 my @ids = <F>;
 foreach my $string (@ids) {
 chomp($string);
 $string .= ".txt";
 print "$string\n";
 }
 close F;

But the result is as follows:

.txto

.txtd

.txte

.txtying

.txtcecode

Instead of appending ".txt" to my lines, the first 4 letters of my string will be replaced by ".txt" Since I want to check if some files exist, I need the full filename with extension.

I have tried to chop, chomp, to substitute (s/\n//), joins and whatever. But the result is still a replacement instead of an append.

Where is the mistake?

like image 620
Ajin Avatar asked Aug 30 '11 14:08

Ajin


2 Answers

Chomp does not remove BOTH \r and \n if the file has DOS line endings and you are running on Linux/Unix.

What you are seeing is actually the original string, a carriage return, and the extension, which overwrites the first 4 characters on the display.

If the incoming file has DOS/Windows line endings you must remove both:

s/\R+$//
like image 189
Jim Garrison Avatar answered Sep 19 '22 19:09

Jim Garrison


A useful debugging technique when you are not quite sure why your data is getting set to what it is is to dump it with Data::Dumper:

#!/usr/bin/perl -w
use strict;
use Data::Dumper ();
$Data::Dumper::Useqq = 1; # important to be able to actually see differences in whitespace, etc

open (F, "<ids.txt") || die "fail: $!\n";
my @ids = <F>;
foreach my $string (@ids) {
    chomp($string);
    print "$string\n";
    print Data::Dumper::Dumper( { 'string' => $string } );
}
close F;
like image 37
ysth Avatar answered Sep 18 '22 19:09

ysth