1

I have a clonable struct, called GenICam. This struct has a HashMap of Rc<dyn Node> trait objects, and a HashMap of Rc<Category> structs which implement the Node trait. The keys are NodeName which is an alias type for String.

Each category has a list of feature names, which are represented in the nodes HashMap of GenICam. This list should be used to populate the node_list field with references to the nodes using the functions below:

use std::{collections::HashMap, rc::Rc};

type NodeName = String;

#[derive(Clone)]
pub struct GenICam {
    nodes: HashMap<NodeName, Rc<Node>>,
    categories: HashMap<NodeName, Rc<Category>>,
}

impl GenICam {
    fn get_categories(&self) -> Vec<Rc<Category>> {
        let mut collect = Vec::new();
        for i in &self.categories {
            collect.push(i.1.clone());
        }
        collect
    }

    /// Fills all categories with references to the features if available
    fn populate_categories(&mut self) {
        let mut cats = self.get_categories();
        for cat in cats {
            let mut mutcat = cat;
            mutcat.populate(&self);
        }
    }
}

#[derive(Clone)]
pub struct Category {
    pub name: NodeName,
    features: Vec<String>,
    pub node_list: HashMap<NodeName, Rc<Node>>,
}

impl Category {
    pub fn populate(&mut self, genicam: &GenICam) {
        for feat in &self.clone().features {
            let result = genicam.node(feat.to_string());
            match result {
                None => (),
                Some(x) => self.add_to_node_list(x),
            };
        }
    }

    /// populate the node hashmap with the given node
    pub fn add_to_node_list(&mut self, node: &Rc<Node>) {
        println!("Succes: {:?}", node.name());
        self.node_list.insert(node.name(), node.clone());
    }
}

I get the following error:

error[E0596]: cannot borrow immutable borrowed content as mutable
    --> src/genicam.rs:174:4
 |
 |             mutcat.populate(&self);
 |             ^^^^^^ cannot borrow as mutable

I cannot wrap my head around why mutcat is immutable, since it is defined as let mut.

Shepmaster
  • 388,571
  • 95
  • 1,107
  • 1,366
  • `let mut mutcat = cat;` defines a mutable binding to an immutable value. – Wesley Wiser Sep 28 '18 at 19:21
  • Ok! I can see that I think. but I have tried to get it as a mutable value, which I guess is provided by get_categories()? Is there some way I am overlooking? – Bastiaan de Graaf Sep 28 '18 at 19:24
  • I can't build in your code in the playground but I think what you want is `.iter_mut()` https://doc.rust-lang.org/std/primitive.slice.html#method.iter_mut – Wesley Wiser Sep 28 '18 at 19:26
  • There's a sort of related question here https://stackoverflow.com/questions/28587698/whats-the-difference-between-placing-mut-before-a-variable-name-and-after-the – Wesley Wiser Sep 28 '18 at 19:27
  • 2
    Thanks a lot, I struggled providing a working example without just dumping the whole project. sorry for the inconvenience, I am going to have a look at the method you suggest! – Bastiaan de Graaf Sep 28 '18 at 19:28
  • 1
    Please review how to create a [MCVE] and then [edit] your question to include it. We cannot tell what crates, types, traits, fields, etc. are present in the code, such as what `Node` is or `GenICam` is. Try to produce something that reproduces your error on the [Rust Playground](https://play.rust-lang.org) or you can reproduce it in a brand new Cargo project. There are [Rust-specific MCVE tips](//stackoverflow.com/tags/rust/info) as well. – Shepmaster Sep 28 '18 at 19:29
  • @BastiaandeGraaf No problem! Just letting you know that I'm not 100% sure. If that fixes your issue, let us know and we can improve your question by getting an MCVE that demonstrates the issue. – Wesley Wiser Sep 28 '18 at 19:31
  • 1
    I believe your question is answered by the answers of [Cannot borrow immutable borrowed content as mutable](https://stackoverflow.com/q/35005704/155423) and/or [Cannot borrow immutable borrowed content as mutable when implementing a binary tree with Rc](https://stackoverflow.com/q/41045011/155423). If you disagree, please [edit] your question to explain the differences. Otherwise, we can mark this question as already answered. – Shepmaster Sep 28 '18 at 19:41
  • the second link you provided seems to! trying to implement it now – Bastiaan de Graaf Sep 28 '18 at 19:54

0 Answers0