File Coverage

blib/lib/Data/BitStream/Code/Delta.pm
Criterion Covered Total %
statement 49 50 98.0
branch 20 24 83.3
condition 3 3 100.0
subroutine 7 7 100.0
pod 2 2 100.0
total 81 86 94.1


line stmt bran cond sub pod time code
1             package Data::BitStream::Code::Delta;
2 28     28   22940 use strict;
  28         65  
  28         1016  
3 28     28   149 use warnings;
  28         54  
  28         2991  
4             BEGIN {
5 28     28   62 $Data::BitStream::Code::Delta::AUTHORITY = 'cpan:DANAJ';
6 28         2460 $Data::BitStream::Code::Delta::VERSION = '0.08';
7             }
8              
9             our $CODEINFO = { package => __PACKAGE__,
10             name => 'Delta',
11             universal => 1,
12             params => 0,
13             encodesub => sub {shift->put_delta(@_)},
14             decodesub => sub {shift->get_delta(@_)}, };
15              
16 28     28   179 use Moo::Role;
  28         78  
  28         211  
17             requires qw(maxbits read write put_gamma get_gamma);
18              
19             # Elias Delta code.
20             #
21             # Store the number of binary bits in Gamma code, then the value in binary
22             # excepting the top bit which is known from the base.
23             #
24             # Large numbers store more efficiently compared to Gamma. Small numbers take
25             # more space.
26              
27             sub put_delta {
28 4311     4311 1 39869 my $self = shift;
29 4311         11988 my $maxbits = $self->maxbits;
30 4311         19975 my $maxval = $self->maxval;
31              
32 4311         8030 foreach my $val (@_) {
33 6987 100 100     30453 $self->error_code('zeroval') unless defined $val and $val >= 0;
34 6985 100       12513 if ($val == $maxval) {
35 6         17 $self->put_gamma($maxbits);
36             } else {
37 6979         8520 my $base = 0;
38 6979         10718 { my $v = $val+1; $base++ while ($v >>= 1); }
  6979         10844  
  6979         84905  
39 6979         28405 $self->put_gamma($base);
40 6979 100       40463 $self->write($base, $val+1) if $base > 0;
41             }
42             }
43 4309         12380 1;
44             }
45              
46             sub get_delta {
47 4450     4450 1 24781 my $self = shift;
48 4450         5504 my $count = shift;
49 4450 100       9171 if (!defined $count) { $count = 1; }
  4336 50       9361  
    0          
50 114         167 elsif ($count < 0) { $count = ~0; } # Get everything
51 0         0 elsif ($count == 0) { return; }
52              
53 4450         5958 my @vals;
54 4450         11499 my $maxbits = $self->maxbits;
55 4450         13660 $self->code_pos_start('Delta');
56 4450         313069 while ($count-- > 0) {
57 7549         21981 $self->code_pos_set;
58 7549         5406434 my $base = $self->get_gamma();
59 7544 100       17289 last unless defined $base;
60 7405 100       22182 if ($base == 0) { push @vals, 0; }
  1012 100       2911  
    100          
61 6         27 elsif ($base == $maxbits) { push @vals, $self->maxval; }
62 1         7 elsif ($base > $maxbits) { $self->error_code('base', $base); }
63             else {
64 6386         18837 my $remainder = $self->read($base);
65 6386 50       14505 $self->error_off_stream unless defined $remainder;
66 6386         21857 push @vals, ((1 << $base) | $remainder)-1;
67             }
68             }
69 4444         12018 $self->code_pos_end;
70 4444 100       179198 wantarray ? @vals : $vals[-1];
71             }
72 28     28   24509 no Moo::Role;
  28         106  
  28         145  
73             1;
74              
75             # ABSTRACT: A Role implementing Elias Delta codes
76              
77             =pod
78              
79             =head1 NAME
80              
81             Data::BitStream::Code::Delta - A Role implementing Elias Delta codes
82              
83             =head1 VERSION
84              
85             version 0.08
86              
87             =head1 DESCRIPTION
88              
89             A role written for L that provides get and set methods for
90             the Elias Delta codes. The role applies to a stream object.
91              
92             =head1 METHODS
93              
94             =head2 Provided Object Methods
95              
96             =over 4
97              
98             =item B< put_delta($value) >
99              
100             =item B< put_delta(@values) >
101              
102             Insert one or more values as Delta codes. Returns 1.
103              
104             =item B< get_delta() >
105              
106             =item B< get_delta($count) >
107              
108             Decode one or more Delta codes from the stream. If count is omitted,
109             one value will be read. If count is negative, values will be read until
110             the end of the stream is reached. In scalar context it returns the last
111             code read; in array context it returns an array of all codes read.
112              
113             =back
114              
115             =head2 Required Methods
116              
117             =over 4
118              
119             =item B< read >
120              
121             =item B< write >
122              
123             =item B< get_gamma >
124              
125             =item B< put_gamma >
126              
127             =item B< maxbits >
128              
129             These methods are required for the role.
130              
131             =back
132              
133             =head1 SEE ALSO
134              
135             =over 4
136              
137             =item Peter Elias, "Universal codeword sets and representations of the integers", IEEE Trans. Information Theory 21(2), pp. 194-203, Mar 1975.
138              
139             =item Peter Fenwick, "Punctured Elias Codes for variable-length coding of the integers", Technical Report 137, Department of Computer Science, University of Auckland, December 1996
140              
141             =back
142              
143             =head1 AUTHORS
144              
145             Dana Jacobsen
146              
147             =head1 COPYRIGHT
148              
149             Copyright 2011 by Dana Jacobsen
150              
151             This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself.
152              
153             =cut