At 15:15 +0000 22/12/05, James Harvard wrote:
I'm trying to detect a file's line endings (\r\n for DOS, \r for Mac and \n for Unix as I'm sure y'all know).

Is there any easy way to do this?

use Fcntl;

sub get_line_ending_for_file {
  my( $file ) = @_;

  my $fh;
  sysopen( $fh, $file, O_RDONLY );
  sysread( $fh, $_, 33000 );
  close( $fh );

  return /(\015\012|\015|\012)/ ? $1 : "\n";
}

Adjust the 33000 number to whatever maximum line size you think might be appropriate.

Enjoy,
   Peter.


I don't want to slurp the whole file, because it could be 14 MB or more, so I wanted to read in chunks until I got to a line break. However I can see a potential problem ending a chunk half way through a DOS \r\n, so then you just get \r which makes it look like a Mac formatted file.

Anyway, I started to roll my own code for it, and because I'm new to Perl I hoped that one of you kind souls would have a quick look (below) to check that I've got the right idea of how to do this sort of thing with Perl. (It seems to work with my tests, but that doesn't necessarily mean that it is a robust method!)

Also, I assume that one can pass a file handle to a sub-routine?
$/ = &sniff_line_endings(<INFILE>) ;

Many thanks,
James Harvard

open (INFILE,$filename) or die "Couldn't open" ;
$/ = \50 ;
my $taste = '' ;
my $lb = undef ;
until ($lb) {
        $taste .= <INFILE> ;
        if ($taste =~ /\r\n/) {
                $lb = "\r\n" ;
                # DOS line endings
        } elsif ($taste =~ /\r(?!$)/) {
                $lb = "\r" ;
                # Mac line endings
        } elsif ($taste =~ /\n/) {
                $lb = "\n" ;
                # Unix line endings
        }
}
$/ = $lb ;
seek INFILE, 0, 0 ; # reset the file read pointer
# do while(<INFILE>) stuff


--
<http://www.stairways.com/>  <http://download.stairways.com/>

Reply via email to