function - How do you return non-copyable types? -


i trying understand how return non-primitives (i.e. types not implement copy). if return i32, function creates new value in memory copy of return value, can used outside scope of function. if return type doesn't implement copy, not this, , ownership errors.

i have tried using box create values on heap caller can take ownership of return value, doesn't seem work either.

perhaps approaching in wrong manner using same coding style use in c# or other languages, functions return values, rather passing in object reference parameter , mutating it, can indicate ownership in rust.

the following code examples fails compilation. believe issue within iterator closure, have included entire function in case not seeing something.

pub fn get_files(path: &path) -> vec<&path> {        let contents = fs::walk_dir(path);         match contents {            ok(c) => c.filter_map(|i| { match {                    ok(d) => {                         let val = d.path();                        let p = val.as_path();                        some(p)                    },                    err(_) => none } })                .collect(),            err(e) => panic!("an error occurred getting files {:?}: {}", pa     th, e)        }   } 

the compiler gives following error (i have removed line numbers , extraneous text):

error: `val` not live long enough                      let p = val.as_path();                                             ^~~ in expansion of closure expansion expansion site reference must valid anonymous lifetime #1 defined on block... ...but borrowed value valid block suffix following statement                      let val = d.path();                      let p = val.as_path();                      some(p)                  }, 

you return value by... returning it. however, signature shows trying return reference value. can't when object dropped @ end of block because reference become invalid.

in case, i'd write like

#![feature(fs_walk)]  use std::fs; use std::path::{path, pathbuf};  fn get_files(path: &path) -> vec<pathbuf> {      let contents = fs::walk_dir(path).unwrap();      contents.filter_map(|i| {         i.ok().map(|p| p.path())     }).collect() }  fn main() {     f in get_files(path::new("/etc")) {         println!("{:?}", f);     } } 

the main thing function returns vec<pathbuf> — collection of type owns path, , more references else's memory.

in code, let p = val.as_path(). here, val pathbuf. call as_path, defined as: fn as_path(&self) -> &path. means given reference pathbuf, can reference path that live long pathbuf will. however, trying keep reference around longer vec exist, dropped @ end of iteration.


Comments

Popular posts from this blog

dns - How To Use Custom Nameserver On Free Cloudflare? -

python - Pygame screen.blit not working -

c# - Web API response xml language -