2016-04-05 6 views
1

dieses Beispiel nehmenWarum kann ich sort_by_key mit einem Vec verwenden?

fn main() { 

    let mut test: Vec<u32> = Vec::new(); 

    test.push(5); 
    test.push(8); 
    test.push(0); 

    test.sort_by_key(|k| k.abs()); 
} 

Ich suchte the source code for Vec, aber ich weiß nicht ein Merkmal oder so etwas wie derive sehen.

trait SomeTrait { 
    fn sort_by_key... 
} 

impl SomeTrait for Vec... { } 

Die IntelliSense meiner IDE erkennen nicht sort_by_key entweder.

suchte ich im Rust Github und gefunden this implementation in slice.rs:

pub fn sort_by_key<B, F>(&mut self, mut f: F) 
    where F: FnMut(&T) -> B, B: Ord 
{ 
    self.sort_by(|a, b| f(a).cmp(&f(b))) 
} 

Aber ich kann nicht sehen, wie Vec auf einer Scheibe bezieht und wie Vecsort_by_key zugreifen können.

habe ich diesen Konstruktor in vec.rs:

pub fn new() -> Vec<T> { 
    Vec { 
     buf: RawVec::new(), 
     len: 0, 
    } 
} 

ich die struct navigiert, aber ich kann nicht verstehen, wo sort_by_key herkommt.


Nach dem response by Jascha

kann ich nicht verstehen, die Dokumentation als mein Englisch ist nicht sehr gut. Ich verstehe, dass durch die Verwendung von Deref die Struktur, die Deref implementiert, Methoden zugreifen kann, auf die es angewendet wird, in diesem Fall ein Stück, aber es könnte ein anderes sein?


Ich fand this url die mich Frage verstehen meine Follow-up hilft und kann anderen helfen:

struct Foo; 
impl Foo { 
    fn foo(&self) { } 
} 

struct Bar { 
    foo: Foo, 
} 

impl std::ops::Deref for Bar { 
    type Target = Foo; 

    fn deref(&self) -> &Foo { 
     &self.foo 
    } 
} 

fn main() { 
    let test: Bar = Bar { foo: Foo }; 
    test.foo(); 
} 

Ich denke, das ist sehr cool

+0

Ich kann diese Frage überhaupt nicht verstehen - können Sie vielleicht einige Komponenten davon neu schreiben? –

+0

@ ㅣ ZV ㅣ Ich aktualisiere ich hoffe du verstehst besser. Danke –

Antwort

3

Vec<T> implementiert Deref<Target=[T]> ([T] ist eine Scheibe). Sie können mehr über Deref-Zwangsmaßnahmen here finden. Die API-Dokumentation listet sogar alle methods auf, die über Deref zugänglich sind.

+0

Ich war an dieser -> https://doc.rust-lang.org/collections/vec/struct.Vec.html Der Link, den Sie setzen, ist detaillierter Dank. Ich und schaue rost/vec.rs siehe jetzt deref und ich schaue mehr darüber Danke für deine Zeit. –

+0

Sie können mir dabei helfen, ich kann die Dokumentation nicht wirklich verstehen (mein Englisch ist nicht sehr gut), ich kann verstehen, dass mit Deref, die Struktur, die Deref implementiert, auf Methoden zugreifen kann, auf die es zutrifft, in diesem Fall ist Scheibe, aber es könnte ein anderer –

5

Wie Jascha erwähnt, Vec<T> implementiert Deref<Target=[T]> und DerefMut.

Beachten Sie die spezifischen Syntax hier: Target ist ein assoziiertes Art von Deref (keine Eingabe) und die Umsetzung wie folgt aussieht:

impl<T> Deref for Vec<T> { 
    type Target = [T]; 

    // .. 
} 

Die Tatsache, dass Target ist ein assoziiertes Art von Deref wichtig ist, weil es bedeutet, dass Derefimmer nur einmal für einen bestimmten (konkreten) Typ implementiert werden kann.

Dies wiederum bedeutet, dass der Compiler beim Auflösen von Methoden auf einen Typ einfach deref-Abhängigkeiten anwenden kann.Das heißt, solange keine Methode des angegebenen Namens gefunden wird, kann er sehen, ob der aktuelle Typ erneut dereferenziert werden kann, und es erneut versuchen (ja, dies kann verkettet werden).


In der aktuellen Situation des Compilers Das bedeutet:

  • sucht nach einem sort_by_key auf &mut Vec<T>, gibt es keine
  • sucht nach einem sort_by_key auf &mut [T], es

existiert Dann transformiert es den Anruf von:

let mut v = vec![1, 3, 2]; 
v.sort_by_key(...); 

in:

let mut v = vec![1, 3, 2]; 
(&mut *v).sort_by_key(...); 

automatisch.

+0

Vielen Dank für Ihre Erklärung jetzt besser verstehen, wie es funktioniert –

+0

Ich dachte, dass es vielleicht gut wäre, den Titel "Warum kann ich sort_by_key mit einem Vec verwenden? (Deref)" aber tat nicht vorher wissen, vielleicht, wenn dieses Wort hinzugefügt wird, erleichtert es anderen für den Zugriff auf die Informationen, die Sie und andere in dieser Frage ausführlich beschrieben. Aber ich weiß nicht, ob es gut wäre, das zum Titel hinzuzufügen? –

+0

@AngelAngel: Ich weiß nicht: x –

Verwandte Themen