is there something more elegant to convert Dos to unix in subroutine?

A

Andrew

sub toUnixFile() {
my ($file) = @_;
my ($temp_file) = $file . ".tmp";
move($file, $temp_file);
open(in, "<$temp_file");
open(out, ">$file");
while(<in>) {
chomp;
~ s/\r$//;
print out "$_\n";
}
close in;
close out;
unlink $temp_file;
return 0;
}
 
U

Uri Guttman

A> sub toUnixFile() {
A> my ($file) = @_;
A> my ($temp_file) = $file . ".tmp";
A> move($file, $temp_file);
A> open(in, "<$temp_file");
A> open(out, ">$file");
A> while(<in>) {
A> chomp;
A> ~ s/\r$//;
A> print out "$_\n";
A> }
A> close in;
A> close out;
A> unlink $temp_file;
A> return 0;
A> }

perl -I.bak -pe 'tr/\r\n/\n/s'

uri
 
G

Gunnar Hjalmarsson

Andrew said:
[ Subject: is there something more elegant to convert Dos to unix
in subroutine? ]

sub toUnixFile() {
my ($file) = @_;
my ($temp_file) = $file . ".tmp";
move($file, $temp_file);
open(in, "<$temp_file");
open(out, ">$file");
while(<in>) {
chomp;
~ s/\r$//;
print out "$_\n";
}
close in;
close out;
unlink $temp_file;
return 0;
}

Yes. Subroutines that do what they are supposed to do are always more
elegant.

Please post working code, or rephrase your question.
 
A

Ala Qumsieh

Uri said:
perl -I.bak -pe 'tr/\r\n/\n/s'

I'm really confused. I thought your shift keys were permanently broken,
but now I see a -I when you actually mean -i! What is happening to this
world?

FWIW, I like the following:

perl -pi.bak -e 'y/\cM//d' file_name

--Ala
 
T

Tad McClellan

Michele Dondi said:
sub toUnixFile() {
[snip]

FWIW I customarily use

perl -lpi.bak -e '' <files>


Or, if you are playing golf:

perl -lpi.bak -e1 <files>


Or, if you are confident and playing to win:

perl -lpi -e1 <files>
 
M

Michele Dondi

Or, if you are playing golf:

perl -lpi.bak -e1 <files>

Not at all, just lazy, and even if now I *do* remember which
convention is which, I always prefer to have "someone" else do that
for me. Someone who I am confindent that will remember correctly too,
BTW!

And under Win* it's:

perl -lpi.bak -e "" <files>

Incidentally, nice to notice that your golf-like solution wouldn't
require different conventions on the cmd line too!
Or, if you are confident and playing to win:

perl -lpi -e1 <files>

D'Oh! Under Win* it seems that I cannot be confident! ;-)


Michele
 
M

Matija Papec

X-Ftn-To: Uri Guttman

Uri Guttman said:
A> close out;
A> unlink $temp_file;
A> return 0;
A> }

perl -I.bak -pe 'tr/\r\n/\n/s'

tr/\r//d should be more straightforward?
 
U

Uri Guttman

MP> tr/\r//d should be more straightforward?

it could be. better golf score for sure.

uri
 
A

Andrew

Hm, my subroutine is actually working just fine, prove me wrong, it
conversts DOS files to UNIX just fine.
All examples given involve calling perl from code, I don't like it, I
would like a subroutine or function which can be included in my perl
code. I don't like calling perl from perl.
Thanks,


Gunnar Hjalmarsson said:
Andrew said:
[ Subject: is there something more elegant to convert Dos to unix
in subroutine? ]

sub toUnixFile() {
my ($file) = @_;
my ($temp_file) = $file . ".tmp";
move($file, $temp_file);
open(in, "<$temp_file");
open(out, ">$file");
while(<in>) {
chomp;
~ s/\r$//;
print out "$_\n";
}
close in;
close out;
unlink $temp_file;
return 0;
}

Yes. Subroutines that do what they are supposed to do are always more
elegant.

Please post working code, or rephrase your question.
 
P

Paul Lalli

[please post your reply below the quoted material - doing otherwise is
considered rude]

