There's a library which provides a generic function and some implementations to work with:
#include <iostream>
namespace lib {
struct Impl1 {};
struct Impl2 {};
void process(Impl1) { std::cout << 1; }
void process(Impl2) { std::cout << 2; }
template<typename T> void generalize(T t) { process(t); }
}
I want to extend it via external code. Here's how C++ allows to do it:
#include <lib.h> // the previous snippet
namespace client {
struct Impl3 {};
void process(Impl3) { std::cout << 3; }
}
int main() { // test
lib::generalize(client::Impl3{}); // it couts 3
}
Note: lib
's code knows nothing about the client
's one and performs no dynamic dispatch nonetheless. How can I achieve the same in my Rust code? (If I can't, is anything alike planned?)
Sure, this is exactly what traits are for:
pub mod lib {
pub trait Impl {
fn process(&self);
}
pub struct Impl1 {}
pub struct Impl2 {}
impl Impl for Impl1 {
fn process(&self) {
println!("1");
}
}
impl Impl for Impl2 {
fn process(&self) {
println!("2");
}
}
pub fn generalize<T: Impl>(t: T) {
t.process();
}
}
mod client {
pub struct Impl3 {}
impl super::lib::Impl for Impl3 {
fn process(&self) {
println!("3");
}
}
}
fn main() {
lib::generalize(client::Impl3 {});
}
See it on the Playground.