How to solve "temporary value dropped while borrowed"

hi everyone, I'm trying to learn rust on my free days.I am a js developer.In rust I'm trying to create a component based UI template.This is the minimum example I can reproduce in Rust playground.

https://play.rust-lang.org/?version=stable&mode=debug&edition=2018&gist=a2f28dba1ef2ae3461d8d79a0f44f3da

In javascript, this can be created easily, but in rust, many things are different.

I already know that rust doesn't allow you to do certain things. You have to organize the code in a different way.

I have a vector of enums. I also want to add components that will return a new set of vectors.The component returns a vector from a member function that is not a reference.

let _new_children = match new_view.unwrap() {
    View::View(children) => children, // reference &Vec<View>
    View::Render(ref component) => component.render(), // struct Vec<View>
};

let _new_children = match new_view.unwrap() {
    View::View(children) => children,
    View::Render(ref component) => &component.render(), //  temporary value dropped while borrowed
};

How can I solve this problem, do I need to rewrite the way functions check the difference between two vectors (itertools has a zip_longest method, which I also use)

Thank you in advance

You can do this:

let render_out;
let new_children = match new_view.unwrap() {
    View::View(children) => children,
    View::Render(ref component) => {
        render_out = component.render();
        &render_out
    }
};

This ensures the returned vector is kept alive for long enough to last after the match.

4 Likes

Hey,
I'm still somewhat of a beginner, but I think I can help you with this one.
Your problem is, that &component.render() creates a new Vec but that newly created vector only lives inside the match block.
That's why the compiler is telling you that "the temporary value is dropped".

So for example here:

let _new_children = match new_view.unwrap() {
    View::View(children) => children,
    View::Render(ref component) => &component.render(), //  temporary value dropped while borrowed
};

you are trying to make _new children store a reference (&) to the Vec created by component.render(). But this result only lives inside the second match arm ( View::Render(ref component), so you can not create a reference outside of the match block, because the new vector would already be gone.

I wrote a working version of your code using highly nested match blocks to illustrate what you could do.

I really hope this somewhat clarifies your problem.

Best regards!

https://play.rust-lang.org/?version=stable&mode=debug&edition=2018&gist=71e6181fda2b1ef479ce6d7a1ec6cd6f

2 Likes

I guess @alice was faster with this one :wink:

Thank You very much

This topic was automatically closed 90 days after the last reply. New replies are no longer allowed.