Boost logo

Boost :

From: Daniel Walker (daniel.j.walker_at_[hidden])
Date: 2007-04-13 14:26:17


On 4/13/07, Neal Becker <ndbecker2_at_[hidden]> wrote:
> I just posted something on ublas, but I think it may be of more general
> interest.
>
> I have been using boost::range heavily, and find it useful for generic
> interfaces. I think it is also useful to have a multi-dimensional
> extension to range. In particular, a 2-d extension would help in creating
> algorithms that can accept a variety of 2-d structures.
>
> For example, range has size, begin, end.
>
> range2d would have size1, size2, begin1, begin2.

I think this is an interesting idea, and I've been looking into a
little while. You could make this multi-dimensional not just 2d. How
about something like ..

    // get the number of lines in the plane at index 0 of a 3d space
    plane_type& space_2d = span(space_3d, 0);
    range_size<
        plane_type
>::type n_2d = size(space_2d);

I'm not sure if span is the right name for it, and this has got to be
encroaching on UBLAS' domain. But it's doable for ranges. I just tried
the following, which I believe will work for arbitrary dimensions.

#include <boost/preprocessor.hpp>
#include <boost/range.hpp>
#include <boost/utility.hpp>
using namespace boost;

#define RANGE_SPAN_RETURN_TYPE_OPEN(z, n, _) \
  typename range_value< \
/**/

#define RANGE_SPAN_RETURN_TYPE_CLOSE(z, n, _) \
>::type \
/**/

#define RANGE_SPAN_GET_OPEN(z, n, _) \
  *next(begin( \
/**/

#define RANGE_SPAN_GET_CLOSE(z, n, _) \
  ), BOOST_PP_CAT(i, n)) \
/**/

// RANGE_SPAN expands to something like ...
// template<typename Range>
// typename range_value<
// typename range_value< Range >::type
// >::type &
// span(Range& range , const int i0 , const int i1)
// {
// return *next(begin( *next(begin( range ), i0) ), i1) ;
// }
#define RANGE_SPAN(z, n, _) \
  template<typename Range> \
  BOOST_PP_REPEAT(n, RANGE_SPAN_RETURN_TYPE_OPEN, _) \
      Range \
  BOOST_PP_REPEAT(n, RANGE_SPAN_RETURN_TYPE_CLOSE, _) \
  & \
  span(Range& range BOOST_PP_ENUM_TRAILING_PARAMS(n, const int i)) \
  { \
      return \
          BOOST_PP_REPEAT(n, RANGE_SPAN_GET_OPEN, _) \
              range \
          BOOST_PP_REPEAT(n, RANGE_SPAN_GET_CLOSE, _) \
      ; \
  } \
/**/

// Overloads could be generated for larger dimensions than 3.
BOOST_PP_REPEAT(3, RANGE_SPAN, _)

int main()
{
    typedef int volume_type[1][1][1];
    typedef int plane_type[1][1];
    typedef int line_type[1];

    volume_type space_3d;

    plane_type& space_2d = span(space_3d, 0);
    range_size<
        plane_type
>::type n_2d = size(space_2d);

    line_type& space_1d = span(space_3d, 0, 0);
    range_size<
        line_type
>::type n_1d = size(space_1d);
}

Daniel


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk