1 package Scalar::Vec::Util;
10 Scalar::Vec::Util - Utility routines for vec strings.
23 XSLoader::load(__PACKAGE__, $VERSION);
26 *SVU_PP = sub () { 1 };
27 *SVU_SIZE = sub () { 1 };
36 use Scalar::Vec::Util qw/vfill vcopy veq/;
39 vfill $s, 0, 100, 1; # Fill with 100 bits 1 starting at 0.
41 vcopy $s, 20, $t, 10, 30; # Copy 30 bits from $s, starting at 20,
42 # to $t, starting at 10.
43 vcopy $t, 10, $t, 20, 30; # Overalapping areas DWIM.
44 if (veq $t, 10, $t, 20, 30) { ... } # Yes, they are equal now.
48 A set of utilities to manipulate bits in vec strings.
49 Highly optimized XS routines are used when available, but straightforward pure perl replacements are also provided for platforms without a C compiler.
51 This module doesn't reimplement bit vectors.
52 It can be used on the very same scalars that C<vec> builds, or actually on any Perl string (C<SVt_PV>).
58 True when pure perl fallbacks are used instead of XS functions.
62 Size in bits of the unit used for moves.
63 The higher this value is, the faster the XS functions are.
64 It's usually C<CHAR_BIT * $Config{alignbytes}>, except on non-little-endian architectures where it currently falls back to C<CHAR_BIT> (e.g. SPARC).
68 =head2 C<vfill $vec, $start, $length, $bit>
70 Starting at C<$start> in C<$vec>, fills C<$length> bits with C<$bit>.
71 Grows C<$vec> if necessary.
76 for (@_) { return 0 unless defined }
81 (undef, my $s, my $l, my $x) = @_;
82 croak "Invalid argument" unless _alldef @_;
85 vec($_[0], $_, 1) = $x for $s .. $s + $l - 1;
88 =head2 C<< vcopy $from => $from_start, $to => $to_start, $length >>
90 Copies C<$length> bits starting at C<$from_start> in C<$from> to C<$to_start> in C<$to>.
91 If C<$from_start + $length> is too long for C<$from>, zeros are copied past C<$length>.
92 Grows C<$to> if necessary.
97 my ($fs, $ts, $l) = @_[1, 3, 4];
98 croak "Invalid argument" unless _alldef @_;
100 my $step = $ts - $fs;
102 vec($_[2], $_ + $step, 1) = vec($_[0], $_, 1) for $fs .. $fs + $l - 1;
103 } else { # There's a risk of overwriting if $_[0] and $_[2] are the same SV.
104 vec($_[2], $_ + $step, 1) = vec($_[0], $_, 1) for reverse $fs .. $fs + $l - 1;
108 =head2 C<< veq $v1 => $v1_start, $v2 => $v2_start, $length >>
110 Returns true if the C<$length> bits starting at C<$v1_start> in C<$v1> and C<$v2_start> in C<$v2> are equal, and false otherwise.
111 If needed, C<$length> is decreased to fit inside C<$v1> and C<$v2> boundaries.
116 my ($s1, $s2, $l) = @_[1, 3, 4];
117 croak "Invalid argument" unless _alldef @_;
120 return 0 if vec($_[0], $s1 + $i, 1) != vec($_[2], $s2 + $i, 1);
128 The functions L</vfill>, L</vcopy> and L</veq> are only exported on request.
129 All of them are exported by the tags C<':funcs'> and C<':all'>.
131 The constants L</SVU_PP> and L</SVU_SIZE> are also only exported on request.
132 They are all exported by the tags C<':consts'> and C<':all'>.
136 use base qw/Exporter/;
140 'funcs' => [ qw/vfill vcopy veq/ ],
141 'consts' => [ qw/SVU_PP SVU_SIZE/ ]
143 our @EXPORT_OK = map { @$_ } values %EXPORT_TAGS;
144 $EXPORT_TAGS{'all'} = [ @EXPORT_OK ];
148 The following timings were obtained by running the C<samples/bench.pl> script.
149 The C<_pp> entries are the pure Perl versions, whereas C<_bv> are L<Bit::Vector> versions.
153 =item This is for perl 5.8.8 on a Core 2 Duo 2.66GHz machine (unit is 64 bits).
155 Filling bits at a given position :
156 Rate vfill_pp vfill_bv vfill
157 vfill_pp 80.3/s -- -100% -100%
158 vfill_bv 1053399/s 1312401% -- -11%
159 vfill 1180792/s 1471129% 12% --
161 Copying bits from a bit vector to a different one :
162 Rate vcopy_pp vcopy_bv vcopy
163 vcopy_pp 112/s -- -100% -100%
164 vcopy_bv 62599/s 55622% -- -89%
165 vcopy 558491/s 497036% 792% --
167 Moving bits in the same bit vector from a given position to a different one :
168 Rate vmove_pp vmove_bv vmove
169 vmove_pp 64.8/s -- -100% -100%
170 vmove_bv 64742/s 99751% -- -88%
171 vmove 547980/s 845043% 746% --
173 Testing bit equality from different positions of different bit vectors :
174 Rate veq_pp veq_bv veq
175 veq_pp 92.7/s -- -100% -100%
176 veq_bv 32777/s 35241% -- -94%
177 veq 505828/s 545300% 1443% --
179 =item This is for perl 5.10.0 on a Pentium 4 3.0GHz (unit is 32 bits).
181 Rate vfill_pp vfill_bv vfill
182 vfill_pp 185/s -- -100% -100%
183 vfill_bv 407979/s 220068% -- -16%
184 vfill 486022/s 262184% 19% --
186 Rate vcopy_pp vcopy_bv vcopy
187 vcopy_pp 61.5/s -- -100% -100%
188 vcopy_bv 32548/s 52853% -- -83%
189 vcopy 187360/s 304724% 476% --
191 Rate vmove_pp vmove_bv vmove
192 vmove_pp 63.1/s -- -100% -100%
193 vmove_bv 32829/s 51933% -- -83%
194 vmove 188572/s 298787% 474% --
196 Rate veq_pp veq_bv veq
197 veq_pp 34.2/s -- -100% -100%
198 veq_bv 17518/s 51190% -- -91%
199 veq 192181/s 562591% 997% --
201 =item This is for perl 5.10.0 on an UltraSPARC-IIi (unit is 8 bits).
203 Rate vfill_pp vfill vfill_bv
204 vfill_pp 4.23/s -- -100% -100%
205 vfill 30039/s 709283% -- -17%
206 vfill_bv 36022/s 850568% 20% --
208 Rate vcopy_pp vcopy_bv vcopy
209 vcopy_pp 2.74/s -- -100% -100%
210 vcopy_bv 8146/s 297694% -- -60%
211 vcopy 20266/s 740740% 149% --
213 Rate vmove_pp vmove_bv vmove
214 vmove_pp 2.66/s -- -100% -100%
215 vmove_bv 8274/s 311196% -- -59%
216 vmove 20287/s 763190% 145% --
218 Rate veq_pp veq_bv veq
219 veq_pp 7.33/s -- -100% -100%
220 veq_bv 2499/s 33978% -- -87%
221 veq 19675/s 268193% 687% --
227 Please report architectures where we can't use the alignment as the move unit.
228 I'll add exceptions for them.
232 L<Carp>, L<Exporter> (core modules since perl 5), L<XSLoader> (since perl 5.006).
236 L<Bit::Vector> gives a complete reimplementation of bit vectors.
240 Vincent Pit, C<< <perl at profvince.com> >>, L<http://www.profvince.com>.
242 You can contact me by mail or on C<irc.perl.org> (vincent).
246 Please report any bugs or feature requests to C<bug-scalar-vec-util at rt.cpan.org>, or through the web interface at L<http://rt.cpan.org/NoAuth/ReportBug.html?Queue=Scalar-Vec-Util>.
247 I will be notified, and then you'll automatically be notified of progress on your bug as I make changes.
251 You can find documentation for this module with the perldoc command.
253 perldoc Scalar::Vec::Util
255 Tests code coverage report is available at L<http://www.profvince.com/perl/cover/Scalar-Vec-Util>.
257 =head1 COPYRIGHT & LICENSE
259 Copyright 2008 Vincent Pit, all rights reserved.
261 This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself.
265 1; # End of Scalar::Vec::Util