mirror of
https://github.com/boostorg/fusion.git
synced 2025-07-22 00:32:53 +02:00
zip to shortest of collection of variable length seqs@
[SVN r35517]
This commit is contained in:
@ -9,12 +9,17 @@
|
|||||||
#if !defined(FUSION_END_IMPL_20060123_2208)
|
#if !defined(FUSION_END_IMPL_20060123_2208)
|
||||||
#define FUSION_END_IMPL_20060123_2208
|
#define FUSION_END_IMPL_20060123_2208
|
||||||
|
|
||||||
#include <boost/fusion/sequence/intrinsic/end.hpp>
|
|
||||||
#include <boost/fusion/sequence/view/zip_view/zip_view_iterator_fwd.hpp>
|
#include <boost/fusion/sequence/view/zip_view/zip_view_iterator_fwd.hpp>
|
||||||
|
#include <boost/fusion/sequence/intrinsic/end.hpp>
|
||||||
|
#include <boost/fusion/sequence/intrinsic/begin.hpp>
|
||||||
|
#include <boost/fusion/sequence/intrinsic/size.hpp>
|
||||||
|
#include <boost/fusion/sequence/intrinsic/front.hpp>
|
||||||
|
#include <boost/fusion/iterator/advance.hpp>
|
||||||
#include <boost/fusion/algorithm/transformation/transform.hpp>
|
#include <boost/fusion/algorithm/transformation/transform.hpp>
|
||||||
#include <boost/type_traits/remove_reference.hpp>
|
#include <boost/type_traits/remove_reference.hpp>
|
||||||
#include <boost/type_traits/is_reference.hpp>
|
#include <boost/type_traits/is_reference.hpp>
|
||||||
#include <boost/mpl/assert.hpp>
|
#include <boost/mpl/assert.hpp>
|
||||||
|
#include <boost/mpl/min.hpp>
|
||||||
|
|
||||||
namespace boost { namespace fusion {
|
namespace boost { namespace fusion {
|
||||||
|
|
||||||
@ -22,29 +27,30 @@ namespace boost { namespace fusion {
|
|||||||
|
|
||||||
namespace detail
|
namespace detail
|
||||||
{
|
{
|
||||||
struct poly_end
|
template<typename M>
|
||||||
|
struct endpoints
|
||||||
{
|
{
|
||||||
template<typename SeqRef>
|
template<typename SeqRef>
|
||||||
struct result
|
struct result
|
||||||
: result_of::end<typename remove_reference<SeqRef>::type>
|
|
||||||
{
|
{
|
||||||
BOOST_MPL_ASSERT((is_reference<SeqRef>));
|
typedef typename remove_reference<SeqRef>::type Seq;
|
||||||
|
typedef typename result_of::begin<Seq>::type begin;
|
||||||
|
typedef typename result_of::advance<begin, M>::type type;
|
||||||
};
|
};
|
||||||
|
|
||||||
template<typename Seq>
|
template<typename Seq>
|
||||||
typename result<Seq&>::type
|
typename result<Seq&>::type
|
||||||
operator()(Seq& seq) const
|
operator()(Seq& seq) const
|
||||||
{
|
{
|
||||||
return fusion::end(seq);
|
return fusion::advance<M>(fusion::begin(seq));
|
||||||
}
|
}
|
||||||
|
|
||||||
template<typename Seq>
|
template<typename Seq>
|
||||||
typename result<Seq const&>::type
|
typename result<Seq const&>::type
|
||||||
operator()(Seq const& seq) const
|
operator()(Seq const& seq)
|
||||||
{
|
{
|
||||||
return fusion::end(seq);
|
return fusion::advance<M>(fusion::begin(seq));
|
||||||
}
|
}
|
||||||
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -60,19 +66,16 @@ namespace boost { namespace fusion {
|
|||||||
struct apply
|
struct apply
|
||||||
{
|
{
|
||||||
typedef zip_view_iterator<
|
typedef zip_view_iterator<
|
||||||
typename result_of::transform<typename Sequence::sequences, detail::poly_end>::type,
|
typename result_of::transform<typename Sequence::sequences, detail::endpoints<typename Sequence::size> >::type,
|
||||||
typename Sequence::category> type;
|
typename Sequence::category> type;
|
||||||
|
|
||||||
static type
|
static type
|
||||||
call(Sequence& sequence)
|
call(Sequence& sequence)
|
||||||
{
|
{
|
||||||
return type(
|
return type(
|
||||||
fusion::transform(sequence.sequences_, detail::poly_end()));
|
fusion::transform(sequence.sequences_, detail::endpoints<typename Sequence::size>()));
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
}}
|
}}
|
||||||
|
@ -9,38 +9,9 @@
|
|||||||
#if !defined(FUSION_SIZE_IMPL_20060124_0800)
|
#if !defined(FUSION_SIZE_IMPL_20060124_0800)
|
||||||
#define FUSION_SIZE_IMPL_20060124_0800
|
#define FUSION_SIZE_IMPL_20060124_0800
|
||||||
|
|
||||||
#include <boost/fusion/support/category_of.hpp>
|
|
||||||
#include <boost/fusion/iterator/deref.hpp>
|
|
||||||
#include <boost/fusion/iterator/equal_to.hpp>
|
|
||||||
#include <boost/fusion/sequence/intrinsic/value_at.hpp>
|
|
||||||
#include <boost/fusion/algorithm/query/find_if.hpp>
|
|
||||||
#include <boost/mpl/eval_if.hpp>
|
|
||||||
#include <boost/mpl/placeholders.hpp>
|
|
||||||
#include <boost/type_traits/is_same.hpp>
|
|
||||||
#include <boost/type_traits/remove_reference.hpp>
|
|
||||||
|
|
||||||
namespace boost { namespace fusion {
|
namespace boost { namespace fusion {
|
||||||
|
|
||||||
struct zip_view_tag;
|
struct zip_view_tag;
|
||||||
struct random_access_iterator_tag;
|
|
||||||
|
|
||||||
namespace detail
|
|
||||||
{
|
|
||||||
template<typename Sequence>
|
|
||||||
struct zip_view_size
|
|
||||||
{
|
|
||||||
typedef result_of::find_if<
|
|
||||||
typename Sequence::sequences,
|
|
||||||
is_same<traits::category_of<remove_reference<mpl::_> >, random_access_iterator_tag> > finder;
|
|
||||||
|
|
||||||
typedef typename remove_reference<typename mpl::eval_if<
|
|
||||||
result_of::equal_to<typename finder::type, typename result_of::end<typename Sequence::sequences>::type>,
|
|
||||||
result_of::value_at_c<typename Sequence::sequences, 0>,
|
|
||||||
result_of::deref<typename finder::type> >::type>::type best_sequence;
|
|
||||||
|
|
||||||
typedef typename fusion::result_of::size<best_sequence> type;
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
namespace extension
|
namespace extension
|
||||||
{
|
{
|
||||||
@ -55,7 +26,7 @@ namespace boost { namespace fusion {
|
|||||||
{
|
{
|
||||||
template<typename Sequence>
|
template<typename Sequence>
|
||||||
struct apply
|
struct apply
|
||||||
: detail::zip_view_size<Sequence>::type
|
: Sequence::size
|
||||||
{};
|
{};
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
@ -44,22 +44,28 @@ namespace boost { namespace fusion {
|
|||||||
: fusion::result_of::equal_to<typename fusion::result_of::find_if<Sequences, mpl::not_<is_reference<mpl::_> > >::type, typename fusion::result_of::end<Sequences>::type>
|
: fusion::result_of::equal_to<typename fusion::result_of::find_if<Sequences, mpl::not_<is_reference<mpl::_> > >::type, typename fusion::result_of::end<Sequences>::type>
|
||||||
{};
|
{};
|
||||||
|
|
||||||
template<typename Sequences>
|
struct seq_ref_size
|
||||||
struct all_same_size_impl
|
|
||||||
{
|
{
|
||||||
typedef mpl::transform_view<Sequences, fusion::result_of::size<remove_reference<mpl::_> > > sizes;
|
template<typename Seq>
|
||||||
typedef typename mpl::at_c<sizes, 0>::type first_size;
|
struct result
|
||||||
typedef mpl::iterator_range<
|
: result_of::size<typename remove_reference<Seq>::type>
|
||||||
typename mpl::next<typename mpl::begin<sizes>::type>::type,
|
{};
|
||||||
typename mpl::end<sizes>::type> remainder;
|
};
|
||||||
typedef typename mpl::find_if<remainder, mpl::not_<is_same<mpl::_, first_size> > >::type found_difference;
|
|
||||||
typedef typename is_same<found_difference, typename mpl::end<remainder>::type>::type type;
|
struct poly_min
|
||||||
|
{
|
||||||
|
template<typename Lhs, typename Rhs>
|
||||||
|
struct result
|
||||||
|
: mpl::min<Lhs, Rhs>
|
||||||
|
{};
|
||||||
};
|
};
|
||||||
|
|
||||||
template<typename Sequences>
|
template<typename Sequences>
|
||||||
struct all_same_size
|
struct min_size
|
||||||
: all_same_size_impl<Sequences>::type
|
{
|
||||||
{};
|
typedef typename result_of::transform<Sequences, detail::seq_ref_size>::type sizes;
|
||||||
|
typedef typename result_of::fold<sizes, typename result_of::front<sizes>::type, detail::poly_min>::type type;
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
struct zip_view_tag;
|
struct zip_view_tag;
|
||||||
@ -69,12 +75,12 @@ namespace boost { namespace fusion {
|
|||||||
struct zip_view : sequence_base< zip_view<Sequences> >
|
struct zip_view : sequence_base< zip_view<Sequences> >
|
||||||
{
|
{
|
||||||
BOOST_MPL_ASSERT((detail::all_references<Sequences>));
|
BOOST_MPL_ASSERT((detail::all_references<Sequences>));
|
||||||
BOOST_MPL_ASSERT((detail::all_same_size<Sequences>));
|
|
||||||
typedef typename detail::strictest_traversal<Sequences>::type category;
|
typedef typename detail::strictest_traversal<Sequences>::type category;
|
||||||
typedef zip_view_tag fusion_tag;
|
typedef zip_view_tag fusion_tag;
|
||||||
typedef fusion_sequence_tag tag; // this gets picked up by MPL
|
typedef fusion_sequence_tag tag; // this gets picked up by MPL
|
||||||
typedef mpl::true_ is_view;
|
typedef mpl::true_ is_view;
|
||||||
typedef typename fusion::result_of::as_vector<Sequences>::type sequences;
|
typedef typename fusion::result_of::as_vector<Sequences>::type sequences;
|
||||||
|
typedef typename detail::min_size<Sequences>::type size;
|
||||||
|
|
||||||
zip_view(
|
zip_view(
|
||||||
const Sequences& seqs)
|
const Sequences& seqs)
|
||||||
|
Reference in New Issue
Block a user