C++ 使用具有集合交叉点的地图

C++ 使用具有集合交叉点的地图,c++,stl,set-intersection,C++,Stl,Set Intersection,以前没有使用过set_交叉点,但我相信它可以用于地图。我编写了以下示例代码,但它没有给出我期望的结果: #include <map> #include <string> #include <iostream> #include <algorithm> using namespace std; struct Money { double amount; string currency; bool operator<

以前没有使用过set_交叉点,但我相信它可以用于地图。我编写了以下示例代码,但它没有给出我期望的结果:

#include <map>
#include <string>
#include <iostream>
#include <algorithm>

using namespace std;

struct Money
{
    double amount;
    string currency;

    bool operator< ( const Money& rhs ) const
    {
        if ( amount != rhs.amount )
            return ( amount < rhs.amount );
        return ( currency < rhs.currency );
    }
};

int main( int argc, char* argv[] )
{
    Money mn[] =
    {
        { 2.32,  "USD" },
        { 2.76,  "USD" },
        { 4.30,  "GBP" },
        { 1.21,  "GBP" },

        { 1.37,  "GBP" },
        { 6.74,  "GBP" },
        { 2.55,  "EUR" }
    };

    typedef pair< int, Money > MoneyPair;
    typedef map< int, Money > MoneyMap;

    MoneyMap map1;
    map1.insert( MoneyPair( 1, mn[0] ) );
    map1.insert( MoneyPair( 2, mn[1] ) );
    map1.insert( MoneyPair( 3, mn[2] ) );  // (3)
    map1.insert( MoneyPair( 4, mn[3] ) );  // (4)

    MoneyMap map2;
    map2.insert( MoneyPair( 3, mn[2] ) );  // (3)
    map2.insert( MoneyPair( 4, mn[3] ) );  // (4)
    map2.insert( MoneyPair( 5, mn[4] ) );
    map2.insert( MoneyPair( 6, mn[5] ) );
    map2.insert( MoneyPair( 7, mn[6] ) );

    MoneyMap out;
    MoneyMap::iterator out_itr( out.begin() );
    set_intersection( map1.begin(), map1.end(), map2.begin(), map2.end(), inserter( out, out_itr ) );

    cout << "intersection has " << out.size() << " elements." << endl;
    return 0;
}
我确信这与地图/配对上的比较器有关,但无法理解

MoneyMap map2;
map1.insert( MoneyPair( 3, mn[3] ) );  // (3)
map1.insert( MoneyPair( 4, mn[4] ) );  // (4)
map1.insert( MoneyPair( 5, mn[5] ) );
map1.insert( MoneyPair( 6, mn[6] ) );
map1.insert( MoneyPair( 7, mn[7] ) );

除非这是一个输入错误,否则您只是将内容重新插入到map1中,而不是插入到map2中。我用正确的代码测试了它,结果输出了“交叉点有2个元素。”

Niki对您的输入错误肯定是正确的--
map2
在这里是空的!然而,你需要注意其他一些事情

假设您的代码如下所示:

MoneyMap map1;
map1.insert( MoneyPair( 1, mn[1] ) );
map1.insert( MoneyPair( 2, mn[2] ) );
map1.insert( MoneyPair( 3, mn[3] ) );  // (3)
map1.insert( MoneyPair( 4, mn[4] ) );  // (4)

MoneyMap map2;
map2.insert( MoneyPair( 3, mn[4] ) );  // (3)
map2.insert( MoneyPair( 4, mn[3] ) );  // (4)
map2.insert( MoneyPair( 5, mn[6] ) );
map2.insert( MoneyPair( 6, mn[5] ) );
map2.insert( MoneyPair( 7, mn[1] ) );

MoneyMap out;
MoneyMap::iterator out_itr( out.begin() );
set_intersection(map1.begin(), map1.end(), 
                 map2.begin(), map2.end(), 
                 inserter( out, out_itr ) );
现在,会发生什么?您会发现,
out
将为空,因为
set\u intersection
使用
std::less
来比较元素,并且映射的元素是成对的——因此(3,mn[3])不同于(3,mn[4])

另一种方法是写作

set_intersection(map1.begin(), map1.end(), 
                 map2.begin(), map2.end(), 
                 inserter( out, out_itr ), map1.value_comp() );
现在,
out
将包含两个元素:(3,mn[3])和(4,mn[4]),因为它们的键匹配。元素总是从第一个迭代器范围复制


请注意,映射始终按其包含的类型
map::value\u compare
排序。如果您使用的是一个时髦的比较函数,
set\u intersection
如果没有显式提供的比较函子,那么如果映射的元素与
std::less

的顺序不一致,那么
set\u intersection
将无法工作。谢谢,您说得对,我已经更正了代码。我从一个客户网站的原始代码中重新输入了这个。客户对发布代码有严格的规定,所以我必须重新输入,没有发现错误。非常感谢。我的问题是操作员中有一个错误
set_intersection(map1.begin(), map1.end(), 
                 map2.begin(), map2.end(), 
                 inserter( out, out_itr ), map1.value_comp() );