Konzept Multiplikationsoperator einer Matrix



  • EOutOfResources schrieb:

    Nein:

    lapack_matrix&& lapack_matrix::operator*(lapack_matrix &rhs) const
    

    Wie kommst du nur auf die Idee, eine RValue Referenz auf eine lokale Variable zurückzugeben. RValue Referenzen _sind_ auch nur Referenzen! Eine ganz normale Wert-rückgabe, allerdings mit move, gehört hier her.

    Move-Semantiks bedeutet, dass es einen Move Ctor gibt, der Move op = kann über den Move Ctor sehr einfach implementiert werden, indem man das Objekt per Value nimmt.



  • 314159265358979 schrieb:

    EOutOfResources schrieb:

    Nein:

    lapack_matrix&& lapack_matrix::operator*(lapack_matrix &rhs) const
    

    Wie kommst du nur auf die Idee, eine RValue Referenz auf eine lokale Variable zurückzugeben. RValue Referenzen _sind_ auch nur Referenzen! Eine ganz normale Wert-rückgabe, allerdings mit move, gehört hier her.

    Move-Semantiks bedeutet, dass es einen Move Ctor gibt, der Move op = kann über den Move Ctor sehr einfach implementiert werden, indem man das Objekt per Value nimmt.

    Wäre dir für ein Beispiel sehr dankbar.



  • Move-Konstruktor:

    Object(Object&& other)
        : some_variables(other.some_variables)
    {
        other.some_variables = some_default_value;
    }
    

    Hier werden die Ressourcen von other "geklaut". Wichtig ist dabei, dass other weiterhin ein gültiges Objekt ist, mit dem gearbeitet werden kann.

    op =:

    Object& operator = (Object rhs) // ganz normale Werte-übergabe
    {
        rhs.swap(*this);
        return *this;
    }
    

    Diese operator = kann sowohl kopieren, als auch moven. Er wird deswegen auch gerne als "unified assignment-operator" bezeichnet. Wenn ein R-Value übergeben wird, wird das rhs-Objekt move-constructed, sprich, der Move-Konstruktor wird für rhs aufgerufen. Wird ein L-Value übergeben, dann wird der normale Copy-Ctor aufgerufen.

    Mit diesem assignment operator entfällt auch der nervige Check, ob other == *this, außerdem ist er Excepion-Save, ein swap() sollte niemals etwas werfen.



  • CStoll schrieb:

    Da wäre es eventuell eine Idee, deine Matrix-Klasse mit Referenzzhälung und copy-on-write Funktionalität auszustatten. (d.h. der Speicher wird erst wirklich kopiert, wenn einer der Verwender etwas daran ändern will)

    Oder nur C++98-Move-Semantik à la auto_ptr , sofern man keine Wertsemantik benötigt. Ist noch etwas günstiger als intrusive_ptr , was hier ja im Prinzip nachgebaut wird.

    314159265358979 schrieb:

    Eine ganz normale Wert-rückgabe, allerdings mit move, gehört hier her.

    Ohne std::move() , eine funktionslokale Variable existiert nicht länger. Move-Konstruktoren können implizit generiert und aufgerufen werden.

    Aber heutige Compiler können schon recht gut RVO. Allerdings muss man ein paar Dinge beachten, um die Optimierung nicht zu verhindern.


Anmelden zum Antworten