| Bit-Vector documentation | view source | Contained in the Bit-Vector distribution. |
Bit::Vector - Efficient bit vector, set of integers and "big int" math library
See Bit::Vector::Overload(3).
See Bit::Vector::String(3).
Version
$version = Bit::Vector->Version();
Word_Bits
$bits = Bit::Vector->Word_Bits(); # bits in a machine word
Long_Bits
$bits = Bit::Vector->Long_Bits(); # bits in an unsigned long
new
$vector = Bit::Vector->new($bits); # bit vector constructor
@veclist = Bit::Vector->new($bits,$count);
new_Hex
$vector = Bit::Vector->new_Hex($bits,$string);
new_Bin
$vector = Bit::Vector->new_Bin($bits,$string);
new_Dec
$vector = Bit::Vector->new_Dec($bits,$string);
new_Enum
$vector = Bit::Vector->new_Enum($bits,$string);
Concat_List
$vector = Bit::Vector->Concat_List(@vectors);
new
$vec2 = $vec1->new($bits); # alternative call of constructor
@veclist = $vec->new($bits,$count);
Shadow
$vec2 = $vec1->Shadow(); # new vector, same size but empty
Clone
$vec2 = $vec1->Clone(); # new vector, exact duplicate
Concat
$vector = $vec1->Concat($vec2);
Concat_List
$vector = $vec1->Concat_List($vec2,$vec3,...);
Size
$bits = $vector->Size();
Resize
$vector->Resize($bits);
$vector->Resize($vector->Size()+5);
$vector->Resize($vector->Size()-5);
Copy
$vec2->Copy($vec1);
Empty
$vector->Empty();
Fill
$vector->Fill();
Flip
$vector->Flip();
Primes
$vector->Primes(); # Sieve of Erathostenes
Reverse
$vec2->Reverse($vec1);
Interval_Empty
$vector->Interval_Empty($min,$max);
Interval_Fill
$vector->Interval_Fill($min,$max);
Interval_Flip
$vector->Interval_Flip($min,$max);
Interval_Reverse
$vector->Interval_Reverse($min,$max);
Interval_Scan_inc
if (($min,$max) = $vector->Interval_Scan_inc($start))
Interval_Scan_dec
if (($min,$max) = $vector->Interval_Scan_dec($start))
Interval_Copy
$vec2->Interval_Copy($vec1,$offset2,$offset1,$length);
Interval_Substitute
$vec2->Interval_Substitute($vec1,$off2,$len2,$off1,$len1);
is_empty
if ($vector->is_empty())
is_full
if ($vector->is_full())
equal
if ($vec1->equal($vec2))
Lexicompare (unsigned)
if ($vec1->Lexicompare($vec2) == 0)
if ($vec1->Lexicompare($vec2) != 0)
if ($vec1->Lexicompare($vec2) < 0)
if ($vec1->Lexicompare($vec2) <= 0)
if ($vec1->Lexicompare($vec2) > 0)
if ($vec1->Lexicompare($vec2) >= 0)
Compare (signed)
if ($vec1->Compare($vec2) == 0)
if ($vec1->Compare($vec2) != 0)
if ($vec1->Compare($vec2) < 0)
if ($vec1->Compare($vec2) <= 0)
if ($vec1->Compare($vec2) > 0)
if ($vec1->Compare($vec2) >= 0)
to_Hex
$string = $vector->to_Hex();
from_Hex
$vector->from_Hex($string);
to_Bin
$string = $vector->to_Bin();
from_Bin
$vector->from_Bin($string);
to_Dec
$string = $vector->to_Dec();
from_Dec
$vector->from_Dec($string);
to_Enum
$string = $vector->to_Enum(); # e.g. "2,3,5-7,11,13-19"
from_Enum
$vector->from_Enum($string);
Bit_Off
$vector->Bit_Off($index);
Bit_On
$vector->Bit_On($index);
bit_flip
$bit = $vector->bit_flip($index);
bit_test
contains
$bit = $vector->bit_test($index);
$bit = $vector->contains($index);
if ($vector->bit_test($index))
if ($vector->contains($index))
Bit_Copy
$vector->Bit_Copy($index,$bit);
LSB (least significant bit)
$vector->LSB($bit);
MSB (most significant bit)
$vector->MSB($bit);
lsb (least significant bit)
$bit = $vector->lsb();
msb (most significant bit)
$bit = $vector->msb();
rotate_left
$carry = $vector->rotate_left();
rotate_right
$carry = $vector->rotate_right();
shift_left
$carry = $vector->shift_left($carry);
shift_right
$carry = $vector->shift_right($carry);
Move_Left
$vector->Move_Left($bits); # shift left "$bits" positions
Move_Right
$vector->Move_Right($bits); # shift right "$bits" positions
Insert
$vector->Insert($offset,$bits);
Delete
$vector->Delete($offset,$bits);
increment
$carry = $vector->increment();
decrement
$carry = $vector->decrement();
inc
$overflow = $vec2->inc($vec1);
dec
$overflow = $vec2->dec($vec1);
add
$carry = $vec3->add($vec1,$vec2,$carry);
($carry,$overflow) = $vec3->add($vec1,$vec2,$carry);
subtract
$carry = $vec3->subtract($vec1,$vec2,$carry);
($carry,$overflow) = $vec3->subtract($vec1,$vec2,$carry);
Neg
Negate
$vec2->Neg($vec1);
$vec2->Negate($vec1);
Abs
Absolute
$vec2->Abs($vec1);
$vec2->Absolute($vec1);
Sign
if ($vector->Sign() == 0)
if ($vector->Sign() != 0)
if ($vector->Sign() < 0)
if ($vector->Sign() <= 0)
if ($vector->Sign() > 0)
if ($vector->Sign() >= 0)
Multiply
$vec3->Multiply($vec1,$vec2);
Divide
$quot->Divide($vec1,$vec2,$rest);
GCD (Greatest Common Divisor)
$vecgcd->GCD($veca,$vecb);
$vecgcd->GCD($vecx,$vecy,$veca,$vecb);
Power
$vec3->Power($vec1,$vec2);
Block_Store
$vector->Block_Store($buffer);
Block_Read
$buffer = $vector->Block_Read();
Word_Size
$size = $vector->Word_Size(); # number of words in "$vector"
Word_Store
$vector->Word_Store($offset,$word);
Word_Read
$word = $vector->Word_Read($offset);
Word_List_Store
$vector->Word_List_Store(@words);
Word_List_Read
@words = $vector->Word_List_Read();
Word_Insert
$vector->Word_Insert($offset,$count);
Word_Delete
$vector->Word_Delete($offset,$count);
Chunk_Store
$vector->Chunk_Store($chunksize,$offset,$chunk);
Chunk_Read
$chunk = $vector->Chunk_Read($chunksize,$offset);
Chunk_List_Store
$vector->Chunk_List_Store($chunksize,@chunks);
Chunk_List_Read
@chunks = $vector->Chunk_List_Read($chunksize);
Index_List_Remove
$vector->Index_List_Remove(@indices);
Index_List_Store
$vector->Index_List_Store(@indices);
Index_List_Read
@indices = $vector->Index_List_Read();
Or
Union
$vec3->Or($vec1,$vec2);
$set3->Union($set1,$set2);
And
Intersection
$vec3->And($vec1,$vec2);
$set3->Intersection($set1,$set2);
AndNot
Difference
$vec3->AndNot($vec1,$vec2);
$set3->Difference($set1,$set2);
Xor
ExclusiveOr
$vec3->Xor($vec1,$vec2);
$set3->ExclusiveOr($set1,$set2);
Not
Complement
$vec2->Not($vec1);
$set2->Complement($set1);
subset
if ($set1->subset($set2)) # true if $set1 is subset of $set2
Norm
$norm = $set->Norm();
$norm = $set->Norm2();
$norm = $set->Norm3();
Min
$min = $set->Min();
Max
$max = $set->Max();
Multiplication
$matrix3->Multiplication($rows3,$cols3,
$matrix1,$rows1,$cols1,
$matrix2,$rows2,$cols2);
Product
$matrix3->Product($rows3,$cols3,
$matrix1,$rows1,$cols1,
$matrix2,$rows2,$cols2);
Closure
$matrix->Closure($rows,$cols);
Transpose
$matrix2->Transpose($rows2,$cols2,$matrix1,$rows1,$cols1);
new()", of course.) 0") for
"false" and a numeric one ("1") for "true". Block_Read()" and "Block_Store()" (the only time in this
module where this could make any difference), however, a conversion to and
from "least order byte first" order is automatically supplied.
Block_Read()" provides and what "Block_Store()"
expects is always in "least order byte first" order, regardless of the order
in which words are stored internally on your machine.
Block_Read()"
can always be read in correctly with "Block_Store()" on a different machine.
Word_" are
MACHINE-DEPENDENT!
Chunk_". Chunk_"
range from "1" to "Bit::Vector->Long_Bits();" bits ("0" is NOT
allowed!).
Concat()", "Concat_List()",
"Copy()", "Interval_Copy()" and "Interval_Substitute()", where no
conditions at all are imposed on the size of their bit vector arguments.
Multiply()", all three bit vector arguments must in principle
obey the rule of matching sizes, but the bit vector in which the result of
the multiplication is to be stored may be larger than the two bit vector
arguments containing the factors for the multiplication.
Power()", the bit vector for the result must be the same
size or greater than the base of the exponentiation term. The exponent
can be any size. 0" and
"$vector->Size()-1", or a fatal "index out of range"
error will occur. See Bit::Vector::Overload(3).
See Bit::Vector::String(3).
$version = Bit::Vector->Version();
$bits = Bit::Vector->Word_Bits();
$bits = Bit::Vector->Long_Bits();
$vector = Bit::Vector->new($bits);
$bits"
bits (with indices ranging from "0" to "$bits-1").
$bits = 0) are permitted now.
$bits" it will be
interpreted as a large positive number due to its internal two's
complement binary representation.
@veclist = Bit::Vector->new($bits,$count);
$count".
$count" bit vectors which all have the
same number of bits "$bits" (and which are all initialized, i.e.,
all bits are cleared).
$count" is zero, an empty list is returned.
$bits" is zero, a list of null-sized bit vectors is returned.
$count" it will
be interpreted as a large positive number due to its internal two's
complement binary representation.
$vector = Bit::Vector->new_Hex($bits,$string);
$bits" bits) and to initialize it
all in one go.
new()" and then passes the given string to the method "from_Hex()".
new()" immediately above for
possible causes) or if the given string cannot be converted successfully
(see the description of the method "from_Hex()" further below for
details).
$vector = Bit::Vector->new_Bin($bits,$string);
$bits" bits) and to initialize it
all in one go.
new()" and then passes the given string to the method "from_Bin()".
new()" above for possible causes)
or if the given string cannot be converted successfully (see the
description of the method "from_Bin()" further below for details).
$vector = Bit::Vector->new_Dec($bits,$string);
$bits" bits) and to initialize it
all in one go.
new()" and then passes the given string to the method "from_Dec()".
new()" does not initialize
the memory area occupied by the new bit vector with zeros (which is
pointless in this case, because "from_Dec()" will do it anyway),
and second because it saves you from the associated overhead of one
additional method invocation.
new()" above for possible causes)
or if the given string cannot be converted successfully (see the
description of the method "from_Dec()" further below for details).
$vector = Bit::Vector->new_Enum($bits,$string);
$bits" bits) and to initialize it
all in one go.
new()" and then passes the given string to the method "from_Enum()".
new()" does not initialize
the memory area occupied by the new bit vector with zeros (which is
pointless in this case, because "from_Enum()" will do it anyway),
and second because it saves you from the associated overhead of one
additional method invocation.
new()" above for possible causes)
or if the given string cannot be converted successfully (see the
description of the method "from_Enum()" further below for details).
$vector = Bit::Vector->Concat_List(@vectors);
$vec2 = $vec1->new($bits);
@veclist = $vec->new($bits);
$vec1" (or "$vec") is not affected by this, it just serves
as an anchor for the method invocation mechanism.
Bit::Vector->" instead of
"$vec1->" (and even though laziness is - allegedly - a programmer's
virtue :-)), maybe it is better not to use this feature if you don't
want to get booed at. ;-) $vec2 = $vec1->Shadow();
$vec2" of the SAME SIZE as "$vec1"
but which is EMPTY.
$vec2 = $vec1->Clone();
$vec2" of the SAME SIZE as "$vec1"
which is an EXACT COPY of "$vec1". $vector = $vec1->Concat($vec2);
$vec1" and "$vec2".
$vec1" become the MOST significant part
of the resulting bit vector, and "$vec2" the LEAST significant part.
$vector = $vec1->Concat_List($vec2,$vec3,...);
$vec1 . $vec2 . $vec3 . ...
$bits = $vector->Size();
Resize()"d to). $vector->Resize($bits);
$bits" it will
be interpreted as a large positive number due to its internal two's
complement binary representation.
$vec2->Copy($vec1);
$vec1" to bit vector "$vec2".
$vec2" get overwritten, i.e.,
are lost.
$vector->Empty();
$vector->Fill();
$vector->Flip();
$vector->Primes();
$vec2->Reverse($vec1);
$vec1" to
the vector "$vec2", thereby reversing the order
of all bits.
$vec1" becomes the
most significant bit of "$vec2", whereas the most
significant bit of "$vec1" becomes the least
significant bit of "$vec2", and so forth
for all bits in between.
$vec1" and "$vec2" may be identical.
$vec1->Interval_Reverse(0,$vec1->Size()-1);.) $vector->Interval_Empty($min,$max);
[$min..$max] (including both limits)
in the given vector.
$min" and "$max" may have the same value; this is the same
as clearing a single bit with "Bit_Off()" (but less efficient).
$vector->Interval_Empty(0,$vector->Size()-1);
is the same as $vector->Empty(); (but less efficient). $vector->Interval_Fill($min,$max);
[$min..$max] (including both limits)
in the given vector.
$min" and "$max" may have the same value; this is the same
as setting a single bit with "Bit_On()" (but less efficient).
$vector->Interval_Fill(0,$vector->Size()-1);
is the same as $vector->Fill(); (but less efficient). $vector->Interval_Flip($min,$max);
[$min..$max]
(including both limits) in the given vector.
$min" and "$max" may have the same value; this is the same
as flipping a single bit with "bit_flip()" (but less efficient).
$vector->Interval_Flip(0,$vector->Size()-1);
is the same as $vector->Flip(); and
$vector->Complement($vector);
(but less efficient). $vector->Interval_Reverse($min,$max);
[$min..$max]
(including both limits) in the given vector.
$min" and "$max" swap places, and so forth
for all bits in between.
$min" and "$max" may have the same value; this has no
effect whatsoever, though. if (($min,$max) = $vector->Interval_Scan_inc($start))
$start" (i.e., "$min" >= "$start")
and proceeds upwards (i.e., "$max" >= "$min"), thus repeatedly
increments the search pointer "$start" (internally).
$start" is NOT altered. I.e., you have to set it to the desired
value yourself prior to each call to "Interval_Scan_inc()" (see also
the example given below).
$min"
and "$max" are the same.
$start = 0;
while (($start < $vector->Size()) &&
(($min,$max) = $vector->Interval_Scan_inc($start)))
{
$start = $max + 2;
# do something with $min and $max
}
if (($min,$max) = $vector->Interval_Scan_dec($start))
$start" (i.e., "$max" <= "$start")
and proceeds downwards (i.e., "$min" <= "$max"), thus repeatedly
decrements the search pointer "$start" (internally).
$start" is NOT altered. I.e., you have to set it to the desired
value yourself prior to each call to "Interval_Scan_dec()" (see also
the example given below).
$min"
and "$max" are the same.
$start = $vector->Size() - 1;
while (($start >= 0) &&
(($min,$max) = $vector->Interval_Scan_dec($start)))
{
$start = $min - 2;
# do something with $min and $max
}
$vec2->Interval_Copy($vec1,$offset2,$offset1,$length);
$offset1" you choose, with a length of "$length"
bits) from a given "source" bit vector "$vec1" to another position
"$offset2" in a "target" bit vector "$vec2".
$vec1" and "$vec2" do NOT
need to have the same (matching) size!
$offset1 + $length" and
"$offset2 + $length" (or both) may exceed the actual length
of its corresponding bit vector ("$vec1->Size()" and
"$vec2->Size()", respectively).
$length" parameter is automatically reduced
internally so that both terms above are bounded by the number of bits
of their corresponding bit vector.
$length" parameter, supplied by you
in the initial method call, may also be zero right from the start!)
$offset1" and "$offset2" must lie within the
range "0" and, respectively, "$vec1->Size()-1" or
"$vec2->Size()-1", or a fatal "offset out of range" error
will occur.
$vec1" and "$vec2" may be identical, i.e.,
you may copy a stretch of contiguous bits from one part of a given
bit vector to another part.
$vec2->Interval_Substitute($vec1,$off2,$len2,$off1,$len1);
$off1" and a length of "$len1"
bits) from a given "source" bit vector "$vec1" for a different
stretch of contiguous bits (defined by a position (offset) "$off2"
and a length of "$len2" bits) in another, "target" bit vector
"$vec2".
$vec1" and "$vec2" do NOT
need to have the same (matching) size!
$off1" and "$off2" must lie within the
range "0" and, respectively, "$vec1->Size()" or
"$vec2->Size()", or a fatal "offset out of range" error
will occur.
$vec1->Size()-1" and "$vec2->Size()-1", as they would
be for any other method in this module, but that these offsets may
actually point to one position PAST THE END of the corresponding
bit vector.
$off1 + $len1" exceeds the size
"$vec1->Size()" of bit vector "$vec1" (or if "$off2 + $len2"
exceeds "$vec2->Size()"), the corresponding length ("$len1"
or "$len2", respectively) is automatically reduced internally
so that "$off1 + $len1 <= $vec1->Size()" (and
"$off2 + $len2 <= $vec2->Size()") holds.
$len1" or "$len2") of zero.
$len1 == 0") means that the indicated stretch of bits in
the target bit vector (starting at position "$off2") is to
be replaced by NOTHING, i.e., is to be DELETED.
$len2 == 0") means that NOTHING is replaced, and that the
stretch of bits from the source bit vector is simply INSERTED
into the target bit vector at the indicated position ("$off2").
Interval_Copy()", "Insert()" and "Delete()"), this method
IMPLICITLY and AUTOMATICALLY adapts the length of the resulting
bit vector as needed, as given by
$size = $vec2->Size(); # before
$size += $len1 - $len2; # after
Resize()".)
$len2 == 0") a stretch of bits into
or deleting ("$len1 == 0") an interval of bits from the target bit
vector will automatically increase or decrease, respectively, the size
of the target bit vector accordingly.
$vec1" and "$vec2" may be identical, i.e.,
in-place processing is possible.
if ($vector->is_empty())
0").
1") if the bit vector is empty and "false" ("0")
otherwise.
1") if the given bit
vector has a length of zero, i.e., if it contains no bits at all. if ($vector->is_full())
1") if the bit vector is full and "false" ("0")
otherwise.
0"). if ($vec1->equal($vec2))
1") if the two bit vectors are exact
copies of one another and "false" ("0") otherwise. $cmp = $vec1->Lexicompare($vec2);
-1" if the first bit vector is smaller
than the second bit vector, "0" if the two bit vectors are
exact copies of one another and "1" if the first bit vector
is greater than the second bit vector. $cmp = $vec1->Compare($vec2);
-1" if the first bit vector is smaller
than the second bit vector, "0" if the two bit vectors are
exact copies of one another and "1" if the first bit vector
is greater than the second bit vector. $string = $vector->to_Hex();
$vector->from_Hex($string);
to_Hex()" (see above).
$string = $vector->to_Bin();
$vector = Bit::Vector->new(8); $vector->Primes(); $string = $vector->to_Bin(); print "'$string'\n";
'10101100'
$vector->from_Bin($string);
to_Bin()" (see above).
0" and "1") than are
needed to completely fill the given bit vector, the remaining (most significant)
bits are all cleared.
0" or "1", a fatal syntax error
ensues ("input string syntax error"). $string = $vector->to_Dec();
10).
from_Dec()" (see below) in order
to copy the contents of this bit vector to another one (or to restore the
contents of this one). This is not advisable, though, since this would be
very inefficient (there are much more efficient methods for storing and
copying bit vectors in this module).
10 with remainder
until the quotient becomes 0 (each remainder in turn represents a single
decimal digit of the resulting string).
10, the bit vector is repeatedly divided by the
largest power of 10 that will fit into a machine word. The remainder is
then repeatedly divided by 10 using only machine word arithmetics, which
is much faster than dividing the whole bit vector ("divide and rule" principle).
$vector->from_Dec($string);
0-9)
and an optional leading sign ("+" or "-"), a fatal "input string
syntax error" occurs.
eval", like this:
eval { $vector->from_Dec("1152921504606846976"); };
if ($@)
{
# an error occurred
}
if ($@ =~ /item is not a string/)
if ($@ =~ /input string syntax error/)
if ($@ =~ /numeric overflow error/)
if ($@ =~ /unable to allocate memory/)
10 corresponding to its position in
the decimal number, i.e., 1, 10, 100, 1000, 10000 and so on).
to_Dec()"), the implementation of this
method in this module uses the principle of "divide and rule" in order
to speed up the conversion, i.e., as many decimal digits as possible
are first accumulated (converted) in a machine word and only then
stored in the given bit vector.
$string = $vector->to_Enum();
1") in the bit vector.
$vector = Bit::Vector->new(20); $vector->Bit_On(2); $vector->Bit_On(3); $vector->Bit_On(11); $vector->Interval_Fill(5,7); $vector->Interval_Fill(13,19); print "'", $vector->to_Enum(), "'\n";
'2,3,5-7,11,13-19'
Bit::Vector->Configuration("out=enum");
$vector = Bit::Vector->new(20);
$vector->Index_List_Store(2,3,5,6,7,11,13,14,15,16,17,18,19);
print "'$vector'\n";
$vector->from_Enum($string);
$string" must only contain unsigned integers
or ranges of integers (two unsigned integers separated by a
dash "-"), separated by commas (",").
0" and
"$vector->Size()-1".
eval", like this:
eval { $vector->from_Enum("2,3,5-7,11,13-19"); };
if ($@)
{
# an error occurred
}
if ($@ =~ /item is not a string/)
if ($@ =~ /input string syntax error/)
if ($@ =~ /index out of range/)
if ($@ =~ /minimum > maximum index/)
eval { $vector->from_Enum("11,5-7,3,13-19,2"); };
Bit_On()", internally, and each range to
the method "Interval_Fill()".
$vector->Bit_Off($index);
$index" in the given vector. $vector->Bit_On($index);
$index" in the given vector. $vector->bit_flip($index)
$index"
in the given vector.
0" if the bit is
cleared or "1" if the bit is set (AFTER flipping it). if ($vector->bit_test($index))
if ($vector->contains($index))
$index"
in the given vector, i.e., returns "0" if it is cleared
(in the "off" state) or "1" if it is set (in the "on" state). $vector->Bit_Copy($index,$bit);
$index" in the given vector either
to "0" or "1" depending on the boolean value "$bit". $vector->LSB($bit);
$bit".
$vector->Bit_Copy(0,$bit);". $vector->MSB($bit);
$bit".
$vector->Bit_Copy($vector->Size()-1,$bit);". $bit = $vector->lsb();
$bit = $vector->bit_test(0);". $bit = $vector->msb();
$bit = $vector->bit_test($vector->Size()-1);". $carry_out = $vector->rotate_left();
carry MSB vector: LSB
out:
+---+ +---+---+---+--- ---+---+---+---+
| | <---+--- | | | | ... | | | | <---+
+---+ | +---+---+---+--- ---+---+---+---+ |
| |
+------------------------------------------------+
0", the most
significant bit (MSB) is the bit with index "$vector->Size()-1". $carry_out = $vector->rotate_right();
MSB vector: LSB carry
out:
+---+---+---+--- ---+---+---+---+ +---+
+---> | | | | ... | | | | ---+---> | |
| +---+---+---+--- ---+---+---+---+ | +---+
| |
+------------------------------------------------+
0", the most
significant bit (MSB) is the bit with index "$vector->Size()-1". $carry_out = $vector->shift_left($carry_in);
carry MSB vector: LSB carry out: in: +---+ +---+---+---+--- ---+---+---+---+ +---+ | | <--- | | | | ... | | | | <--- | | +---+ +---+---+---+--- ---+---+---+---+ +---+
0", the most
significant bit (MSB) is the bit with index "$vector->Size()-1". $carry_out = $vector->shift_right($carry_in);
carry MSB vector: LSB carry in: out: +---+ +---+---+---+--- ---+---+---+---+ +---+ | | ---> | | | | ... | | | | ---> | | +---+ +---+---+---+--- ---+---+---+---+ +---+
0", the most
significant bit (MSB) is the bit with index "$vector->Size()-1". $vector->Move_Left($bits);
$bits" bits, i.e., inserts "$bits"
new bits at the lower end (least significant bit) of the bit vector, moving
all other bits up by "$bits" places, thereby losing the "$bits" most
significant bits.
$bits" is equal to zero.
$bits" is greater than or equal to the size of the given bit vector!
for ( $i = 0; $i < $bits; $i++ ) { $vector->shift_left(0); }
$bits" greater than or
equal to the number of bits in a machine word on your system) than
this straightforward approach. $vector->Move_Right($bits);
$bits" bits, i.e., deletes the
"$bits" least significant bits of the bit vector, moving all other bits
down by "$bits" places, thereby creating "$bits" new bits at the upper
end (most significant bit) of the bit vector.
$bits" is equal to zero.
$bits" is greater than or equal to the size of the given bit vector!
for ( $i = 0; $i < $bits; $i++ ) { $vector->shift_right(0); }
$bits" greater than or
equal to the number of bits in a machine word on your system) than
this straightforward approach. $vector->Insert($offset,$bits);
$bits" fresh new bits at position "$offset"
in the given bit vector.
$bits" most significant bits are lost, and all bits starting
with bit number "$offset" up to and including bit number
"$vector->Size()-$bits-1" are moved up by "$bits" places.
$bits" bits starting at bit number "$offset"
(up to and including bit number "$offset+$bits-1") are then set
to zero (cleared).
$bits" uppermost (most significant) bits - instead,
these bits are lost forever.
$vector->Resize($vector->Size() + $bits);
Interval_Substitute()" instead of "Insert()",
which performs automatic growing and shrinking of its target bit vector.
$offset" must lie in the permitted range between
"0" and "$vector->Size()-1", or a fatal "offset out of range"
error will occur.
$offset + $bits" exceeds "$vector->Size()-1",
all the bits starting with bit number "$offset" up to bit number
"$vector->Size()-1" are simply cleared. $vector->Delete($offset,$bits);
$offset" up to and including bit number "$offset+$bits-1"
from the given bit vector.
$offset+$bits"
up to and including bit number "$vector->Size()-1") are moved
down by "$bits" places.
$bits" bits are then
set to zero (cleared).
$bits" uppermost bits.
$size = $vector->Size();
if ($bits > $size) { $bits = $size; }
$vector->Resize($size - $bits);
Interval_Substitute()" instead of "Delete()",
which performs automatic growing and shrinking of its target bit vector.
$offset" must lie in the permitted range between
"0" and "$vector->Size()-1", or a fatal "offset out of range"
error will occur.
$offset + $bits" exceeds "$vector->Size()-1",
all the bits starting with bit number "$offset" up to bit number
"$vector->Size()-1" are simply cleared. $carry = $vector->increment();
before: 2 ^ (b-1) - 1 (= "0111...1111") after: 2 ^ (b-1) (= "1000...0000")
b" is the number of bits of the given bit vector.
0") in all cases except when a
carry over occurs (in which case it returns "true", i.e., "1"),
which happens when the number "1111...1111" is incremented,
which gives "0000...0000" plus a carry over to the next higher
(binary) digit.
$carry = $vector->decrement();
before: 2 ^ (b-1) (= "1000...0000") after: 2 ^ (b-1) - 1 (= "0111...1111")
b" is the number of bits of the given bit vector.
0") in all cases except when a
carry over occurs (in which case it returns "true", i.e., "1"),
which happens when the number "0000...0000" is decremented,
which gives "1111...1111" minus a carry over to the next higher
(binary) digit.
$overflow = $vec2->inc($vec1);
$vec1" to bit
vector "$vec2" and increments the copy (not the original).
1"), or false ("0")
if not. (See the description of the method "add()" below for
a more in-depth explanation of what "overflow" means).
$vec1"
and "$vec2" may be identical. $overflow = $vec2->dec($vec1);
$vec1" to bit
vector "$vec2" and decrements the copy (not the original).
1"), or false ("0")
if not. (See the description of the method "subtract()" below
for a more in-depth explanation of what "overflow" means).
$vec1"
and "$vec2" may be identical. $carry = $vec3->add($vec1,$vec2,$carry);
($carry,$overflow) = $vec3->add($vec1,$vec2,$carry);
$vec1"
and "$vec2" with carry "$carry" and stores the result in
bit vector "$vec3".
$carry" parameter is a boolean value, i.e.,
only its least significant bit is taken into account. (Think of
it as though "$carry &= 1;" was always executed internally.)
1") if the sign (i.e., the most
significant bit) of the result is wrong. This can happen when
adding two very large positive numbers or when adding two (by
their absolute value) very large negative numbers. See also
further below.
# initialize
for ( $i = 0; $i < $n; $i++ )
{
$a[$i] = Bit::Vector->new($bits);
$b[$i] = Bit::Vector->new($bits);
$c[$i] = Bit::Vector->new($bits);
}
# fill @a and @b
# $a[ 0 ] is low order part, # $a[$n-1] is high order part, # and same for @b
# add
$carry = 0;
for ( $i = 0; $i < $n; $i++ )
{
$carry = $c[$i]->add($a[$i],$b[$i],$carry);
}
$vec1" and "$vec2" are unsigned or signed (i.e., in two's
complement binary representation).
$carry = $vec3->subtract($vec1,$vec2,$carry);
($carry,$overflow) = $vec3->subtract($vec1,$vec2,$carry);
$vec1" and "$vec2" with carry "$carry" and stores the
result in bit vector "$vec3".
$carry" parameter is a boolean value, i.e.,
only its least significant bit is taken into account. (Think of
it as though "$carry &= 1;" was always executed internally.)
1") if the sign (i.e., the most
significant bit) of the result is wrong. This can happen when
subtracting a very large negative number from a very large
positive number or vice-versa. See also further below.
# initialize
for ( $i = 0; $i < $n; $i++ )
{
$a[$i] = Bit::Vector->new($bits);
$b[$i] = Bit::Vector->new($bits);
$c[$i] = Bit::Vector->new($bits);
}
# fill @a and @b
# $a[ 0 ] is low order part, # $a[$n-1] is high order part, # and same for @b
# subtract
$carry = 0;
for ( $i = 0; $i < $n; $i++ )
{
$carry = $c[$i]->subtract($a[$i],$b[$i],$carry);
}
$vec1" and "$vec2" are unsigned or signed (i.e., in two's
complement binary representation).
$vec2->Neg($vec1);
$vec2->Negate($vec1);
$vec1" and stores the result in bit vector "$vec2".
+" to
"-" or vice-versa. In other words, applying this method twice on a given
number yields the original number again.
$vec1" and
"$vec2" may be identical.
$vec1" is 2 ^ (n-1)
(i.e., "1000...0000"), where "n" is the number of bits the given bit
vector contains: The negated value of this number is the number itself! $vec2->Abs($vec1);
$vec2->Absolute($vec1);
$vec1", the contents of bit vector "$vec1" are copied
to bit vector "$vec2" either with the method "Copy()" (if the number
in bit vector "$vec1" is positive), or with "Negate()" (if the number
in bit vector "$vec1" is negative).
$vec1" and stores the result in bit vector "$vec2".
$vec1" and
"$vec2" may be identical.
$vec1" is 2 ^ (n-1)
(i.e., "1000...0000"), where "n" is the number of bits the given bit
vector contains: The absolute value of this number is the number itself,
even though this number is still negative by definition (the most
significant bit is still set)! $sign = $vector->Sign();
0" if all bits in the given bit vector are cleared,
i.e., if the given bit vector contains the number "0", or if the given
bit vector has a length of zero (contains no bits at all).
-1" if the most
significant bit is set (i.e., if the bit vector contains a negative
number), or "1" otherwise (i.e., if the bit vector contains a
positive number). $vec3->Multiply($vec1,$vec2);
$vec1"
and "$vec2" and stores the result in bit vector "$vec3".
$msb1 = $vec1->msb();
$msb2 = $vec2->msb();
$vec1->Resize($vec1->Size()+1);
$vec2->Resize($vec2->Size()+1);
$vec3->Resize($vec3->Size()+1);
$vec1->MSB($msb1);
$vec2->MSB($msb2);
$vec3->Multiply($vec1,$vec2);
$vec3" may be larger
than the two factors "$vec1" and "$vec2".
n" bits may yield a result
which is at most "2n" bits long.
$vec3" have
twice the size of bit vector "$vec1" and "$vec2", unless you are
absolutely sure that the result will fit into a bit vector of the same
size as the two factors.
$vec3"
may be identical with "$vec1" or "$vec2", or both. $quot->Divide($vec1,$vec2,$rest);
$vec1"
and "$vec2" and stores the quotient in bit vector "$quot" and
the remainder in bit vector "$rest".
$quot" and "$rest" must be two DISTINCT bit vectors,
or a fatal "result vector(s) must be distinct" error will occur.
$vec2"
is equal to zero.
$msb1 = $vec1->msb();
$msb2 = $vec2->msb();
$vec1->Resize($vec1->Size()+1);
$vec2->Resize($vec2->Size()+1);
$quot->Resize($quot->Size()+1);
$rest->Resize($rest->Size()+1);
$vec1->MSB($msb1);
$vec2->MSB($msb2);
$quot->Divide($vec1,$vec2,$rest);
$quot"
may be identical with "$vec1" or "$vec2" or both, and "$rest"
may also be identical with "$vec1" or "$vec2" or both, as long
as "$quot" and "$rest" are distinct. (!) $vecgcd->GCD($veca,$vecb);
$veca" and "$vecb" and stores the result
in bit vector "$vecgcd".
int GCD(int a, int b)
{
int t;
while (b != 0)
{
t = a % b; /* = remainder of (a div b) */
a = b;
b = t;
}
return(a);
}
GCD(z,0) == GCD(0,z) == z. $vecgcd->GCD($vecx,$vecy,$veca,$vecb);
$veca" and "$vecb" and
stores the result in bit vector "$vecgcd".
"x" and "y" so that
GCD(a,b) == x * a + y * b, and stores them in bit vector "$vecx"
and "$vecy", respectively.
a = 2322 b = 654
GCD( 2322, 654 ) == 6
x = 20 y = -71
20 * 2322 - 71 * 654 == 6
$vec3->Power($vec1,$vec2);
$vec1" elevated to
the "$vec2" power, i.e., "$vec1 ** $vec2", and stores the result
in bit vector "$vec3".
$vec1 * $vec1 * $vec1 * $vec1 * $vec1 * $vec1 * $vec1 * $vec1 * $vec1 * $vec1 * $vec1 * $vec1 * $vec1
$vec1" multiplied with itself 13 times. The grouping
into lines above is no coincidence. The first line comprises 8
factors, the second contains 4, and the last line just one. This
just happens to be the binary representation of 13. ;-)
$power[0] = $vec1; $power[1] = $vec1 * $vec1; $power[2] = $power[1] * $power[1]; $power[3] = $power[2] * $power[2]; etc.
$result = 1; $result *= $power[0] if ($vec2 & 1); $result *= $power[1] if ($vec2 & 2); $result *= $power[2] if ($vec2 & 4); $result *= $power[3] if ($vec2 & 8); etc.
$vec3" must be of the same size as the base
"$vec1" or greater. "$vec3" and "$vec1" may be the same
vector (i.e., in-place calculation as in "$vec1 **= $vec2;" is
possible), but "$vec3" and "$vec2" must be distinct. Finally,
the exponent "$vec2" must be positive. A fatal error occurs if
any of these conditions is not met. $vector->Block_Store($buffer);
Block_Read()"), and when you want to
restore the previously saved bit vector.
$buffer" MUST be a string (NO automatic conversion
from numeric to string is provided here as would normally in Perl!)
containing the bit vector in "low order byte first" order.
$buffer"
from a file prior to passing it to this method. $buffer = $vector->Block_Read();
$size = $vector->Word_Size();
Chunk_"
instead, with chunk sizes no greater than 32 bits.
Word_Size()" returns the number of machine words that the
internal array of words of the given bit vector contains.
scalar(@array)" for a Perl array. $vector->Word_Store($offset,$word);
$word" at a given
position "$offset" in the internal array of words of the given
bit vector.
$offset" must lie in the permitted range between "0"
and "$vector->Word_Size()-1", or a fatal "offset out of range"
error will occur.
$array[$offset] = $word;" for a Perl array. $word = $vector->Word_Read($offset);
$offset" in the internal array of words of the given
bit vector.
$offset" must lie in the permitted range between "0"
and "$vector->Word_Size()-1", or a fatal "offset out of range"
error will occur.
$word = $array[$offset];" for a Perl array. $vector->Word_List_Store(@words);
@words" in the
internal array of machine words of the given bit vector.
$words[0]") is stored
in the LEAST significant word of the internal array of words (the
one with offset "0"), the next value from the list ("$words[1]")
is stored in the word with offset "1", and so on, as intuitively
expected.
@words" contains fewer elements than the internal
array of words of the given bit vector contains machine words,
the remaining (most significant) words are filled with zeros.
@words" contains more elements than the internal
array of words of the given bit vector contains machine words,
the superfluous values are simply ignored.
@array = @words;" for a Perl array. @words = $vector->Word_List_Read();
$words[0]")
is the LEAST significant word from the given bit vector, and the
RIGHTMOST value in the returned list ("$words[$#words]") is
the MOST significant word of the given bit vector.
@words = @array;" for a Perl array. $vector->Word_Insert($offset,$count);
$count" empty new machine words at position
"$offset" in the internal array of words of the given bit vector.
$count" most significant words are lost, and all words starting
with word number "$offset" up to and including word number
"$vector->Word_Size()-$count-1" are moved up by "$count" places.
$count" words starting at word number "$offset"
(up to and including word number "$offset+$count-1") are then set
to zero (cleared).
$count" uppermost (most significant) words - instead,
these words are lost forever.
$vector->Resize($vector->Size() + $count * Bit::Vector->Word_Bits());
$offset" must lie in the permitted range between
"0" and "$vector->Word_Size()-1", or a fatal "offset out
of range" error will occur.
$offset + $count" exceeds "$vector->Word_Size()-1",
all the words starting with word number "$offset" up to word number
"$vector->Word_Size()-1" are simply cleared. $vector->Word_Delete($offset,$count);
$offset" up to and including word number "$offset+$count-1"
from the internal array of machine words of the given bit vector.
$offset+$count"
up to and including word number "$vector->Word_Size()-1") are
moved down by "$count" places.
$count" words are then
set to zero (cleared).
$count" uppermost words.
$bits = $vector->Size();
$count *= Bit::Vector->Word_Bits();
if ($count > $bits) { $count = $bits; }
$vector->Resize($bits - $count);
$offset" must lie in the permitted range between
"0" and "$vector->Word_Size()-1", or a fatal "offset out
of range" error will occur.
$offset + $count" exceeds "$vector->Word_Size()-1",
all the words starting with word number "$offset" up to word number
"$vector->Word_Size()-1" are simply cleared. $vector->Chunk_Store($chunksize,$offset,$chunk);
Bit::Vector->Long_Bits()" bits wide.
$chunksize" does not lie between "1" and
"Bit::Vector->Long_Bits()", a fatal "chunk size out of range"
error will occur.
$chunksize" least significant bits
from the value "$chunk" to the given bit vector, starting at
bit position "$offset" and proceeding upwards until bit number
"$offset+$chunksize-1".
0" of "$chunk" becomes bit number "$offset"
in the given bit vector, and bit number "$chunksize-1" becomes
bit number "$offset+$chunksize-1".)
$offset+$chunksize-1" exceeds "$vector->Size()-1",
the corresponding superfluous (most significant) bits from "$chunk"
are simply ignored.
$offset" itself must lie in the permitted range between
"0" and "$vector->Size()-1", or a fatal "offset out of range"
error will occur.
Chunk_" methods) is useful, for
example, when you are reading in data in chunks of, say, 8 bits, which
you need to access later, say, using 16 bits at a time (like audio CD
wave files, for instance). $chunk = $vector->Chunk_Read($chunksize,$offset);
Bit::Vector->Long_Bits()" bits wide.
$chunksize" does not lie between "1" and
"Bit::Vector->Long_Bits()", a fatal "chunk size out of range"
error will occur.
$chunksize" bits from the given bit vector
starting at bit position "$offset" and proceeding upwards until
bit number "$offset+$chunksize-1".
$offset" of the given bit vector becomes bit number
"0" of the returned value, and bit number "$offset+$chunksize-1"
becomes bit number "$chunksize-1".)
$offset+$chunksize-1" exceeds "$vector->Size()-1",
the non-existent bits are simply not returned.
$offset" itself must lie in the permitted range between
"0" and "$vector->Size()-1", or a fatal "offset out of range"
error will occur. $vector->Chunk_List_Store($chunksize,@chunks);
$chunksize") you like
(within certain limits).
$chunksize" must lie in the range between "1"
and "Bit::Vector->Long_Bits()", or a fatal "chunk size out of
range" error will occur.
$chunks[0]") fills the "$chunksize"
least significant bits, the next chunk from the list ("$chunks[1]")
fills the bits number "$chunksize" to number "2*$chunksize-1",
the third chunk ("$chunks[2]") fills the bits number "2*$chunksize",
to number "3*$chunksize-1", and so on.
$vector->Size()-1"
(which happens whenever "$vector->Size()" is not a multiple of
"$chunksize"), the superfluous chunks and/or bits are simply ignored.
$vector->Chunk_List_Store(3, split(//, reverse $string));
from_Hex()",
"from_Bin()", "from_Dec()" and "from_Enum()",
this statement does not include any syntax checking, i.e.,
it may fail silently, without warning.
if ($string =~ /^[0-7]+$/)
{
# okay, go ahead with conversion as shown above
}
else
{
# error, string contains other than octal characters
}
$pattern = 0xDEADBEEF;
$length = 32; # = length of $pattern in bits
$size = $vector->Size();
$factor = int($size / $length);
if ($size % $length) { $factor++; }
$vector->Chunk_List_Store($length, ($pattern) x $factor);
@chunks = $vector->Chunk_List_Read($chunksize);
$chunksize")
of your choosing (within certain limits).
$chunksize" must lie in the range between "1"
and "Bit::Vector->Long_Bits()", or a fatal "chunk size out of
range" error will occur.
$chunksize" least significant bits (bits number "0" to
"$chunksize-1") become the first chunk in the returned list
(i.e., "$chunks[0]"). The bits number "$chunksize" to
"2*$chunksize-1" become the next chunk in the list
("$chunks[1]"), and so on.
$vector->Size()" is not a multiple of "$chunksize",
the last chunk in the list will contain fewer bits than "$chunksize".
$chunksize",
the number of returned list elements can be extremely large! BE CAREFUL!
$string = reverse join('', $vector->Chunk_List_Read(3));
$vector->Index_List_Remove(@indices);
foreach $index (@indices)
{
$vector->Bit_Off($index);
}
Index_List_Store()". As a
consequence, you can "wipe out" what you did using the method
"Index_List_Remove()" by passing the identical argument list
to the method "Index_List_Store()".) $vector->Index_List_Store(@indices);
foreach $index (@indices)
{
$vector->Bit_On($index);
}
Index_List_Remove()". As a
consequence, you can "wipe out" what you did using the method
"Index_List_Store()" by passing the identical argument list
to the method "Index_List_Remove()".) @indices = $vector->Index_List_Read();
$limit = 1000; # or whatever
$vector = Bit::Vector->new($limit+1);
$vector->Primes();
@primes = $vector->Index_List_Read();
$vec3->Or($vec1,$vec2);
$set3->Union($set1,$set2);
$set1" and "$set2" and stores
the result in "$set3".
$set3 = $set1 u $set2" in set theory
(where "u" is the "cup" operator).
$set3" may be identical
with "$set1" or "$set2" or both. $vec3->And($vec1,$vec2);
$set3->Intersection($set1,$set2);
$set1" and "$set2" and
stores the result in "$set3".
$set3 = $set1 n $set2" in set theory
(where "n" is the "cap" operator).
$set3" may be identical
with "$set1" or "$set2" or both. $vec3->AndNot($vec1,$vec2);
$set3->Difference($set1,$set2);
$set1" less "$set2" and
stores the result in "$set3".
$set3 = $set1 \ $set2" in set theory
(where "\" is the "less" operator).
$set3" may be identical
with "$set1" or "$set2" or both. $vec3->Xor($vec1,$vec2);
$set3->ExclusiveOr($set1,$set2);
$set1" and "$set2"
and stores the result in "$set3".
$set3 = ($set1 u $set2) \ ($set1 n $set2)" in set
theory (the union of the two sets less their intersection).
$set3" may be identical
with "$set1" or "$set2" or both. $vec2->Not($vec1);
$set2->Complement($set1);
$set1" and stores the result
in "$set2".
$set1" in binary
representation.
$set2" may be identical
with "$set1". if ($set1->subset($set2))
1") if "$set1" is a subset of "$set2"
(i.e., completely contained in "$set2") and "false" ("0")
otherwise.
1") in "$set1" must
also be set in "$set2", but "$set2" may contain set bits
which are not set in "$set1", in order for the condition
of subset relationship to be true between these two sets.
$norm = $set->Norm();
$norm = $set->Norm2();
Norm()" above, only with a
different algorithm:
Norm()"
above on some systems, depending on the system's architecture
and the compiler and optimisation used, for bit vectors with
sparse set bits and for bit vectors with sparse cleared bits
(i.e., predominantly set bits). $norm = $set->Norm3();
Norm()" and "Norm2()"
above, however with a different algorithm.
Norm()" used
in previous versions of this module.
$min = $set->Min();
$set".
n" is the
number of bits of an unsigned long on your machine.) $max = $set->Max();
$set".
n" is the number of bits of an unsigned long on your machine.) $m3->Multiplication($r3,$c3,$m1,$r1,$c1,$m2,$r2,$c2);
$m1" and "$m2" and stores the result in matrix "$m3".
^") as the boolean
addition operator ("+").
rows3 == rows1 cols3 == cols2 cols1 == rows2
$m3->Product($r3,$c3,$m1,$r1,$c1,$m2,$r2,$c2);
$m1" and "$m2" and stores the result in matrix "$m3".
|") as the
boolean addition operator ("+").
rows3 == rows1 cols3 == cols2 cols1 == rows2
$matrix->Closure($rows,$cols);
1" (otherwise it remains set to "0").
$matrix2->Transpose($rows2,$cols2,$matrix1,$rows1,$cols1);
$matrix1"
(stored as a bit vector) and stores the result in matrix "$matrix2".
rows2 == cols1 cols2 == rows1
$matrix1" and "$matrix2" are
identical) is only possible if the matrix is quadratic. Otherwise,
a fatal "matrix is not quadratic" error will occur.
Bit::Vector::Overload(3), Bit::Vector::String(3), Storable(3).
Set::IntRange(3), Math::MatrixBool(3), Math::MatrixReal(3), DFA::Kleene(3), Math::Kleene(3), Graph::Kruskal(3).
This man page documents "Bit::Vector" version 7.1.
Steffen Beyer mailto:STBEY@cpan.org http://www.engelschall.com/u/sb/download/
Copyright (c) 1995 - 2009 by Steffen Beyer. All rights reserved.
This package is free software; you can redistribute it and/or modify it under the same terms as Perl itself, i.e., under the terms of the "Artistic License" or the "GNU General Public License".
The C library at the core of this Perl module can additionally be redistributed and/or modified under the terms of the "GNU Library General Public License".
Please refer to the files "Artistic.txt", "GNU_GPL.txt" and "GNU_LGPL.txt" in this distribution for details!
This package is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
See the "GNU General Public License" for more details.
| Bit-Vector documentation | view source | Contained in the Bit-Vector distribution. |