Boost logo

Boost Users :

Subject: Re: [Boost-users] [MultiIndex] more on key extractor issues
From: Joaquin M Lopez Munoz (joaquin_at_[hidden])
Date: 2013-01-20 08:19:26


John M. Dlugosz <mpbecey7gu <at> snkmail.com> writes:

>
>
> > Have you taken a look at the table in:
> >
> > http://www.boost.org/libs/multi_index/doc/tutorial/
> > key_extraction.html#advanced_key_extractors
>
> I read that part in detail (including the typo, T:gg instead of
> T::gg), going over all the MI docs again after my postings.  I agree
> this seems to address that use-case, but I really don't understand
> the table and section, and certainly had no clue what it was getting
> at when I read it without this issue specifically in mind. 

Sorry to hear that: the section's declared intent is to show how
to use member and fun extractors in the various constness scenarios
with and without pointers involved. Admittedly the subject gets rapidly
complicated, hence the inclusion of this very section in the docs.

> "The column "applicable to const elements?" states
> whether the corresponding key extractor can be used when passed
> constant elements (this relates to the elements specified in the
> first column, not the referenced
> T objects)."  What does that mean?

Consider these two scenarios

  // scenario #1
  struct T{int f();};
  multi_index_container<T,...> c;

  // scenario #2
  struct T{int f();};
  multi_index_container<T*,...> c;

In scenario #1, you can't use T::f as a key because T's inside the container
are treated as const. But in scenario #2 you can, because it is T*'s that are
treated as const, not the actual T's being pointed. to. This is what the
quoted statement refers to.

> I was actually looking at this in regards to figuring out what a
> non-const member function extractor was good for.
> "this also implies that multi_index_containers
> of elements of T cannot be sorted by T::g
> or T::gg,"  if you are not using it to sort by, what
> is the point of having the key extractor?

The key extractor are general-purpose utilities, what the table shows
is that you can't use them with multi_index_container's in some scenarios
(but you can in others)

> Anyway, I found that it works correctly on both compilers if the
> middle argument (the key type) is declared const for member and not
> for const_mem_fun.  I suppose that is due to differences in the
> metaprogramming, but really they should be treated the same.  Const
> on the first parameter, T, doesn't seem to matter if it's declared
> const or not.

The differences in usage stem from the fact that constness, when referring
to a member or member function can apply to

  1. access restrictions
  2. type returned

Consider the following

  struct T
  {
    const X f();
    X g()const;
  };

In order to index by f, one has to use

  mem_fun<T,const X,&T::f>

while g is indexed with

  const_mem_fun<T,X,&T::g>

That is, returning a const value is not the same as being a const member
function. When working with pure data members, both aspects of constness
coincide, so member<> can cope without having to resort to an alternate
const_member<> or something.

Joaquín M López Muñoz
Telefónica Digital


Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net