Gunnar Hjalmarsson said:
[ Subject: is there something more elegant to convert Dos to unix
in subroutine? ]

sub toUnixFile() {
my ($file) = @_;
my ($temp_file) = $file . ".tmp";
move($file, $temp_file);
open(in, "<$temp_file");
open(out, ">$file");
while(<in>) {
chomp;
~ s/\r$//;
print out "$_\n";
}
close in;
close out;
unlink $temp_file;
return 0;
}

Yes. Subroutines that do what they are supposed to do are always more
elegant.

Please post working code, or rephrase your question.

Hm, my subroutine is actually working just fine, prove me wrong, it
conversts DOS files to UNIX just fine.

I *think* the bit Gunnar was complaining about is the line right below
chomp. Presumably, your goal with this line is to perform a search and
replace on $_. The bizzare part is the random ~ in front of it. Why is
that there? While not a syntax error, it is a most unusual logic error.
(And indeed, if you enable warnings, you'll see Perl yell at you about
"useless use of one's complement" or similar). The fact that the code
still works is more of a side affect of that line than anything else.

(Gunnar, feel free to point out if there's another bit that I'm missing)
All examples given involve calling perl from code, I don't like it, I
would like a subroutine or function which can be included in my perl
code. I don't like calling perl from perl.
Thanks,

In the future, you should probably specify important details like that at
the beginning. The reason everyone sent you those tiny short programs was
that you never specified this would be a small part of a larger program.

What, out of curiousity, is the cause of your disliking calling a Perl
one-liner from within a larger program?

Paul Lalli
 
A

Ala Qumsieh

Michele Dondi said:
sub toUnixFile() {
[snip]

FWIW I customarily use

perl -lpi.bak -e '' <files>

Correct me if I'm wrong, but this doesn't work on *nix systems since the
auto chomp() will only remove \n characters, leaving \r's intact.

--Ala
 
G

Gunnar Hjalmarsson

[ Please put quoted text *before* your own comments. ]
Gunnar said:
Andrew said:
[ Subject: is there something more elegant to convert Dos to
unix in subroutine? ]

sub toUnixFile() {
my ($file) = @_;
my ($temp_file) = $file . ".tmp";
move($file, $temp_file);
open(in, "<$temp_file");
open(out, ">$file");
while(<in>) {
chomp;
~ s/\r$//;
print out "$_\n";
}
close in;
close out;
unlink $temp_file;
return 0;
}

Yes. Subroutines that do what they are supposed to do are always
more elegant.

Please post working code, or rephrase your question.

Hm, my subroutine is actually working just fine, prove me wrong,

Sure.

#!/usr/bin/perl

sub toUnixFile() {
my ($file) = @_;
}

toUnixFile('/path/to/file');

Resulting error message:
"Too many arguments for main::toUnixFile"

Since your subroutine requires an argument, the code won't even compile.

Are you still claiming that your sub is working just fine? ;-)
All examples given involve calling perl from code, I don't like it,
I would like a subroutine or function which can be included in my
perl code.

Right, and you said so in the subject line. Note that you might have
got more accurate responses if you had repeated your question in the
body of the message.

If the files to be processed aren't too big, you can always slurp them
into a scalar:

sub toUnixFile {
my $file = shift;
local(*FH, $/);
open FH, "+< $file" or die $!;
$_ = <FH>;
tr/\r//d;
seek FH, 0, 0;
truncate FH, 0;
print FH;
}
 
U

Uri Guttman

A> Hm, my subroutine is actually working just fine, prove me wrong, it
A> conversts DOS files to UNIX just fine.

it has several bugs.

A> All examples given involve calling perl from code, I don't like it, I
A> would like a subroutine or function which can be included in my perl
A> code. I don't like calling perl from perl.

huh? what calling perl from code are you talking about? the answers were
all one liners and it is trivial to convert any of them to a sub.

and what if that file already existed?

and what if either of those open calls fails?

what is that naked ~ doing there?

why the return 0? you don't return from anywhere else.

so your sub it not 'actually working just fine'. proving it wrong was
too easy. you just didn't get the answers.

