Into< T > for itself?

As far as I know Into< T > is always implemented for itself.
But in the code, the assumption seems does not hold.
Is that bug, or my misunderstanding?

Playground

core::iter::Once<T>: Clone is just T: Clone, BTW.

1 Like

node_extends_out_nodes expects Id and Iter::Item to be the same type, but you call it with both Id and Self::Id. The simplest fix is to call into() on both (Rust Playground):

     fn node_extend_out_node<Id>(&mut self, node_id: Id, out_node_id: Id)
     where
         Id: Into<Self::Id>,
         core::iter::Once<Id>: Clone,
     {
         let out_node_id: Self::Id = out_node_id.into();
-        self.node_extend_out_nodes(node_id, core::iter::once(out_node_id));
+        self.node_extend_out_nodes(node_id.into(), core::iter::once(out_node_id));
     }
2 Likes

That is not the problem. The problem is that the signature of node_extend_out_nodes() is:

fn node_extend_out_nodes<Id, Iter>(&mut self, node_id: Id, out_nodes_iter: Iter)
    where
        Iter: IntoIterator<Item = Id>

I.e., the type of node_id is required to be the same as the item type of the iterator.

However, when you are calling it, you are calling it like this:

        let out_node_id: Self::Id = out_node_id.into();
        self.node_extend_out_nodes(node_id, core::iter::once(out_node_id));

I.e. you are calling it with two potentially different types: the Id type parameter, and the Self::Id associated type.

3 Likes

Another possibility is to change Iter: IntoIterator<Item = Id> to Iter: IntoIterator<Item = Self::Id> in the bounds.

core::iter::Once<T>: Clone is just T: Clone , BTW.

Indeed, but without expressing it explicitly I get error:

  --> module/rust_move/wautomata/rust/impl/automata/abs/graph.rs:84:44
   |
84 |       self.node_extend_out_nodes( node_id, core::iter::once( out_node_id ) );
   |            ---------------------           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected an implementor of trait `Clone`
   |            |
   |            required by a bound introduced by this call
   |
   = note: required because of the requirements on the impl of `Clone` for `std::iter::Once<Id>`
note: required by a bound in `graph::internal::GraphEditableInterface::node_extend_out_nodes`

Oh, I see!

Are you sure that you copied the entire set of bounds for node_extend_out_nodes()? The compiler message suggests that the method requires Iter: Clone.

I can't reproduce on the playground (the Clone bound isn't required at all) but did you add T: Clone?

2 Likes

I can't reproduce on the playground (the Clone bound isn't required at all) but did you add T: Clone ?

Oh, I see. You meant replacing core::iter::Once< Id > : Clone with Id : Clone.
Yes, you are right. That works.