-
Notifications
You must be signed in to change notification settings - Fork 17
/
Copy pathaccumulate.hpp
83 lines (64 loc) · 2.02 KB
/
accumulate.hpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
// Copyright (c) 2015-2020 Daniel Frey
// Please see LICENSE for license or visit https://github.com/taocpp/sequences/
#ifndef TAO_SEQ_ACCUMULATE_HPP
#define TAO_SEQ_ACCUMULATE_HPP
#include <type_traits>
#include "config.hpp"
#include "integer_sequence.hpp"
namespace tao
{
namespace sequence
{
#ifdef TAO_SEQ_FOLD_EXPRESSIONS
namespace impl
{
template< typename OP, typename T, T N >
struct wrap_accumulate
{
};
template< typename OP, typename T, T R, T L >
constexpr auto operator+( std::integral_constant< T, R >, wrap_accumulate< OP, T, L > ) noexcept
{
return typename OP::template apply< T, R, L >();
}
template< typename OP, typename T, T N, T... Ns >
constexpr auto accumulate() noexcept
{
return ( std::integral_constant< T, N >() + ... + wrap_accumulate< OP, T, Ns >() );
}
} // namespace impl
template< typename OP, typename T, T... Ns >
struct accumulate
: decltype( impl::accumulate< OP, T, Ns... >() )
{
};
#else
namespace impl
{
template< bool >
struct accumulate
{
template< typename, typename T, T N >
using apply = std::integral_constant< T, N >;
};
template<>
struct accumulate< false >
{
template< typename OP, typename T, T N0, T N1, T... Ns >
using apply = typename accumulate< sizeof...( Ns ) == 0 >::template apply< OP, T, OP::template apply< T, N0, N1 >::value, Ns... >;
};
} // namespace impl
template< typename OP, typename T, T... Ns >
struct accumulate
: impl::accumulate< sizeof...( Ns ) == 1 >::template apply< OP, T, Ns... >
{
};
#endif
template< typename OP, typename T, T... Ns >
struct accumulate< OP, integer_sequence< T, Ns... > >
: accumulate< OP, T, Ns... >
{
};
} // namespace sequence
} // namespace tao
#endif