如何将不同的对添加到集合中?

Posted

技术标签:

【中文标题】如何将不同的对添加到集合中?【英文标题】:How to add distinct pairs into a set? 【发布时间】:2018-06-24 18:54:08 【问题描述】:

我正在尝试将几对int 插入一个集合,这些对没有任何顺序;即(1,2) = (2,1)。所以简单地我做如下,

typedef pair<int, int> pairs; 

set<pairs> Set;
pair <int,int> myPair;

// adding pairs:
myPair=pair<int,int>(0,1);
pathSet.insert(myPair);
myPair=pair<int,int>(0,2);
pathSet.insert(myPair);
myPair=pair<int,int>(1,0);
pathSet.insert(myPair);

所以我最终得到了一个像

这样的集合
(0,1), (0,2) , (1,0)

我想拥有

(0,1), (0,2)

如何避免重复?有什么办法吗?与'set'相比,在效率方面有没有更好的ADT像std::unordered_set

【问题讨论】:

我推荐this std::set reference,你可以了解自定义compare函数。 感谢您的链接。但是,如果有人不知道某事并在这里问,我不明白这是怎么回事?为什么别人要给负分?也许我找不到它,也不知道从哪里开始,在这里问它!它是如此不公平和令人失望! @Someprogrammerdude 预计发帖者会做一些研究,比如找到一个参考,比如我链接的那个,看看可能的比较器参数,然后尝试使用它,如果不工作,问一个关于如何使用的问题使用它。不幸的是,有些人认为所有新手问题都没有足够的研究并投反对票。即使你有a good question 并关注a good question checklist,你仍然有被否决的风险。 【参考方案1】:

您需要一个自定义比较函数。在那里,确保在比较时一对中元素的顺序无关紧要。一种简单的方法是让对中的第一个元素始终是较小的元素(否则交换第一个和第二个)。

代码可能如下所示:

int main() 

    typedef pair<int, int> pairs;

    auto cmp = [](pairs a, pairs b) 
        if (a.first > a.second) 
            swap(a.first, a.second);
        
        if (b.first > b.second) 
            swap(b.first, b.second);
        
        return a < b;
    ;
    set<pairs, decltype(cmp)> pathSet(cmp);

    pairs myPair=pair<int,int>(0,1);
    pathSet.insert(myPair);
    myPair=pair<int,int>(0,2);
    pathSet.insert(myPair);
    myPair=pair<int,int>(1,0);
    pathSet.insert(myPair);

    cout << pathSet.size();

输出:

2

【讨论】:

【参考方案2】:

您需要为std::set 提供custom compare function,因为您使用std::pair 作为模板类型。在 C++11 中,您也可以将其设为 lambda。

compare 函数的思想是首先检查Pair 是否为Pair.first &lt; Pair.second,如果不是,则在compare 函数中交换以使它们按顺序排列。这不会更改原始插入对元素的顺序,但会删除您提到的重复项。

auto compare = [](pairs lhs, pairs rhs) 
   
      if(lhs.first > lhs.second ) lhs = pairslhs.second, lhs.first ;
      if(rhs.first > rhs.second ) rhs = pairsrhs.second, rhs.first ;
      return lhs< rhs;
   ;

类似这样的:See live here

#include <iostream>
#include <set>

typedef std::pair<int, int> pairs;

int main()

   auto compare = [](pairs lhs, pairs rhs) //custom compare lambda function
   
      if(lhs.first > lhs.second ) lhs = pairslhs.second, lhs.first ;
      if(rhs.first > rhs.second ) rhs = pairsrhs.second, rhs.first ;
      return lhs< rhs;
   ;

   std::set<pairs, decltype(compare)> Set(compare);

   Set.emplace(std::make_pair(0,1)); // use can also emplace to the Set
   Set.emplace(pairs0,2);
   Set.emplace(pairs1,0);

   for(const auto& it: Set)
      std::cout << it.first << " " << it.second << std::endl;

输出:

0 1
0 2

【讨论】:

以上是关于如何将不同的对添加到集合中?的主要内容,如果未能解决你的问题,请参考以下文章

Firestore - 如何在将文档添加到集合后获取文档 ID

如何将文件中的不同行号存储到一个集合中?

从不同线程将值添加到全局集中并等待所有线程完成

使用ArrayList集合,对其添加100个不同的元素:................

如何将操作按钮添加到 collectionView 的部分单元格中?

Xamarin.Forms 如何将数据从 CollectionView 传输到不同的视图?