Is it
possible for the structure to be parametrized on smart pointer?
Not without higher kinded types (which eventually we do want--so the
answer is "not yet").
I've been thinking about that a bit more and I think it might be
possible to support different reference types without higher-kinded
types. We can define a `Reference` trait that is then implemented for
`Rc`, `Arc` and what have you. Something like:
trait Reference<T> : Clone {
fn borrow<'a>(&'a self) -> &'a T;
}
If we also want to create references without knowing their concrete
type, we also need a trait for creating them:
trait ReferenceFactory<T, TRef: Reference<T>> {
fn create_reference(&self, val: T) -> TRef;
}
And then we can define a container type, using the generic reference type:
struct Container<T, TRef, TRefFactory> {
items: ~[TRef],
reference_factory: TRefFactory
}
It contains a `ReferenceFactory` value that is used to create
`Reference` instances when the container needs one (see the `add` method
below):
impl<
T,
TRef: Reference<T>,
TRefFactory: ReferenceFactory<T, TRef>
>
Container<T, TRef, TRefFactory> {
pub fn create(factory: TRefFactory) -> Container<T, TRef,
TRefFactory> {
Container {
reference_factory: factory,
items: ~[]
}
}
pub fn add(&mut self, val: T) {
self.items.push(self.reference_factory.create_reference(val));
}
}
This setup is a bit roundabout but it should get the job done. Of
course, I may have overlooked something but at least rustc swallows the
above code without complaint ;)
If we could call static methods on type parameters, the factory
functionality could be moved to the `Reference` trait:
trait Reference<T> : Clone {
fn borrow<'a>(&'a self) -> &'a T;
fn new(value: T) -> Self;
}
// Now using the static `new` method instead of the `ReferenceFactory` trait
pub fn add(&mut self, val: T) {
self.items.push(TRef::new(val));
}
With this, the code would actually be of acceptable complexity in my eyes.
-Michael
_______________________________________________
Rust-dev mailing list
[email protected]
https://mail.mozilla.org/listinfo/rust-dev