Comparer-Problem in Set ???



  • Hallo Gemeinde,
    habe folgendes Problem:
    Eine Klasse B hat einen set<A*> mit Zeiger auf Objete von der Klasse A.
    Nun will ich aber eine spezielle Anordnung von A-Objekten im Set implementieren. Eigentlich kann man das so machen:

    Class A
    {}
    
    Class B
    {
    struct Com
     {
       bool operator()(const A* i, const A* j) const
       {
         return ... // do compare
       }
     }
    
     std::set<A*,Com>;
    }
    

    So weit würde das funktionieren. Aber das Problem ist, dass ist in der Funktion operator() auf die Klasse B selbst zugreifen muss, d.h. z.B.

    Class B
    {
     struct Com
     {
       bool operator()(const A* i, const A* j) const
       {
         return getSomeProperty(i) < getSomeProperty(j);
       }
     }
    
     int getSomeProperty(const A* i) const
     { return ..//some property of i }
    
     std::set<A*,Com>;
    }
    

    und das geht natürlich nicht, da getSomeProperty nicht statisch ist und in Com nicht sichtbar. Aus Designgründen kann ich die Referenz auf B in A nicht speichern (so dass ich auf B-Objekt über A zugreifen kann.
    Kann man das irgendwie lösen?
    Kann man bei der Deklaration von set anstatt von Com eine boolesche Funktion von B irgendwie übergeben? Dann könnte sie nähmlich auf die lokale Datenstrukturen zugreifen.
    Irgendwie sowas:

    Class B
    {
      bool compare(const A* i, const A* j) const
      {
        return getSomeProperty(i) < getSomeProperty(j);
      }
    
     int getSomeProperty(const A* i) const
     { return ..//some property of i }
    
     std::set<A*,[b]compare[/b]>;
    }
    

    Aber das geht ja so nicht... Hat jemand eine Lösund?



  • Du könntest dem Comparator (nicht der Klasse A) eine Referenz auf das Objekt mitgeben, das zum Vergleich genutzt werden soll:

    class B
    {
      struct Comparator
      {
        bool operator()(const A* l,const A* r) const
        {
          return m_base.getProperty(l)<m_base.getProperty(r);
        }
        Comparator(const B& base) : m_base(base) {}
        const B& m_base;
      };
    
      set<A*,Comparator> m_set;
    
      B() : m_set(Comparator(*this)) {}
    };
    

    Allerdings solltest du darafu achten, daß getProperty für ein gegebenes Objekt immer den selben Wert zurückliefert, sonst könnte es die Integrität der set<> zerstören.

    (eine Alternative wäre es vermutlich, getProperty() als Element von A zu implementieren)


Anmelden zum Antworten