簡體   English   中英

C ++設置插入如何與自定義比較器一起使用

[英]How C++ set insert work with custom comparator

我在擰一組指針

class CLwObj {
private:
string name ;
int type ;

public:
CLwObj() {}
CLwObj(string val, int typ) { name =val ; type = typ; }

string getName() { return name; }
int getType() { return type; }
};

class CLwObjCompare
{
    public:
    bool operator () (CLwObj* obj1, CLwObj* obj2) const
    {
        bool val =  ((obj1->getName().compare(obj2->getName()) < 0) ) ;
        return val;
    }
};

int main ()
{
    set<CLwObj*, CLwObjCompare> myset ;

    CLwObj *obj1 = new CLwObj("hello", 1);
    CLwObj *obj2 = new CLwObj("kello", 1);
    CLwObj *obj3 = new CLwObj("hello", 1);

    myset.insert(obj1);
    myset.insert(obj2);
    myset.insert(obj3);
    return 0;
}

請解釋插入如何與自定義比較器一起使用,由於兩個具有相同的名稱,我僅獲得兩個條目。

我以為比較功能只能決定順序。
所有對象將具有不同的地址,因此應該有3個條目。

http://www.cplusplus.com/reference/set/set/ (在“ Compare模板”參數上):

set對象使用此表達式來確定元素在容器中遵循的順序以及兩個元素鍵是否等效 (通過反身比較它們:如果!comp(a,b)&&!comp(b,a)等效) 。 集合容器中不能有兩個元素相等。 這可以是函數指針或函數對象(有關示例,請參見構造函數)。

根據標准 §23.2.4:

  1. 每個關聯容器都在Key上進行了參數設置,並且使用了一個排序關系Compare,該關系在Key元素上引入了嚴格的弱排序(25.4)。 另外,map和multimap將任意映射類型T與Key關聯。 比較類型的對象稱為容器的比較對象。

  2. 短語“鍵的等效性”是指通過比較而不是鍵上的操作符==施加的等效關系。 也就是說,如果對於比較對象comp,comp(k1,k2)== false && comp(k2,k1)== false,則認為兩個鍵k1和k2是等效的。 對於同一容器中的任何兩個鍵k1和k2,調用comp(k1,k2)都應始終返回相同的值。

§23.4.6.1(重點是我的):

  1. 一個集合滿足容器,可逆容器(23.2), 關聯容器(23.2.4)和可識別分配器的容器(表99)的所有要求。

復制評論以繼續討論

您通過了比較器CLwObjCompareset使用該比較器確定2個對象是否相同。

參見http://en.cppreference.com/w/cpp/container/set

標准庫在所有使用比較概念的地方,唯一性都是通過等價關系確定的。 用不精確的術語來說,如果兩個對象a和b的比較值都不小於另一個,則視為等效(不是唯一的):!comp(a,b)&&!comp(b,a)

繼續討論

以下是我的建議:

class CLwObj {
private:
    string name ;
    int type ;

public:
    CLwObj() {}
    CLwObj(string val, int typ) { name =val ; type = typ; }

    string getName() const { return name; }
    int getType() const { return type; }
};

class CLwObjCompare
{
public:
    bool operator () (const CLwObj& obj1, const CLwObj& obj2) const
    {
        return lhs.getName() < rhs.getName() && lhs.getType() < rhs.getType();
    }
};

int main ()
{
    set<CLwObj, CLwObjCompare> myset ;

    myset.emplace("hello", 1);
    myset.emplace("kello", 1);
    myset.emplace("hello", 2);
    return 0;
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM