2 Stimmen

Hat C++ ein Äquivalent zu Pythons __setitem__

Wie der Titel schon sagt, hat C++ das Äquivalent zu Python's setitem y getitem für den Unterricht?

Im Grunde können Sie damit etwa Folgendes tun.

MyClass anObject;

anObject[0] = 1;
anObject[1] = "foo";

7voto

newacct Punkte 114757

Überladen Sie im Grunde den Indexoperator ( operator[] ), und gibt einen Verweis zurück (so dass er sowohl gelesen als auch beschrieben werden kann)

6voto

Daniel Earwicker Punkte 111630

Sie können den []-Operator überladen, aber es ist nicht ganz dasselbe wie ein separates getitem/setitem-Methodenpaar, da Sie nicht die Möglichkeit haben, unterschiedliche Behandlungen für get und setting anzugeben.

Sie können sich jedoch annähern, indem Sie ein temporäres Objekt zurückgeben, das den Zuweisungsoperator außer Kraft setzt.

1voto

dalle Punkte 17489

Um den Beitrag von Earwicker zu ergänzen:

#include <string>
#include <iostream>

template <typename Type>
class Vector
{
public:
    template <typename Element>
    class ReferenceWrapper
    {
    public:
        explicit ReferenceWrapper(Element& elem)
         : elem_(elem)
        {
        }

        // Similar to Python's __getitem__.
        operator const Type&() const
        {
            return elem_;
        }

        // Similar to Python's __setitem__.
        ReferenceWrapper& operator=(const Type& rhs)
        {
            elem_ = rhs;
            return *this;
        }

        // Helper when Type is defined in another namespace.
        friend std::ostream& operator<<(std::ostream& os, const ReferenceWrapper& rhs)
        {
            return os << rhs.operator const Type&();
        }

    private:
        Element& elem_;
    };

    explicit Vector(size_t sz)
     : vec_(sz)
    {
    }

    ReferenceWrapper<const Type> operator[](size_t ix) const
    {
        return ReferenceWrapper<const Type>(vec_[ix]);
    }

    ReferenceWrapper<Type> operator[](size_t ix)
    {
        return ReferenceWrapper<Type>(vec_[ix]);
    }

private:
    std::vector<Type> vec_;
};

int main()
{
    Vector<std::string> v(10);
    std::cout << v[5] << "\n";

    v[5] = "42";
    std::cout << v[5] << "\n";
}

1voto

peterchen Punkte 39679

Es ist nicht portabel, aber MSVC hat __declspec(Eigenschaft) die auch Indexer zulässt:

struct Foo
{
   void SetFoo(int index, int value) { ... }
   int GetFoo(int index) { ... }

   __declspec(property(propget=GetFoo, propput=SetFoo)) int Foo[]; 
}

Abgesehen davon hat Earwicker die tragbare Lösung skizziert, aber er hat Recht, dass Sie auf viele Probleme stoßen werden.

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X