[−][src]Trait structural::enums::VariantCount
For querying the amount of variants of an enum.
Safety
Count must be a TStr
with the amount of enum variants written in decimal.
For example:TS!(9)
would be used for an enum with 9 variants.
Implementors who specify fewer variants than the enum actually has
may result in undefined behavior when the enum is matched in the switch
macro.
Example
This example demonstrates using VariantCount
as a bound to
restrict a pre-existing structural alias.
use structural::{Structural,TS,structural_alias,switch}; use structural::enums::VariantCount; { // Enum assert_eq!( nonexhaustive(Enum::Foo), Some(0) ); assert_eq!( exhaustive_a(Enum::Foo), 0 ); assert_eq!( exhaustive_b(Enum::Foo), 0 ); let bar=Enum::Bar(0); assert_eq!( nonexhaustive(bar.clone()), Some(1) ); assert_eq!( exhaustive_a(bar.clone()), 1 ); assert_eq!( exhaustive_b(bar), 1 ); let baz=Enum::Baz{wha:"whoah".into()}; assert_eq!( nonexhaustive(baz.clone()), Some(2) ); assert_eq!( exhaustive_a(baz.clone()), 2 ); assert_eq!( exhaustive_b(baz), 2 ); } { // HyperEnum: // This enum has a superset of the variants required by `Ternary`. // The commented out lines below don't compile // because the `exhaustive_*` functions require the enum to only have // the `Foo`,`Bar`,and `Baz` variants assert_eq!( nonexhaustive(HyperEnum::Foo), Some(0) ); // assert_eq!( exhaustive_a(HyperEnum::Foo), 0 ); // assert_eq!( exhaustive_b(HyperEnum::Foo), 0 ); assert_eq!( nonexhaustive(HyperEnum::Bar), Some(1) ); // assert_eq!( exhaustive_a(HyperEnum::Bar), 1 ); // assert_eq!( exhaustive_b(HyperEnum::Bar), 1 ); assert_eq!( nonexhaustive(HyperEnum::Baz), Some(2) ); // assert_eq!( exhaustive_a(HyperEnum::Baz), 2 ); // assert_eq!( exhaustive_b(HyperEnum::Baz), 2 ); assert_eq!( nonexhaustive(HyperEnum::Boom), None ); } // This function returns the index of the current variant of the enum, // but because `Ternary` is a nonexhaustive structural trait, // it returns None to handle the case where the enum is // none of the three variants. // fn nonexhaustive<T>(this: T)->Option<u8> where T: Ternary, { // The VariantCount bound allow this switch to be exhaustive. switch!{this; Foo=>Some(0), Bar=>Some(1), Baz=>Some(2), // This branch is required, // because `Ternary` doesn't require the enum to have exactly 3 variants _=>None, } } // This function returns the index of the current variant of the enum, fn exhaustive_a<T>(this: T)->u8 where T: Ternary + VariantCount<Count=TS!(3)>, { // The VariantCount bound allow this switch to be exhaustive. switch!{this; Foo=>0, Bar=>1, Baz=>2, } } fn exhaustive_b<T>(this: T)->u8 where // `TernaryExhaustive` is equivalent to `Ternary + VariantCount<Count=TS!(3)>`. // // You would use a `+ VariantCount<Count=_>` bound if all of thse happen: // - The structural alias came from somewhere else. // - It's a nonexhaustive structural alias. // - You don't want to do declare another alias,like `TernarySuper`. T: TernaryExhaustive { exhaustive_a(this) } structural_alias!{ // `#[struc(and_exhaustive_enum(...))]` generates a subtrait with //`VariantCount<Count=TS!($variant_count)>` as an additional bound // (the `$variant_count` stands for the number of variants in the structural alias) #[struc(and_exhaustive_enum(name="TernaryExhaustive"))] pub trait Ternary{ Foo, Bar, Baz, } pub trait TernarySuper: Ternary + VariantCount<Count=TS!(3)> {} } #[derive(Structural,Clone)] enum Enum{ Foo, Bar(u32), Baz{wha:String}, } #[derive(Structural,Clone)] enum HyperEnum{ Foo, Bar, Baz, Boom, }
Associated Types
type Count: IsTStr
This is a TStr (eg:TS!(3)
)
representing the amount of variants of the enum.
This is a type instead of a &'static str
constant so that
it can be a supertrait of dyn-compatible traits.
Implementations on Foreign Types
impl<T> VariantCount for Option<T>
[src]
impl<T, E> VariantCount for Result<T, E>
[src]
impl<T> VariantCount for ManuallyDrop<T> where
T: VariantCount,
[src]
T: VariantCount,
type Count = VariantCountOut<T>
impl<P> VariantCount for Pin<P> where
P::Target: VariantCount,
P: Deref,
P::Target: Sized,
[src]
P::Target: VariantCount,
P: Deref,
P::Target: Sized,
type Count = VariantCountOut<P::Target>
impl<T> VariantCount for Arc<T> where
T: VariantCount,
T: ?Sized,
[src]
T: VariantCount,
T: ?Sized,
type Count = VariantCountOut<T>
impl<T> VariantCount for Rc<T> where
T: VariantCount,
T: ?Sized,
[src]
T: VariantCount,
T: ?Sized,
type Count = VariantCountOut<T>
impl<T> VariantCount for Box<T> where
T: VariantCount,
T: ?Sized,
[src]
T: VariantCount,
T: ?Sized,
type Count = VariantCountOut<T>
impl<'a, T> VariantCount for &'a T where
T: VariantCount,
T: ?Sized,
[src]
T: VariantCount,
T: ?Sized,
type Count = VariantCountOut<T>
impl<'a, T> VariantCount for &'a mut T where
T: VariantCount,
T: 'a + ?Sized,
[src]
T: VariantCount,
T: 'a + ?Sized,
type Count = VariantCountOut<T>
Implementors
impl<T> VariantCount for FieldCloner<T> where
T: VariantCount,
[src]
T: VariantCount,
type Count = VariantCountOut<T>
impl<T> VariantCount for StrucWrapper<T> where
T: VariantCount,
[src]
T: VariantCount,