Hi, So traits seem to be quite similar to Haskell's classes, being also used for parametric polymorphism. Now, Haskell classes are usually implemented using runtime dictionary passing. In general, code cannot be specialized for every function call, since there may be an unbounded number of instances generated for it, as is explained in this reddit answer: http://www.reddit.com/r/haskell/comments/1ar642/what_type_of_binding_does_haskell_use/c94o2ju
Knowing that Rust implements traits using monomorphization of code (much like C++ templates), I was curious about how it handled such cases, and tried this: struct W<T> { f: T } trait Show { fn show(&self) -> int; } impl Show for int { fn show(&self) -> int { 666 } } impl<T:Show> Show for W<T> { fn show(&self) -> int { self.f.show()+1 } } impl<T:Clone> Clone for W<T> { fn clone(&self) -> W<T> { W{f:self.f.clone()} } } fn foo<S:Show+Clone>(s: &S, n: int) { let w = W{f:s.clone()}; if n > 0 { foo(&w, n-1); } } fn main() { foo(&W{f:42i},42); } It gave me an "error: reached the recursion limit during monomorphization", which... well, that's a possible solution :) I'm not sure whether this is a big problem in practice, but I was wondering if it would be possible to switch to some runtime mechanism in cases like this. Maybe we could make a special version of every generic functions, that takes a dictionary at runtime and that would be able to handle types unknown at compile-time. We would switch to this version when monomorphization does not work. It could also allow dynamic linking of libraries with generic functions, or it could be a way to compile some programs (or some parts of programs) much faster. I was thinking about, for example, an IDE where generic function calls to types defined inside the files currently being edited use their dynamic version, so that recompile times can be virtually inexistent (like Java). On the other hand, the release build would of course monomorphize as much as possible to make the perf optimal. Now the question is: would this conform to the current semantic of monomorphization? Do special things happen during monomorphization that cannot be reproduced at runtime? This is the case in C++ (and one of the reasons why C++ templates are so "bad"). Is it the case in Rust, which should already have all the required info (type bounds) before monomorphization? I apologize if this has already been discussed. I could not find many satisfying answers by googling. Cheers, LP.
_______________________________________________ Rust-dev mailing list Rust-dev@mozilla.org https://mail.mozilla.org/listinfo/rust-dev