Bachelors_Thesis_Code/Rabin_fingerprint.cpp

74 lines
2.1 KiB
C++
Raw Normal View History

2021-11-14 14:35:05 +01:00
#include "Rabin_fingerprint.hpp"
Rabin_fingerprint::Rabin_fingerprint(uint32_t p, size_t window_size_in_bits) {
set_modulo_polynomial(p);
set_shift_polynomial(window_size_in_bits);
}
void Rabin_fingerprint::set_modulo_polynomial (uint32_t p) {
polynomial = p & ((uint32_t)pow(2, 31)-1);
}
void Rabin_fingerprint::set_shift_polynomial (size_t window_size_in_bits) {
#ifndef NDEBUG
if (polynomial == 0)
throw std::logic_error("Call set_modulo_polynomial first, as this function depends on the polynomial variable being set.");
#endif
shift_polynomial = 1;
// NOTE: We shift the bit 1 space too long, since we are removing the bit that has been pushed outside the window
for (size_t i = 0; i < window_size_in_bits; i++) {
shift_polynomial <<= 1;
if ((shift_polynomial & (uint32_t)pow(2, 31)) != 0)
shift_polynomial ^= polynomial;
}
}
void Rabin_fingerprint::push_char (char c) {
std::bitset<8> b(c);
for (char i = 7; i >= 0; i--) {
push_bit((bool)b[i]);
}
}
void Rabin_fingerprint::push_bit (bool b) {
fingerprint <<= 1;
fingerprint |= b;
if ((fingerprint & (uint32_t)pow(2, 31)) != 0)
fingerprint ^= polynomial;
}
void Rabin_fingerprint::shift_bit (bool b) {
#ifndef NDEBUG
if (shift_polynomial == 0)
throw std::logic_error("Call set_shift_polynomial first, as this function depends on the shift_polynomial variable being set.");
#endif
if (b)
fingerprint ^= shift_polynomial;
}
void Rabin_fingerprint::slide_char (char c_in, char c_out) {
std::bitset<8> b_in(c_in);
std::bitset<8> b_out(c_out);
for (char i = 7; i >= 0; i--) {
slide_bit((bool)b_in[i], (bool)b_out[i]);
}
}
/* #include <iostream> */
void Rabin_fingerprint::slide_bit (bool b_in, bool b_out) {
/* std::cout << "bitset b(c): " << b << std::endl; */
/* std::cout << "push bit " << b[i] << std::endl; */
/* std::cout << "push bit " << b_in << std::endl; */
push_bit(b_in);
/* std::cout << "shift bit " << b_out << std::endl; */
shift_bit(b_out);
}
uint32_t Rabin_fingerprint::get_fingerprint () {
return fingerprint;
}