now fix your sub and use the ideas shown and post new code. you have to
do some of the work too.

uri
 
G

Gunnar Hjalmarsson

Paul said:
I *think* the bit Gunnar was complaining about is the line right
below chomp.

(Gunnar, feel free to point out if there's another bit that I'm
missing)

My main "complaint" is the prototype that disallows that arguments are
passed to the sub.
 
A

Anno Siegel

Gunnar Hjalmarsson said:
My main "complaint" is the prototype that disallows that arguments are
passed to the sub.

I wonder if that bug was masked by a gratuitous ampersand in the call

"&toUnixFile( $some_file)"

would work (as far as that goes), even with the empty prototype.

Anno
 
G

Gunnar Hjalmarsson

Anno said:
I wonder if that bug was masked by a gratuitous ampersand in the
call

"&toUnixFile( $some_file)"

would work (as far as that goes), even with the empty prototype.

Hmm.. Didn't think of that possibility.
 
A

Andrew

Thanks for constructive remarks, here is the fixed one, which, again,
works just fine :)

#
# Converts DOS to UNIX file
# if trim is true will trim leading and trailing spaces and remove
empty lines
#
sub toUnixFile {
my ($file, $trim) = @_;
-f $file || die "Can't open \"$file\": $! \n";
my $temp_file = $file . ".tmp.$$.$^T";
move($file, $temp_file);
local *in;
local *out;
open(in, "<$temp_file");
open(out, ">$file");
while(<in>) {
chomp;
s/\r$//;
if ($trim eq "true") {
s/^\s*//;
s/\s*$//;
unless ( -z $_ ) {
print out "$_\n";
}
} else {
print out "$_\n";
}
}
close in;
close out;
unlink $temp_file;
}
 
U

Uri Guttman

A> Thanks for constructive remarks, here is the fixed one, which, again,
A> works just fine :)

and looks ugly too!

A> sub toUnixFile {
A> my ($file, $trim) = @_;
A> -f $file || die "Can't open \"$file\": $! \n";

lose the \ there. use an alternative delimiter

A> my $temp_file = $file . ".tmp.$$.$^T";

use the File::Temp module

A> move($file, $temp_file);
A> local *in;
A> local *out;

gack! use lexical filehandles. and glob handles are upper case by tradition
A> open(in, "<$temp_file");
A> open(out, ">$file");

you check for the file with -f but not here? always check your open
calls for failures

A> while(<in>) {
A> chomp;
A> s/\r$//;

why the chomp AND s///? s/[\r\n]+$// would work anywhere.

A> if ($trim eq "true") {
A> s/^\s*//;
A> s/\s*$//;
A> unless ( -z $_ ) {

huh??!! what do you think -z does? this is perl, not shell.

and if i get your logic (which is coded incorrectly), you want to not
print lines that had only blanks. that means this is not a true dos2unix
program since that is not part of the typical spec for that.

A> print out "$_\n";
A> }
A> } else {
A> print out "$_\n";
A> }

redundant code always bothers me. if you used next you could have that
one print line for both cases.


and you still top post.
A> Hm, my subroutine is actually working just fine, prove me wrong, it
A> conversts DOS files to UNIX just fine.
it still has several bugs

A> All examples given involve calling perl from code, I don't like it, I
A> would like a subroutine or function which can be included in my perl
A> code. I don't like calling perl from perl.

you never answered that question.

your skill levels demonstrate that you don't know when to call perl from
perl. so your saying you don't like it doesn't hold any water.

nevr fixed that bug.

never fixed that bug

and most of the bugs i pointed out are still there. you don't listen
well it seems.

uri
 
M

Michele Dondi

Correct me if I'm wrong, but this doesn't work on *nix systems since the
auto chomp() will only remove \n characters, leaving \r's intact.

[ashamed] Tes, you're right. I was implicitly doing a wrong
assumption. Though, what I do *really* customarily use (and *really*
works!) is

perl -lpi.bak -e "" <files>

in Win* environments on (possibly) *nix-line-terminated text files...


Michele
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,755
Messages
2,569,536
Members
45,011
Latest member
AjaUqq1950

Latest Threads

Top