use batch_impl::batch_impl;
use std::collections::HashMap;
#[batch_impl(<T> Cloned<T> Vec<T> {
fn get(&self) -> T {
self[0].clone()
}
})]
trait Cloned<T: Clone> {
fn get(&self) -> T;
}
trait SupA {}
trait SupB: SupA {}
struct SupS;
impl SupA for SupS {}
impl SupB for SupS {}
#[batch_impl(<T: SupB> Inherit<T> ())]
trait Inherit<T: SupA> {}
#[batch_impl(<'a, T> Lifetime<'a, T> ())]
trait Lifetime<'a, T: 'a> {}
#[batch_impl(<'b, T: 'b> LifetimeRenamed<'b, T> ())]
trait LifetimeRenamed<'a, T: 'a> {}
#[batch_impl(<T> StaticT<T> ())]
trait StaticT<T: 'static> {}
#[batch_impl(<'a, T> Mix<'a, T> ())]
trait Mix<'a, T: Clone + 'a> {}
#[batch_impl(<T: SupB, U> PartialBound<T, U> ())]
trait PartialBound<T: SupA, U: SupA> {}
#[batch_impl(<T, U: SupB> PartialBound2<T, U> ())]
trait PartialBound2<T: SupA, U: SupA> {}
impl SupA for i32 {}
#[test]
fn trait_bound_inherit() {
let v: Vec<i32> = vec![42];
assert_eq!(v.get(), 42);
fn check<T: Inherit<SupS>>() {}
check::<()>();
fn check2<T: Lifetime<'static, ()>>() {}
check2::<()>();
fn check2r<T: LifetimeRenamed<'static, ()>>() {}
check2r::<()>();
fn check3<T: StaticT<()>>() {}
check3::<()>();
fn check4<T: Mix<'static, ()>>() {}
check4::<()>();
fn check_p<T: PartialBound<SupS, i32>>() {}
check_p::<()>();
fn check_p2<T: PartialBound2<i32, SupS>>() {}
check_p2::<()>();
}
#[batch_impl(EmptyGenA<> ())]
trait EmptyGenA<T: Clone> {}
#[batch_impl(EmptyGenB<> ())]
trait EmptyGenB<'a, T: 'a> {}
#[batch_impl(EmptyGenC<> Vec<T>)]
trait EmptyGenC<T> {}
#[batch_impl(AssocGen<Item=T> ())]
trait AssocGen<T: Clone> {
type Item;
}
#[batch_impl(AssocGen2<First=T, Second=U> ())]
trait AssocGen2<'a, T: Clone + 'a, U: Ord> {
type First;
type Second;
}
#[test]
fn empty_trait_generics() {
fn check_a<T: EmptyGenA<i32>>() {}
check_a::<()>();
fn check_b<T: EmptyGenB<'static, ()>>() {}
check_b::<()>();
fn check_c<T: EmptyGenC<i32>>() {}
check_c::<Vec<i32>>();
fn check_d<T: AssocGen<i32, Item = i32>>() {}
check_d::<()>();
fn check_e<T: AssocGen2<'static, i32, u32, First = i32, Second = u32>>() {}
check_e::<()>();
}
#[batch_impl(<T> WhereCloned<T> Vec<T> {
fn wget(&self) -> T {
self[0].clone()
}
})]
trait WhereCloned<T>
where
T: Clone,
{
fn wget(&self) -> T;
}
#[batch_impl(<T> WhereBoth<T> ())]
trait WhereBoth<T: Clone>
where
T: Ord,
{
}
#[batch_impl(<'a, T> WhereLifetime<'a, T> ())]
trait WhereLifetime<'a, T>
where
T: 'a,
{
}
#[batch_impl(<T> WhereGen<T> ())]
trait WhereGen<T: Clone>
where
T: IntoIterator,
T::Item: Clone,
{
}
#[batch_impl(WhereGen2<> ())]
trait WhereGen2<T: Clone>
where
T: IntoIterator,
T::Item: Clone,
{
}
trait HasB {
type B;
}
trait OtherTrait {}
struct S;
impl HasB for S {
type B = u8;
}
impl OtherTrait for u8 {}
#[batch_impl(<A> ProjAssoc<A, u8> ())]
trait ProjAssoc<A, B>
where
A: HasB,
A::B: OtherTrait,
{
}
#[batch_impl(WhereArr<> ())]
trait WhereArr<T, const N: usize>
where
[T; N]: Sized,
{
}
trait HasB2 {
type B;
}
struct S2;
impl HasB2 for S2 {
type B = u8;
}
#[batch_impl(Deep<> ())]
trait Deep<T, U>
where
U: HasB2,
Vec<(T, <U as HasB2>::B)>: Sized,
{
}
trait TupleT {
type Assoc;
}
trait TupleT2 {}
impl TupleT for u8 {
type Assoc = u8;
}
impl TupleT2 for (u8, u8) {}
#[batch_impl(TuplePred<> ())]
trait TuplePred<A, B>
where
A: TupleT,
(A, B): TupleT2,
{
}
#[batch_impl(FnType<> ())]
trait FnType<A, B>
where
fn(A) -> B: Sized,
{
}
#[batch_impl(RefPred<> ())]
trait RefPred<'a, T>
where
T: 'a,
&'a T: Sized,
{
}
#[batch_impl(<T> ListPred2<T> [Vec<T>, <U> HashMap<T, U>])]
trait ListPred2<T>
where
T: IntoIterator,
T::Item: Clone,
{
}
#[test]
fn trait_where_clause_inherit() {
let v: Vec<i32> = vec![42];
assert_eq!(v.wget(), 42);
fn check_b<T: WhereBoth<i32>>() {}
check_b::<()>();
fn check_l<T: WhereLifetime<'static, ()>>() {}
check_l::<()>();
fn check_g<T: WhereGen<Vec<i32>>>() {}
check_g::<()>();
fn check_g2<T: WhereGen2<Vec<i32>>>() {}
check_g2::<()>();
fn check_p<T: ProjAssoc<S, u8>>() {}
check_p::<()>();
fn check_a<T: WhereArr<u8, 4>>() {}
check_a::<()>();
fn check_d<T: Deep<S2, S2>>() {}
check_d::<()>();
fn check_t<T: TuplePred<u8, u8>>() {}
check_t::<()>();
fn check_f<T: FnType<u8, u8>>() {}
check_f::<()>();
fn check_r<T: RefPred<'static, u8>>() {}
check_r::<()>();
fn check_lp<T: ListPred2<Vec<i32>>>() {}
check_lp::<Vec<Vec<i32>>>();
check_lp::<HashMap<Vec<i32>, i32>>();
}