use crate::{error::{DecompressError, CompressError}, Compressed, BinaryChunk};
pub trait Comprezable<Rhs = Self> {
fn compress(self) -> Result<Compressed, CompressError>;
fn compress_to_binaries(self, max_num: Option<u128>) -> Result<Compressed, CompressError>;
fn max_binaries(max_num: Option<u128>) -> BinaryChunk;
fn decompress(compressed: Compressed) -> Result<Self, DecompressError> where Self: Sized;
fn decompress_from_binaries(compressed: &mut Vec<u8>, bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized;
}
impl Comprezable for u16 {
fn compress(self) -> Result<Compressed, CompressError> {
Err(CompressError::create(CompressError::DataNoSupported(String::new())))
}
fn compress_to_binaries(self, max_num: Option<u128>) -> Result<Compressed, CompressError> {
let max_num = max_num.unwrap() as Self;
if self > max_num {
return Err(CompressError::create(CompressError::Overflow(format!("given: {}, max-num: {}", self,max_num))))
}
let mult_8_bit_size = find_mult_8_bit_size(max_num, 8, 0, 2);
let compressed_binaries = compress_num(self, mult_8_bit_size, 8, 2, 0);
let res = compressed_binaries.iter().map(|&binary| binary as u8).collect::<Vec<u8>>();
Ok(Compressed::Binaries(res))
}
fn max_binaries(max_num: Option<u128>) -> BinaryChunk {
let max_num = max_num.unwrap() as Self;
BinaryChunk::Single(find_mult_8_bit_size(max_num, 8, 0, 2) + 3)
}
fn decompress(_compressed: Compressed) -> Result<u16, DecompressError> {
Err(DecompressError::create(DecompressError::PrimitiveDataErr(String::new())))
}
fn decompress_from_binaries(compressed: &mut Vec<u8>, bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized {
if compressed.len() < bit_size.unwrap() {
return Err(DecompressError::create(DecompressError::WrongBytesLength(format!("Not enough bytes"))))
}
let compressed_binaries = compressed.drain( .. bit_size.unwrap()).collect::<Vec<u8>>();
let split_at = compressed_binaries.len() - 3;
let (mult_8, remainder) = compressed_binaries.split_at(split_at);
let mult_8_bits = mult_8.iter().map(|bit| bit.to_string()).collect::<String>();
let remainder_bits = remainder.iter().map(|bit| bit.to_string()).collect::<String>();
let mult_8 = Self::from_str_radix(&mult_8_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", mult_8_bits)))
})? * 8;
let remainder = Self::from_str_radix(&remainder_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", remainder_bits)))
})?;
Ok(mult_8 + remainder)
}
}
impl Comprezable for u32 {
fn compress(self) -> Result<Compressed, CompressError> {
Err(CompressError::create(CompressError::DataNoSupported(String::new())))
}
fn compress_to_binaries(self, max_num: Option<u128>) -> Result<Compressed, CompressError> {
let max_num = max_num.unwrap() as Self;
if self > max_num {
return Err(CompressError::create(CompressError::Overflow(format!("given: {}, max-num: {}", self,max_num))))
}
let mult_8_bit_size = find_mult_8_bit_size(max_num, 8, 0, 2);
let compressed_binaries = compress_num(self, mult_8_bit_size, 8, 2, 0);
let res = compressed_binaries.iter().map(|&binary| binary as u8).collect::<Vec<u8>>();
Ok(Compressed::Binaries(res))
}
fn max_binaries(max_num: Option<u128>) -> BinaryChunk {
let max_num = max_num.unwrap() as Self;
BinaryChunk::Single(find_mult_8_bit_size(max_num, 8, 0, 2) + 3)
}
fn decompress(_compressed: Compressed) -> Result<u32, DecompressError> {
Err(DecompressError::create(DecompressError::PrimitiveDataErr(String::new())))
}
fn decompress_from_binaries(compressed: &mut Vec<u8>, bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized {
if compressed.len() < bit_size.unwrap() {
return Err(DecompressError::create(DecompressError::WrongBytesLength(format!("Not enough bytes"))))
}
let compressed_binaries = compressed.drain( .. bit_size.unwrap()).collect::<Vec<u8>>();
let split_at = compressed_binaries.len() - 3;
let (mult_8, remainder) = compressed_binaries.split_at(split_at);
let mult_8_bits = mult_8.iter().map(|bit| bit.to_string()).collect::<String>();
let remainder_bits = remainder.iter().map(|bit| bit.to_string()).collect::<String>();
let mult_8 = Self::from_str_radix(&mult_8_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", mult_8_bits)))
})? * 8;
let remainder = Self::from_str_radix(&remainder_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", remainder_bits)))
})?;
Ok(mult_8 + remainder)
}
}
impl Comprezable for u64 {
fn compress(self) -> Result<Compressed, CompressError> {
Err(CompressError::create(CompressError::DataNoSupported(String::new())))
}
fn compress_to_binaries(self, max_num: Option<u128>) -> Result<Compressed, CompressError> {
let max_num = max_num.unwrap() as Self;
if self > max_num {
return Err(CompressError::create(CompressError::Overflow(format!("given: {}, max-num: {}", self,max_num))))
}
let mult_8_bit_size = find_mult_8_bit_size(max_num, 8, 0, 2);
let compressed_binaries = compress_num(self, mult_8_bit_size, 8, 2, 0);
let res = compressed_binaries.iter().map(|&binary| binary as u8).collect::<Vec<u8>>();
Ok(Compressed::Binaries(res))
}
fn max_binaries(max_num: Option<u128>) -> BinaryChunk {
let max_num = max_num.unwrap() as Self;
BinaryChunk::Single(find_mult_8_bit_size(max_num, 8, 0, 2) + 3)
}
fn decompress(_compressed: Compressed) -> Result<u64, DecompressError> {
Err(DecompressError::create(DecompressError::PrimitiveDataErr(String::new())))
}
fn decompress_from_binaries(compressed: &mut Vec<u8>, bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized {
if compressed.len() < bit_size.unwrap() {
return Err(DecompressError::create(DecompressError::WrongBytesLength(format!("Not enough bytes"))))
}
let compressed_binaries = compressed.drain( .. bit_size.unwrap()).collect::<Vec<u8>>();
let split_at = compressed_binaries.len() - 3;
let (mult_8, remainder) = compressed_binaries.split_at(split_at);
let mult_8_bits = mult_8.iter().map(|bit| bit.to_string()).collect::<String>();
let remainder_bits = remainder.iter().map(|bit| bit.to_string()).collect::<String>();
let mult_8 = Self::from_str_radix(&mult_8_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", mult_8_bits)))
})? * 8;
let remainder = Self::from_str_radix(&remainder_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", remainder_bits)))
})?;
Ok(mult_8 + remainder)
}
}
impl Comprezable for u128 {
fn compress(self) -> Result<Compressed, CompressError> {
Err(CompressError::create(CompressError::DataNoSupported(String::new())))
}
fn compress_to_binaries(self, max_num: Option<u128>) -> Result<Compressed, CompressError> {
let max_num = max_num.unwrap() as Self;
if self > max_num {
return Err(CompressError::create(CompressError::Overflow(format!("given: {}, max-num: {}", self,max_num))))
}
let mult_8_bit_size = find_mult_8_bit_size(max_num, 8, 0, 2);
let compressed_binaries = compress_num(self, mult_8_bit_size, 8, 2, 0);
let res = compressed_binaries.iter().map(|&binary| binary as u8).collect::<Vec<u8>>();
Ok(Compressed::Binaries(res))
}
fn max_binaries(max_num: Option<u128>) -> BinaryChunk {
let max_num = max_num.unwrap() as Self;
BinaryChunk::Single(find_mult_8_bit_size(max_num, 8, 0, 2) + 3)
}
fn decompress(_compressed: Compressed) -> Result<u128, DecompressError> {
Err(DecompressError::create(DecompressError::PrimitiveDataErr(String::new())))
}
fn decompress_from_binaries(compressed: &mut Vec<u8>, bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized {
if compressed.len() < bit_size.unwrap() {
return Err(DecompressError::create(DecompressError::WrongBytesLength(format!("Not enough bytes"))))
}
let compressed_binaries = compressed.drain( .. bit_size.unwrap()).collect::<Vec<u8>>();
let split_at = compressed_binaries.len() - 3;
let (mult_8, remainder) = compressed_binaries.split_at(split_at);
let mult_8_bits = mult_8.iter().map(|bit| bit.to_string()).collect::<String>();
let remainder_bits = remainder.iter().map(|bit| bit.to_string()).collect::<String>();
let mult_8 = Self::from_str_radix(&mult_8_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", mult_8_bits)))
})? * 8;
let remainder = Self::from_str_radix(&remainder_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", remainder_bits)))
})?;
Ok(mult_8 + remainder)
}
}
impl Comprezable for i8 {
fn compress(self) -> Result<Compressed, CompressError> {
Err(CompressError::create(CompressError::DataNoSupported(String::new())))
}
fn compress_to_binaries(self, max_num: Option<u128>) -> Result<Compressed, CompressError> {
let max_num = max_num.unwrap() as Self;
if self.abs() > max_num {
return Err(CompressError::create(CompressError::Overflow(format!("given: {}, max-num: {}", self, max_num))))
}
let mult_8_bit_size = find_mult_8_bit_size(max_num.abs(), 8, 0, 2);
let compressed_binaries = compress_num(self.abs(), mult_8_bit_size, 8, 2, 0);
let mut res = compressed_binaries.iter().map(|&binary| binary as u8).collect::<Vec<u8>>();
if self < 0 {
res.insert(0, 0)
} else {
res.insert(0, 1);
}
Ok(Compressed::Binaries(res))
}
fn max_binaries(max_num: Option<u128>) -> BinaryChunk {
let max_num = max_num.unwrap() as Self;
BinaryChunk::Single(find_mult_8_bit_size(max_num.abs(), 8, 0, 2) + 4)
}
fn decompress(_compressed: Compressed) -> Result<i8, DecompressError> {
Err(DecompressError::create(DecompressError::PrimitiveDataErr(String::new())))
}
fn decompress_from_binaries(compressed: &mut Vec<u8>, bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized {
if compressed.len() < bit_size.unwrap() {
return Err(DecompressError::create(DecompressError::WrongBytesLength(format!("Not enough bytes"))))
}
let mut compressed_binaries = compressed.drain( .. bit_size.unwrap()).collect::<Vec<u8>>();
let sign = compressed_binaries.remove(0);
let split_at = compressed_binaries.len() - 3;
let (mult_8, remainder) = compressed_binaries.split_at(split_at);
let mult_8_bits = mult_8.iter().map(|bit| bit.to_string()).collect::<String>();
let remainder_bits = remainder.iter().map(|bit| bit.to_string()).collect::<String>();
let mult_8 = Self::from_str_radix(&mult_8_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", mult_8_bits)))
})? * 8;
let remainder = Self::from_str_radix(&remainder_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", remainder_bits)))
})?;
let mut res = mult_8 + remainder;
match sign {
0 => {
res = res * -1;
},
1 => (),
_ => panic!()
}
Ok(res)
}
}
impl Comprezable for i16 {
fn compress(self) -> Result<Compressed, CompressError> {
Err(CompressError::create(CompressError::DataNoSupported(String::new())))
}
fn compress_to_binaries(self, max_num: Option<u128>) -> Result<Compressed, CompressError> {
let max_num = max_num.unwrap() as Self;
if self.abs() > max_num {
return Err(CompressError::create(CompressError::Overflow(format!("given: {}, max-num: {}", self, max_num))))
}
let mult_8_bit_size = find_mult_8_bit_size(max_num.abs(), 8, 0, 2);
let compressed_binaries = compress_num(self.abs(), mult_8_bit_size, 8, 2, 0);
let mut res = compressed_binaries.iter().map(|&binary| binary as u8).collect::<Vec<u8>>();
if self < 0 {
res.insert(0, 0)
} else {
res.insert(0, 1);
}
Ok(Compressed::Binaries(res))
}
fn max_binaries(max_num: Option<u128>) -> BinaryChunk {
let max_num = max_num.unwrap() as Self;
BinaryChunk::Single(find_mult_8_bit_size(max_num.abs(), 8, 0, 2) + 4)
}
fn decompress(_compressed: Compressed) -> Result<i16, DecompressError> {
Err(DecompressError::create(DecompressError::PrimitiveDataErr(String::new())))
}
fn decompress_from_binaries(compressed: &mut Vec<u8>, bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized {
if compressed.len() < bit_size.unwrap() {
return Err(DecompressError::create(DecompressError::WrongBytesLength(format!("Not enough bytes"))))
}
let mut compressed_binaries = compressed.drain( .. bit_size.unwrap()).collect::<Vec<u8>>();
let sign = compressed_binaries.remove(0);
let split_at = compressed_binaries.len() - 3;
let (mult_8, remainder) = compressed_binaries.split_at(split_at);
let mult_8_bits = mult_8.iter().map(|bit| bit.to_string()).collect::<String>();
let remainder_bits = remainder.iter().map(|bit| bit.to_string()).collect::<String>();
let mult_8 = Self::from_str_radix(&mult_8_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", mult_8_bits)))
})? * 8;
let remainder = Self::from_str_radix(&remainder_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", remainder_bits)))
})?;
let mut res = mult_8 + remainder;
match sign {
0 => {
res = res * -1;
},
1 => (),
_ => panic!()
}
Ok(res)
}
}
impl Comprezable for i32 {
fn compress(self) -> Result<Compressed, CompressError> {
Err(CompressError::create(CompressError::DataNoSupported(String::new())))
}
fn compress_to_binaries(self, max_num: Option<u128>) -> Result<Compressed, CompressError> {
let max_num = max_num.unwrap() as Self;
if self.abs() > max_num {
return Err(CompressError::create(CompressError::Overflow(format!("given: {}, max-num: {}", self, max_num))))
}
let mult_8_bit_size = find_mult_8_bit_size(max_num.abs(), 8, 0, 2);
let compressed_binaries = compress_num(self.abs(), mult_8_bit_size, 8, 2, 0);
let mut res = compressed_binaries.iter().map(|&binary| binary as u8).collect::<Vec<u8>>();
if self < 0 {
res.insert(0, 0)
} else {
res.insert(0, 1);
}
Ok(Compressed::Binaries(res))
}
fn max_binaries(max_num: Option<u128>) -> BinaryChunk {
let max_num = max_num.unwrap() as Self;
BinaryChunk::Single(find_mult_8_bit_size(max_num.abs(), 8, 0, 2) + 4)
}
fn decompress(_compressed: Compressed) -> Result<i32, DecompressError> {
Err(DecompressError::create(DecompressError::PrimitiveDataErr(String::new())))
}
fn decompress_from_binaries(compressed: &mut Vec<u8>, bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized {
if compressed.len() < bit_size.unwrap() {
return Err(DecompressError::create(DecompressError::WrongBytesLength(format!("Not enough bytes"))))
}
let mut compressed_binaries = compressed.drain( .. bit_size.unwrap()).collect::<Vec<u8>>();
let sign = compressed_binaries.remove(0);
let split_at = compressed_binaries.len() - 3;
let (mult_8, remainder) = compressed_binaries.split_at(split_at);
let mult_8_bits = mult_8.iter().map(|bit| bit.to_string()).collect::<String>();
let remainder_bits = remainder.iter().map(|bit| bit.to_string()).collect::<String>();
let mult_8 = Self::from_str_radix(&mult_8_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", mult_8_bits)))
})? * 8;
let remainder = Self::from_str_radix(&remainder_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", remainder_bits)))
})?;
let mut res = mult_8 + remainder;
match sign {
0 => {
res = res * -1;
},
1 => (),
_ => panic!()
}
Ok(res)
}
}
impl Comprezable for i64 {
fn compress(self) -> Result<Compressed, CompressError> {
Err(CompressError::create(CompressError::DataNoSupported(String::new())))
}
fn compress_to_binaries(self, max_num: Option<u128>) -> Result<Compressed, CompressError> {
let max_num = max_num.unwrap() as Self;
if self.abs() > max_num {
return Err(CompressError::create(CompressError::Overflow(format!("given: {}, max-num: {}", self, max_num))))
}
let mult_8_bit_size = find_mult_8_bit_size(max_num.abs(), 8, 0, 2);
let compressed_binaries = compress_num(self.abs(), mult_8_bit_size, 8, 2, 0);
let mut res = compressed_binaries.iter().map(|&binary| binary as u8).collect::<Vec<u8>>();
if self < 0 {
res.insert(0, 0)
} else {
res.insert(0, 1);
}
Ok(Compressed::Binaries(res))
}
fn max_binaries(max_num: Option<u128>) -> BinaryChunk {
let max_num = max_num.unwrap() as Self;
BinaryChunk::Single(find_mult_8_bit_size(max_num.abs(), 8, 0, 2) + 4)
}
fn decompress(_compressed: Compressed) -> Result<i64, DecompressError> {
Err(DecompressError::create(DecompressError::PrimitiveDataErr(String::new())))
}
fn decompress_from_binaries(compressed: &mut Vec<u8>, bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized {
if compressed.len() < bit_size.unwrap() {
return Err(DecompressError::create(DecompressError::WrongBytesLength(format!("Not enough bytes"))))
}
let mut compressed_binaries = compressed.drain( .. bit_size.unwrap()).collect::<Vec<u8>>();
let sign = compressed_binaries.remove(0);
let split_at = compressed_binaries.len() - 3;
let (mult_8, remainder) = compressed_binaries.split_at(split_at);
let mult_8_bits = mult_8.iter().map(|bit| bit.to_string()).collect::<String>();
let remainder_bits = remainder.iter().map(|bit| bit.to_string()).collect::<String>();
let mult_8 = Self::from_str_radix(&mult_8_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", mult_8_bits)))
})? * 8;
let remainder = Self::from_str_radix(&remainder_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", remainder_bits)))
})?;
let mut res = mult_8 + remainder;
match sign {
0 => {
res = res * -1;
},
1 => (),
_ => panic!()
}
Ok(res)
}
}
impl Comprezable for i128 {
fn compress(self) -> Result<Compressed, CompressError> {
Err(CompressError::create(CompressError::DataNoSupported(String::new())))
}
fn compress_to_binaries(self, max_num: Option<u128>) -> Result<Compressed, CompressError> {
let max_num = max_num.unwrap() as Self;
if self.abs() > max_num {
return Err(CompressError::create(CompressError::Overflow(format!("given: {}, max-num: {}", self, max_num))))
}
let mult_8_bit_size = find_mult_8_bit_size(max_num.abs(), 8, 0, 2);
let compressed_binaries = compress_num(self.abs(), mult_8_bit_size, 8, 2, 0);
let mut res = compressed_binaries.iter().map(|&binary| binary as u8).collect::<Vec<u8>>();
if self < 0 {
res.insert(0, 0)
} else {
res.insert(0, 1);
}
Ok(Compressed::Binaries(res))
}
fn max_binaries(max_num: Option<u128>) -> BinaryChunk {
let max_num = max_num.unwrap() as Self;
BinaryChunk::Single(find_mult_8_bit_size(max_num.abs(), 8, 0, 2) + 4)
}
fn decompress(_compressed: Compressed) -> Result<i128, DecompressError> {
Err(DecompressError::create(DecompressError::PrimitiveDataErr(String::new())))
}
fn decompress_from_binaries(compressed: &mut Vec<u8>, bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized {
if compressed.len() < bit_size.unwrap() {
return Err(DecompressError::create(DecompressError::WrongBytesLength(format!("Not enough bytes"))))
}
let mut compressed_binaries = compressed.drain( .. bit_size.unwrap()).collect::<Vec<u8>>();
let sign = compressed_binaries.remove(0);
let split_at = compressed_binaries.len() - 3;
let (mult_8, remainder) = compressed_binaries.split_at(split_at);
let mult_8_bits = mult_8.iter().map(|bit| bit.to_string()).collect::<String>();
let remainder_bits = remainder.iter().map(|bit| bit.to_string()).collect::<String>();
let mult_8 = Self::from_str_radix(&mult_8_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", mult_8_bits)))
})? * 8;
let remainder = Self::from_str_radix(&remainder_bits, 2).map_err(|_| {
DecompressError::create(DecompressError::BinariesToIntErr(format!("Binaries given: {}", remainder_bits)))
})?;
let mut res = mult_8 + remainder;
match sign {
0 => {
res = res * -1;
},
1 => (),
_ => panic!()
}
Ok(res)
}
}
use lz4_flex::{compress_prepend_size, decompress_size_prepended};
impl Comprezable for Vec<u8> {
fn compress(self) -> Result<Compressed, CompressError> {
Err(CompressError::create(CompressError::DataNoSupported(String::new())))
}
fn compress_to_binaries(self, _max_num: Option<u128>) -> Result<Compressed, CompressError> {
let compressed = Compressed::Bytes(compress_prepend_size(self.as_slice()));
let compressed_length = compressed.to_bytes().len();
let compressed_metalength = Compressed::Binaries(compress_metalength_v2(compressed_length));
let res = compressed_metalength.combine(compressed);
Ok(res)
}
fn max_binaries(_max_num: Option<u128>) -> BinaryChunk {
BinaryChunk::Delimeter
}
fn decompress(_compressed: Compressed) -> Result<Self, DecompressError> where Self: Sized {
Err(DecompressError::create(DecompressError::PrimitiveDataErr(String::new())))
}
fn decompress_from_binaries(compressed: &mut Vec<u8>, _bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized {
let mut chunk_metas: Vec<u8> = vec![];
loop {
if compressed.len() < 8 {
return Err(DecompressError::WrongBytesLength(format!("Not enough bytes to calculate the metalength of compressed vector")))
}
let delimeter = compressed.remove(0);
match delimeter {
0 => {
chunk_metas.extend(compressed.drain(0 .. 7));
},
1 => {
chunk_metas.extend(compressed.drain(0 .. 7));
break
},
_ => {
panic!()
}
};
}
let chunk_metas = chunk_metas
.into_iter()
.map(|bit| bit.to_string())
.collect::<String>();
let meta = u128::from_str_radix(&chunk_metas, 2).unwrap();
let length = compressed.len() as u128;
if length < meta * 8 {
return Err(DecompressError::WrongBytesLength(format!("length of compressed bytes is shorter than meta-length of compressed vector, AKA meta-length out of bound")))
}
let mut res_binaries: Vec<u8> = vec![];
for _ in 1 ..= meta {
res_binaries.extend(compressed.drain(0 .. 8));
}
let res_binaries = Compressed::Binaries(res_binaries).to_bytes();
Ok(decompress_size_prepended(res_binaries.as_slice()).unwrap())
}
}
use std::fmt::Debug;
impl<T: Comprezable + Clone + Debug> Comprezable for Vec<T> {
fn compress(self) -> Result<Compressed, CompressError> {
Err(CompressError::create(CompressError::DataNoSupported(String::new())))
}
fn compress_to_binaries(self, max_num: Option<u128>) -> Result<Compressed, CompressError> {
let mut all_compressed = Compressed::new();
for element in self {
let compressed = element.compress_to_binaries(max_num)?;
all_compressed = all_compressed.combine(compressed);
}
let all_compressed = Compressed::Bytes(all_compressed.to_bytes());
let len = all_compressed.to_bytes().len();
let compressed_metalength = Compressed::Binaries(compress_metalength_v2(len));
let res = compressed_metalength.combine(all_compressed);
Ok(res)
}
fn max_binaries(max_num: Option<u128>) -> BinaryChunk {
let binary_chunk = T::max_binaries(max_num);
binary_chunk
}
fn decompress(_compressed: Compressed) -> Result<Self, DecompressError> where Self: Sized {
Err(DecompressError::create(DecompressError::PrimitiveDataErr(String::new())))
}
fn decompress_from_binaries(compressed: &mut Vec<u8>, bit_size: Option<usize>) -> Result<Self, DecompressError> where Self:Sized {
let size = calc_delimeter_size(compressed, 7)?;
let mut res_binaries: Vec<u8> = vec![];
for _ in 1 ..= size {
res_binaries.extend(compressed.drain(0 .. 8));
}
let mut res: Vec<T> = vec![];
loop {
match T::decompress_from_binaries(&mut res_binaries, bit_size) {
Ok(t) => {
res.push(t);
},
Err(_) => {
break
}
}
}
Ok(res)
}
}
pub fn calc_delimeter_size(compressed: &mut Vec<u8>, delimeter_size: usize) -> Result<u128, DecompressError> {
let mut chunk_metas: Vec<u8> = vec![];
loop {
if compressed.len() < delimeter_size + 1 {
return Err(DecompressError::WrongBytesLength(format!("Not enough bytes to calculate the metalength of compressed vector")))
}
let delimeter = compressed.remove(0);
match delimeter {
0 => {
chunk_metas.extend(compressed.drain(0 .. delimeter_size));
},
1 => {
chunk_metas.extend(compressed.drain(0 .. delimeter_size));
break
},
_ => {
panic!()
}
};
}
let chunk_metas = chunk_metas
.into_iter()
.map(|bit| bit.to_string())
.collect::<String>();
let meta = u128::from_str_radix(&chunk_metas, 2).unwrap();
Ok(meta)
}
pub fn comprez_enum_val<T: Comprezable + Clone + Debug>(val: Option<T>, n: usize, max_num: Option<u128>) -> Result<Compressed, CompressError> {
let n = format!("{:b}", n);
let meta = n.chars().map(|c| c.to_digit(2).unwrap() as u8).rev().collect::<Vec<u8>>();
let mut meta = meta.chunks(4).map(|chunk| {
let mut temp = chunk.to_vec();
let mut count = temp.len();
while count < 4 {
temp.push(0);
count += 1;
}
temp.push(0);
temp.reverse();
temp
}).collect::<Vec<Vec<u8>>>();
meta.reverse();
meta.last_mut().unwrap()[0] = 1;
let meta = meta.into_iter().flatten().collect::<Vec<u8>>();
let meta = Compressed::Binaries(meta);
match val {
Some(t) => {
let compressed = t.compress_to_binaries(max_num)?;
let compressed = meta.combine(compressed);
Ok(compressed)
},
None => {
Ok(meta)
}
}
}
fn compress_num<N: Ord + std::ops::Div<Output = N> + std::ops::Rem<Output = N> + Copy>(num: N, mult_8_bit_size: usize, divider: N, r: N, zero: N) -> Vec<N> {
let mult_8 = num / divider; let remainder = num % divider;
let mut mult_8_bit = encode(mult_8, r, mult_8_bit_size, zero); let remainder_bit = encode(remainder, r, 3, zero);
mult_8_bit.extend(remainder_bit);
mult_8_bit
}
fn compress_metalength_v2(num: usize) -> Vec<u8> {
let mut binaries = encode(num, 2, 0, 0).iter().map(|&bit| bit as u8).collect::<Vec<u8>>();
binaries.reverse();
let mut reversed_chunked_meta = binaries.chunks(7).map(|chunk| {
let mut temp = chunk.to_vec();
while temp.len() < 7 {
temp.push(0);
}
temp.push(0);
temp.reverse();
temp
}).collect::<Vec<Vec<u8>>>();
reversed_chunked_meta.reverse();
reversed_chunked_meta.last_mut()
.ok_or(CompressError::create(CompressError::MetaForVecErr(String::new()))).unwrap()
[0] = 1;
let res = reversed_chunked_meta.into_iter().flatten().collect::<Vec<u8>>();
res
}
fn encode<N: Ord + std::ops::Div<Output = N> + std::ops::Rem<Output = N> + Copy>(mut num: N, r: N, bit_size: usize, zero: N) -> Vec<N> {
let mut res = vec![];
while num != zero {
let remainder = num % r;
num = num / r;
res.push(remainder);
}
res.reverse();
while res.len() < bit_size {
res.insert(0, zero);
}
res
}
fn find_mult_8_bit_size<N: Ord + std::ops::Div<Output = N> + Copy>(mut num: N, divider: N, zero: N, r: N) -> usize {
num = num / divider; let mut res = 0;
while num != zero { num = num / r; res += 1;
}
res
}