2

I know that in c++, the Set template stores the elements as a balanced red black tree. But I would like to know how would multiset store duplicate element. For example, it could store 1,1,2,3 as the following

    1
   / \
  1   2
       \
        3

or as

  1
   \
    1
     \
      2
       \
        3
Joseph D.
  • 11,804
  • 3
  • 34
  • 67
Himanshu Kumar
  • 155
  • 1
  • 9

1 Answers1

4

A sensible implementation of the standard library will have one data-structure implementing all four of map, multimap, set and multiset. The differences in public members boil down to "how do we compare value_type instances?" "what is the result of a duplicate insert?"

Because of the complexity requirements, it is generally a balanced binary tree.

As a sketch of how to adapt a BalancedTree:

template <typename Value, typename Compare, typename Allocator>
class BalancedTree { ... };

template<
    class Key,
    class T,
    class Compare = std::less<Key>,
    class Allocator = std::allocator<std::pair<const Key, T> >
> class map
{
public:
  using value_type = std::pair<const Key, T>;
  class value_compare 
  { 
    value_compare(Compare c) : c(c) {}
    bool operator()( const value_type& lhs, const value_type& rhs ) const
    {
      return c(lhs.first, rhs.first);
    }
    Compare c;
  }

  std::pair<iterator, bool> insert(value_type vt)
  {
    node n(vt);
    auto pos = bt.insert_point(n);
    if (value_comp()(*pos, vt))
      return { bt.splice(pos, n), true };
    return { pos, false };
  }

private:
  BalancedTree<value_type, value_compare, Allocator> bt;
}

template<
    class T,
    class Compare = std::less<T>,
    class Allocator = std::allocator<T>
> class multi_set
{
public:
  using value_type = T;
  iterator insert(value_type vt)
  {
    node n(vt);
    auto pos = bt.insert_point(n);
    return bt.splice(pos, n);
  }

private:
  BalancedTree<T, Compare, Allocator> bt;
}
Caleth
  • 52,200
  • 2
  • 44
  • 75