Ein std::set
funktioniert, indem alle Artikel gemäß dem Objekt <
des Objekts in Reihenfolge gehalten werden. Der Grund, warum Sie nicht-konstante Methoden für Ihr Objekt aufrufen können, ist, weil das Risiko besteht, dass diese Methoden den von Ihrem Objekt zurückgegebenen Wert ändern und somit das Set effektiv unter der Haube "neu ordnen", ohne das std::set
Wissen.
Während Sie nicht genug angegeben haben, was Sie für uns tun möchten, um die beste Antwort zu geben, hier ist ein paar Möglichkeiten, um technisch einige Methoden auf Ihrem Gerät aufrufen zu erreichen. Sie können const_cast
verwenden, um Methoden aufzurufen, von denen Sie sicher sind, dass sie den Schlüssel nicht ändern. Oder Sie können die Elemente in einen Vektor einfügen, Methoden aufrufen, die den "Schlüssel" ändern, und sie dann wieder in den ursprünglichen Satz einfügen.
// Example program
#include <iostream>
#include <string>
#include <set>
#include <algorithm>
class SomeObject
{
std::string key;
int data;
public:
SomeObject(const std::string& key_, int data_) : key(key_), data(data_)
{}
// For a item to be in a set, it must have a "<" operator that tells it how to order it
bool operator <(const SomeObject& rhs) const
{
return key < rhs.key;
}
void setKey(const std::string& key_)
{
key = key_;
}
void setData(int data_)
{
data = data_;
}
};
int main()
{
std::set<SomeObject> setobject;
setobject.insert(SomeObject("c", 1));
setobject.insert(SomeObject("a", 1));
setobject.insert(SomeObject("b", 1));
// internally, the set will keep everything in order "a", "b", "c"
// option 1 - use const_cast (risky!)
{
std::set<SomeObject>::iterator it = setobject.begin();
do {
// const_cast< SomeObject& >(*it).setKey("d"); bad idea, now the set is jacked up because its not in the right order
const_cast< SomeObject& >(*it).setData(2);
it++;
} while (it != setobject.end());
}
// option 2 - put the items in the vector, call the methods, then put them back in the original set
{
std::vector<SomeObject> tempVec(std::begin(setobject), std::end(setobject));
std::vector<SomeObject>::iterator it = tempVec.begin();
do {
it->setKey("d");
it->setData(2);
it++;
} while (it != tempVec.end());
std::set<SomeObject> newSet(std::begin(tempVec), std::end(tempVec));
std::swap(newSet, setobject); // put the new items back in the original setobject
}
}
Wenn die 'std :: set'-Richtlinien nicht mehr gelten, was brauchen Sie eigentlich? Eine 'std :: unordered_map' vielleicht? Übrigens scheinen alle Ihre Funktionsaufrufe in der Probe NOPs zu sein, außer es gibt irgendwelche Nebenwirkungen. Erwäge das Posten von _real code_. –
Warum denkst du, dass du Set nicht benutzen kannst? – koalo
Sie können die Schlüsseleigenschaften eines Satzes nicht ändern, aber Sie können das Element mit den alten Eigenschaften entfernen und durch ein neues ersetzen. Wenn Sie jedoch ein Set durchlaufen, haben Sie wahrscheinlich die falsche Datenstruktur. –