Hi, Ollie,

The working piece of code code: http://is.gd/dX7hzB

First of all, try to go through the official Rust guide [1]. It is mostly 
finished and it is *really* good. In particular, it explains what ownership is 
and how it should be managed.

I’ve took your `example_box.rs` as a base and modified it as follows:
1. I’ve removed `Box`es everywhere. You shouldn’t use them unless you really 
know why you need them. You can read more on boxes and other kinds of pointers 
here [2]. You will need to do it anyway if you go through the guide [1] anyway.
2. I’ve made your functions to accept &mut Vec<Section> and &mut Section. This 
is exactly what ownership is about: these functions should not take ownership 
of their arguments, but they need to modify them, so &mut is the solution.

Apart from that your code is mostly fine.

Hope that helps!

  [1]: http://doc.rust-lang.org/guide.html
  [2]: http://doc.rust-lang.org/guide-pointers.html


On 10 сент. 2014 г., at 18:05, Oldřich Vetešník <oldrich.vetes...@gmail.com> 
wrote:

> Hello,
> 
> I have a problem with creating a mutable nested data structure when combined 
> with functions.
> I’m lost in all those &muts, boxes and lifetimes. :-)
> 
> I would like to crawl a directory looking for subdirectories and in those 
> subdirectories find all images.
> So I started with a vector for holding those subdirectories.
> Then I created a struct to hold a directory path and a vector of images.
> Also a struct for the image itself.
> 
> It all works in one function body but not when refactored into functions.
> I understand that when a variable is sent as an argument, the ownership is 
> moved so it cannot be used after the function call.
> So I sent &-references instead but then it would yell at me that borrowed 
> things are not mutable.
> So I &mut-ed it all and it would yell that lifetimes are not defined.
> So I tried to define lifetimes but then it would say that things do not live 
> long enough. This is where I stopped.
> I also tried the box-way but that yells about immutable dereference. I’m not 
> even sure I have those boxes right.
> 
> This is the code:
> (Also available here https://gist.github.com/ollie/9c81d2a368bf7bf0831a, 
> there is also a Ruby version not listed here.)
> 
> 
> With references and lifetimes:
> 
> #[deriving(Show)]
> struct Image {
>     filename: String,
> }
> 
> #[deriving(Show)]
> struct Section<'a> {
>     path:   String,
>     images: &'a mut Vec<Image>,
> }
> 
> impl Image {
>     fn new(filename: &str) -> Image {
>         Image {
>             filename: String::from_str(filename),
>         }
>     }
> }
> 
> impl<'a> Section<'a> {
>     fn new(path: &str) -> Section {
>         Section {
>             path:   String::from_str(path),
>             images: &mut Vec::new(),
>         }
>     }
> 
>     fn add_image(&mut self, image: Image) {
>         self.images.push(image);
>     }
> }
> 
> fn read_directories(sections: &mut Vec<&mut Section>) {
>     let dirs = ["./dir-a", "./dir-b"];
> 
>     for dir in dirs.iter() {
>         let mut section = &mut Section::new(*dir);
>         read_images(section);
>         sections.push(section);
>     }
> }
> 
> fn read_images(section: &mut Section) {
>     let files = ["./image-1.png", "./image-2.png"];
> 
>     for file in files.iter() {
>         section.add_image(Image::new(*file));
>     }
> }
> 
> fn main() {
>     let mut sections = Vec::new();
>     read_directories(&mut sections);
>     println!("{}", sections);
> }
> 
> 
> With boxes:
> 
> #[deriving(Show)]
> struct Image {
>     filename: String,
> }
> 
> #[deriving(Show)]
> struct Section {
>     path:   String,
>     images: Box<Vec<Image>>,
> }
> 
> impl Image {
>     fn new(filename: &str) -> Image {
>         Image {
>             filename: String::from_str(filename),
>         }
>     }
> }
> 
> impl Section {
>     fn new(path: &str) -> Section {
>         Section {
>             path:   String::from_str(path),
>             images: box Vec::new(),
>         }
>     }
> 
>     fn add_image(&mut self, image: Image) {
>         self.images.push(image);
>     }
> }
> 
> fn read_directories(sections: Box<Vec<Box<Section>>>) {
>     let dirs = ["./dir-a", "./dir-b"];
> 
>     for dir in dirs.iter() {
>         let mut section = box Section::new(*dir);
>         read_images(section);
>         sections.push(section);
>     }
> }
> 
> fn read_images(section: Box<Section>) {
>     let files = ["./image-1.png", "./image-2.png"];
> 
>     for file in files.iter() {
>         section.add_image(Image::new(*file));
>     }
> }
> 
> fn main() {
>     let mut sections = box Vec::new();
>     read_directories(sections);
>     println!("{}", sections);
> }
> 
> 
> All in one, no referenes and lifetimes:
> 
> #[deriving(Show)]
> struct Image {
>     filename: String,
> }
> 
> #[deriving(Show)]
> struct Section {
>     path:   String,
>     images: Vec<Image>,
> }
> 
> impl Image {
>     fn new(filename: &str) -> Image {
>         Image {
>             filename: String::from_str(filename),
>         }
>     }
> }
> 
> impl Section {
>     fn new(path: &str) -> Section {
>         Section {
>             path:   String::from_str(path),
>             images: Vec::new(),
>         }
>     }
> 
>     fn add_image(&mut self, image: Image) {
>         self.images.push(image);
>     }
> }
> 
> fn main() {
>     let mut sections = Vec::new();
>     let dirs         = ["./dir-a", "./dir-b"];
> 
>     for dir in dirs.iter() {
>         let mut section = Section::new(*dir);
>         let files       = ["./image-1.png", "./image-2.png"];
> 
>         for file in files.iter() {
>             section.add_image(Image::new(*file));
>         }
> 
>         sections.push(section);
>     }
> 
>     println!("{}", sections);
> 
>     // [
>     //   Section {
>     //     path: ./dir-a,
>     //     images: [Image { filename: ./image-1.png }, Image { filename: 
> ./image-2.png }]
>     //   },
>     //   Section {
>     //     path: ./dir-b,
>     //     images: [Image { filename: ./image-1.png }, Image { filename: 
> ./image-2.png }]
>     //   }
>     // ]
> }
> 
> I’ve read the tutorial, the rust-by-example site but it still feels alien to 
> me. :-/
> 
> Thank you,
> Ollie
> _______________________________________________
> Rust-dev mailing list
> Rust-dev@mozilla.org
> https://mail.mozilla.org/listinfo/rust-dev

_______________________________________________
Rust-dev mailing list
Rust-dev@mozilla.org
https://mail.mozilla.org/listinfo/rust-dev

Reply via email to