The slurp gets problematic for very large files, of course, so here is a version that uses a fixed buffer. It runs at essentially the same speed - but uses a constant amount of memory instead.
#!/opt/bin/perl
use strict;
use warnings;
use Time::HiRes qw (gettimeofday tv_interval);
my $file = shift;
my $start_time = [gettimeofday];
open(FH,$file) or die("Can't open file: $!\n");
binmode FH;
my $bytes = -s $file;
my $cursor = 0;
my $stride = 4000000;
my $counted_bits = 0;
while (1) {
my $buffer;
my $result = read(FH, $buffer, $stride);
if (0 == $result) {
last;
} elsif (not defined $result) {
warn("Error reading from $file: $!\n");
last;
}
my $bits = unpack "B*", $buffer;
$counted_bits += $bits =~ tr/1/1/;
}
close (FH);
print "Bits: $counted_bits\n";
my $elapsed = tv_interval($start_time);
my $rate = $bytes / $elapsed;
print "Bytes per second: $rate\n";
|