Skip to content

bit_vector - [mainnet]

Constants

The provided index is out of bounds

const EINDEX: u64 = 131072;

An invalid length of bitvector was given

const ELENGTH: u64 = 131073;

The maximum allowed bitvector size

const MAX_SIZE: u64 = 1024;
const WORD_SIZE: u64 = 1;

Structs

BitVector

struct BitVector has copy, drop, store
Fields
length: u64
bit_field: vector<bool>

Functions

new

public fun new(length: u64): bit_vector::BitVector
Implementation
public fun new(length: u64): BitVector {
assert!(length > 0, ELENGTH);
assert!(length < MAX_SIZE, ELENGTH);
let counter = 0;
let bit_field = vector::empty();
while ({spec {
invariant counter <= length;
invariant len(bit_field) == counter;
};
(counter < length)}) {
bit_field.push_back(false);
counter += 1;
};
spec {
assert counter == length;
assert len(bit_field) == length;
};
BitVector {
length,
bit_field,
}
}

set

Set the bit at bit_index in the self regardless of its previous state.

public fun set(self: &mut bit_vector::BitVector, bit_index: u64)
Implementation
public fun set(self: &mut BitVector, bit_index: u64) {
assert!(bit_index < self.bit_field.length(), EINDEX);
self.bit_field[bit_index] = true;
}

unset

Unset the bit at bit_index in the self regardless of its previous state.

public fun unset(self: &mut bit_vector::BitVector, bit_index: u64)
Implementation
public fun unset(self: &mut BitVector, bit_index: u64) {
assert!(bit_index < self.bit_field.length(), EINDEX);
self.bit_field[bit_index] = false;
}

shift_left

Shift the self left by amount. If amount is greater than the bitvector’s length the bitvector will be zeroed out.

public fun shift_left(self: &mut bit_vector::BitVector, amount: u64)
Implementation
public fun shift_left(self: &mut BitVector, amount: u64) {
if (amount >= self.length) {
self.bit_field.for_each_mut(|elem| {
*elem = false;
});
} else {
let i = amount;
while (i < self.length) {
if (self.is_index_set(i)) self.set(i - amount)
else self.unset(i - amount);
i += 1;
};
i = self.length - amount;
while (i < self.length) {
self.unset(i);
i += 1;
};
}
}

is_index_set

Return the value of the bit at bit_index in the self. true represents “1” and false represents a 0

public fun is_index_set(self: &bit_vector::BitVector, bit_index: u64): bool
Implementation
public fun is_index_set(self: &BitVector, bit_index: u64): bool {
assert!(bit_index < self.bit_field.length(), EINDEX);
self.bit_field[bit_index]
}

length

Return the length (number of usable bits) of this bitvector

public fun length(self: &bit_vector::BitVector): u64
Implementation
public fun length(self: &BitVector): u64 {
self.bit_field.length()
}

longest_set_sequence_starting_at

Returns the length of the longest sequence of set bits starting at (and including) start_index in the bitvector. If there is no such sequence, then 0 is returned.

public fun longest_set_sequence_starting_at(self: &bit_vector::BitVector, start_index: u64): u64
Implementation
public fun longest_set_sequence_starting_at(self: &BitVector, start_index: u64): u64 {
assert!(start_index < self.length, EINDEX);
let index = start_index;
// Find the greatest index in the vector such that all indices less than it are set.
while ({
spec {
invariant index >= start_index;
invariant index == start_index || self.is_index_set(index - 1);
invariant index == start_index || index - 1 < len(self.bit_field);
invariant forall j in start_index..index: self.is_index_set(j);
invariant forall j in start_index..index: j < len(self.bit_field);
};
index < self.length
}) {
if (!self.is_index_set(index)) break;
index += 1;
};
index - start_index
}

Specification

BitVector

struct BitVector has copy, drop, store
length: u64
bit_field: vector<bool>
invariant length == len(bit_field);

new

public fun new(length: u64): bit_vector::BitVector
include NewAbortsIf;
ensures result.length == length;
ensures len(result.bit_field) == length;
schema NewAbortsIf {
length: u64;
aborts_if length <= 0 with ELENGTH;
aborts_if length >= MAX_SIZE with ELENGTH;
}

set

public fun set(self: &mut bit_vector::BitVector, bit_index: u64)
include SetAbortsIf;
ensures self.bit_field[bit_index];
schema SetAbortsIf {
self: BitVector;
bit_index: u64;
aborts_if bit_index >= self.length() with EINDEX;
}

unset

public fun unset(self: &mut bit_vector::BitVector, bit_index: u64)
include UnsetAbortsIf;
ensures !self.bit_field[bit_index];
schema UnsetAbortsIf {
self: BitVector;
bit_index: u64;
aborts_if bit_index >= self.length() with EINDEX;
}

shift_left

public fun shift_left(self: &mut bit_vector::BitVector, amount: u64)
pragma verify = false;

is_index_set

public fun is_index_set(self: &bit_vector::BitVector, bit_index: u64): bool
include IsIndexSetAbortsIf;
ensures result == self.bit_field[bit_index];
schema IsIndexSetAbortsIf {
self: BitVector;
bit_index: u64;
aborts_if bit_index >= self.length() with EINDEX;
}
fun spec_is_index_set(self: BitVector, bit_index: u64): bool {
if (bit_index >= self.length()) {
false
} else {
self.bit_field[bit_index]
}
}

longest_set_sequence_starting_at

public fun longest_set_sequence_starting_at(self: &bit_vector::BitVector, start_index: u64): u64
aborts_if start_index >= self.length;
ensures forall i in start_index..result: self.is_index_set(i);