pointers - Cannot move out of borrowed content when borrowing a generic type -
i have program more or less looks this
struct test<t> { vec: vec<t> } impl<t> test<t> { fn get_first(&self) -> &t { &self.vec[0] } fn do_something_with_x(&self, x: t) { // irrelevant } } fn main() { let t = test { vec: vec![1i32, 2, 3] }; let x = t.get_first(); t.do_something_with_x(*x); }
basically, call method on struct test
borrows value. call method on same struct, passing obtained value.
this example works fine. now, when make content of main
generic, doesn't work anymore.
fn generic_main<t>(t: test<t>) { let x = t.get_first(); t.do_something_with_x(*x); }
then following error:
error: cannot move out of borrowed content
src/main.rs:14 let raw_x = *x;
i'm not sure why happening. can explain me why test<i32>
isn't borrowed when calling get_first
while test<t>
is?
the short answer i32
implements copy
trait, t
not. if use fn generic_main<t: copy>(t: test<t>)
, immediate problem fixed.
the longer answer copy
special trait means values can copied copying bits. types i32
implement copy
. types string
not implement copy
because, example, requires heap allocation. if copied string
copying bits, you'd end 2 string
values pointing same chunk of memory. not (it's unsafe!).
therefore, giving t
copy
bound quite restrictive. less restrictive bound t: clone
. clone
trait similar copy
(in copies values), it's done more "copying bits." example, string
type implement clone
creating new heap allocation underlying memory.
this requires change how generic_main
written:
fn generic_main<t: clone>(t: test<t>) { let x = t.get_first(); t.do_something_with_x(x.clone()); }
alternatively, if don't want have either clone
or copy
bounds, change do_something_with_x
method take reference t
rather owned t
:
impl<t> test<t> { // other methods elided fn do_something_with_x(&self, x: &t) { // irrelevant } }
and generic_main
stays same, except don't dereference x
:
fn generic_main<t>(t: test<t>) { let x = t.get_first(); t.do_something_with_x(x); }
you can read more copy
in docs. there nice examples, including how implement copy
own types.
Comments
Post a Comment