2017-02-09 3 views
2

Ich versuche From für eine Art zu implementieren, die ich als wandelbar Bezug zu bekommen, so dass ich impl es für eine &mut TheType, dann aber wie richtig from ich anrufen? Versuche, die ich durchgeführt habe, schlagen fehl, weil es versucht, eine Reflexion durchzuführen (TheType from TheType) oder nicht (oder nicht wissen kann) from von einem Typ &mut TheType aufrufen kann.impl konvertieren :: Aus für (änderbare) Referenz

-Code wird es besser erklären hoffentlich:

enum Component { 
    Position(Point), 
    //other stuff 
} 

struct Point { 
    x: i32, 
    y: i32, 
} 

impl<'a> std::convert::From<&'a mut Component> for &'a mut Point { 
    fn from(comp: &'a mut Component) -> &mut Point { 
     // If let or match for Components that can contain Points 
     if let &mut Component::Position(ref mut point) = comp { 
      point 
     } else { panic!("Cannot make a Point out of this component!"); } 
    } 
} 

// Some function somewhere where I know for a fact that the component passed can contain a Point. And I need to modify the contained Point. I could do if let or match here, but that would easily bloat my code since there's a few other Components I want to implement similar Froms and several functions like this one. 
fn foo(..., component: &mut Component) { 
    // Error: Tries to do a reflexive From, expecting a Point, not a Component 
    // Meaning it is trying to make a regular point, and then grab a mutable ref out of it, right? 
    let component = &mut Point::from(component) 

    // I try to do this, but seems like this is not a thing. 
    let component = (&mut Point)::from(component) // Error: unexpected ':' 

    ... 
} 

Ist das, was ich versuche, hier möglich zu tun? Die impl From oben kompiliert einfach gut, ist nur der Aufruf, der mir entgeht.

Antwort

5

Eine Möglichkeit, dies zu tun wäre, um die Art der component wie folgt zu spezifizieren:

let component: &mut Point = From::from(component); 

Wie Simon Whitehead wies darauf hin, desto mehr idiomatische Weg, dies zu tun wäre, um die entsprechende Funktion zu benutzen, into():

let component: &mut Point = component.into(); 
+3

Auch, weil die stdlib viele Variationen von 'impl In für T umfasst, wobei U: Von ' Sie dies auch tun können, nachdem 'From' Umsetzung:' lassen Komponente: & mut Punkt = component.into(); ' –

3

Die richtige Syntax lautet:

let component = <&mut Point>::from(component); 

Es ist im Wesentlichen die "turbofish" -Syntax ohne die führende ::.

Verwandte Themen