Search code examples
c++stlset-union

does std set_union always take common elements from first


When there are common elements in two arrays, does std set_union always take those common elements from the first array? From the code snippet below it shows it always picks common elements from the first array, but is this guaranteed? How to make it to pick from the second.

#include <algorithm>
#include <vector>
#include <string>
#include <iostream>

struct Foo
{
  Foo(int i, const std::string& n): id(i), name(n){}
  int id;
  std::string name;
};

bool comp(const Foo& first, const Foo& second)
{
  return first.id < second.id;
}

int main()
{
  Foo foo5A(5, "A");
  Foo foo10A(10, "A");
  Foo foo15A(15, "A");
  Foo foo20A(20, "A");
  Foo foo25A(25, "A");
  Foo fooA[] = {foo5A, foo10A, foo15A, foo20A, foo25A};

  Foo foo10B(10, "B");
  Foo foo20B(20, "B");
  Foo foo30B(30, "B");
  Foo foo40B(40, "B");
  Foo foo50B(50, "B");
  Foo fooB[] = {foo10B, foo20B, foo30B, foo40B, foo50B};

  std::vector<Foo> fooUnion;
  std::set_union(fooA, fooA+5, fooB, fooB+5, std::back_inserter(fooUnion), comp);

  for(const auto& f : fooUnion)
  {
    std::cout << f.id << ":" << f.name << std::endl;    
  }  
}

The output is:

5:A
10:A
15:A
20:A
25:A
30:B
40:B
50:B

Solution

  • Yes, it does, from the reference here:

    The union of two sets is formed by the elements that are present in either one of the sets, or in both. Elements from the second range that have an equivalent element in the first range are not copied to the resulting range.

    If you want it to pick from the second (fooB), you swap the arguments:

    std::set_union(fooB, fooB+5, fooA, fooA+5, std::back_inserter(fooUnion), comp);