rhaiscript / book

The Rhai Book.
https://rhai.rs/book
22 stars 22 forks source link

Carification needed : Defining functions from rust and avoiding expensinve clones #16

Open nicoxxl opened 2 years ago

nicoxxl commented 2 years ago

Hello,

I am using Rhai as a scripting language for a small project of mine which involve expensive to clone/large structures.

As I would love to avoid cloning and Rhai does not support references except for the first parameter, I am unsure about the correct course of actions.

It is mentioned but it might be good to add some examples, clarifications and/or best practices around this issue.

schungx commented 2 years ago

Yes, probably a dedicated topic might be in order. I'll see to that.

The actual reason behind the restriction of only having the first parameter being a reference is specialization, which is a feature that is not yet stabilized in Rust.

The suggestion is:

1) You can only have one reference for native Rust functions: the first parameter. So make sure that all the large structures are passed there. If you have more than one large type, consider putting them all in a Map and then passing the Map. Otherwise, you'd be forced to clone at least some of those types (look at the actual implementation of the array functions; some cloning is currently unavoidable).

2) For script functions, the reference is bound to this. Therefore, make sure you design your API such that the large types are used as this. Again, using a Map is an effective strategy to group a number of large types as one.

3) Otherwise, you can use Rc<RefCell<T>> to wrap the large types which makes them shared and clonable. This way, you don't have to worry about copying them.

It is rare that an API would require working with more than 1 parameter that contains an expensive-to-clone type. If such a situation arises, put them all in a Map is a prudent strategy.