match_any

Provides a declarative macro, that matches an expression to any of the patterns and executes the same expression arm for any match.

This macro allows you to use the same expression arm for different types by creating the same match arm for each of the patterns separated by |. A standard match statement only allows such patterns for the same type:

rust let result: Result<i64, i32> = Err(42); let int: i64 = match result { Ok(i) | Err(i) => i.into() }; // does not compile!

rust let result: Result<i64, i32> = Err(42); let int: i64 = match_any!(result, Ok(i) | Err(i) => i.into()); // compiles just fine assert_eq!(int, 42);

Examples

```rust use matchany::matchany;

enum Id { U8(u8), I16(i16), I32(i32) } use Id::*;

let id = Id::I16(-2); let id: i32 = matchany!(id, U8(x) | I16(x) | I32(x) => x.into()); asserteq!(id, -2); ```

Enum Dispatch

Similarly to the enumdispatch crate, this macro can be used to implement "enum dispatch" as an alternative to dynamic dispatch. The major difference between the enumdispatch crate and this macro is, that enumdispatch provides a _procedural macro, while this is a declarative macro. This allows enumdispatch to reduce the boilerplate code a lot more than matchany. However IDE support should be a bit better with match_any.

Enum Dispatch Example

```rust use matchany::matchany;

trait IntId { fn int_id(&self) -> i32; }

impl IntId for u64 { fn int_id(&self) -> i32 { 64 } }

impl IntId for u32 { fn int_id(&self) -> i32 { 32 } }

enum IntIdKind { U64(u64), U32(u32) }

impl IntId for IntIdKind { fn intid(&self) -> i32 { use IntIdKind::*; matchany!(self, U64(i) | U32(i) => i.int_id()) } }

let intidkind = IntIdKind::U32(0); asserteq!(intidkind.intid(), 32); // enum dispatch let intidbox: Box = Box::new(0u32); asserteq!(intidbox.int_id(), 32); // dynamic dispatch ```