use std::cmp::Ordering;
use std::ops::{Bound, Range, RangeBounds};
#[cfg(feature = "pool")]
pub(crate) use refpool::{PoolClone, PoolDefault};
pub(crate) use crate::fakepool::{Pool, PoolClone, PoolDefault};
#[cfg(feature = "triomphe")]
pub(crate) type Ref<A> = ::triomphe::Arc<A>;
#[cfg(not(feature = "triomphe"))]
pub(crate) type Ref<A> = std::sync::Arc<A>;
#[cfg(feature = "triomphe")]
pub(crate) use crate::fakepool::triomphe::Arc as PoolRef;
#[cfg(not(feature = "triomphe"))]
pub(crate) use crate::fakepool::Arc as PoolRef;
pub(crate) fn clone_ref<A>(r: Ref<A>) -> A
where
A: Clone,
{
Ref::try_unwrap(r).unwrap_or_else(|r| (*r).clone())
}
#[derive(Clone, Copy, PartialEq, Eq, Debug)]
pub(crate) enum Side {
Left,
Right,
}
#[allow(dead_code)]
pub(crate) fn linear_search_by<'a, A, I, F>(iterable: I, mut cmp: F) -> Result<usize, usize>
where
A: 'a,
I: IntoIterator<Item = &'a A>,
F: FnMut(&A) -> Ordering,
{
let mut pos = 0;
for value in iterable {
match cmp(value) {
Ordering::Equal => return Ok(pos),
Ordering::Greater => return Err(pos),
Ordering::Less => {}
}
pos += 1;
}
Err(pos)
}
pub(crate) fn to_range<R>(range: &R, right_unbounded: usize) -> Range<usize>
where
R: RangeBounds<usize>,
{
let start_index = match range.start_bound() {
Bound::Included(i) => *i,
Bound::Excluded(i) => *i + 1,
Bound::Unbounded => 0,
};
let end_index = match range.end_bound() {
Bound::Included(i) => *i + 1,
Bound::Excluded(i) => *i,
Bound::Unbounded => right_unbounded,
};
start_index..end_index
}
macro_rules! def_pool {
($name:ident<$($arg:tt),*>, $pooltype:ty) => {
pub struct $name<$($arg,)*>(Pool<$pooltype>);
impl<$($arg,)*> $name<$($arg,)*> {
pub fn new(size: usize) -> Self {
Self(Pool::new(size))
}
pub fn fill(&self) {
self.0.fill();
}
pub fn pool_size(&self) -> usize {
self.0.get_pool_size()
}
}
impl<$($arg,)*> Default for $name<$($arg,)*> {
fn default() -> Self {
Self::new($crate::config::POOL_SIZE)
}
}
impl<$($arg,)*> Clone for $name<$($arg,)*> {
fn clone(&self) -> Self {
Self(self.0.clone())
}
}
};
}
#[cfg(test)]
macro_rules! assert_covariant {
($name:ident<$($gen:tt),*> in $param:ident) => {
#[allow(unused_assignments, unused_variables)]
const _: () = {
type Tmp<$param> = $name<$($gen),*>;
fn assign<'a, 'b: 'a>(src: Tmp<&'b i32>, mut dst: Tmp<&'a i32>) {
dst = src;
}
};
}
}