-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathmp_basics.h
More file actions
130 lines (100 loc) · 2.8 KB
/
mp_basics.h
File metadata and controls
130 lines (100 loc) · 2.8 KB
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
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
#pragma once
////////////////////////////////////////
// type list
template<class...>
struct mp_list{};
///////////////////////////////////////
// bool
template<bool B>
struct mp_bool
{
static const bool value = std::integral_constant<bool, B>::value;
};
///////////////////////////////////////
// not
template<bool B>
struct mp_not
{
static const bool value = !B;
};
///////////////////////////////////////
// convert a size_t to a bool
template<size_t T>
struct mp_to_bool
{
static const bool value = static_cast<bool>(T);
};
///////////////////////////////////////
// is same
template<class A, class B>
struct mp_is_same
{
static const bool value = false;
};
template<class A>
struct mp_is_same<A, A>
{
static const bool value = true;
};
///////////////////////////////////////
//add values...
constexpr size_t mp_get_sum()
{
return 0;
}
template<class V1, class... V>
constexpr size_t mp_get_sum(V1 v1, V... v)
{
return v1 + mp_get_sum(v...);
}
//////////////////////////////////////
// get count of type in type list
template<class V, class L>
struct mp_count;
template<class V, template<class...> class L, class... T>
struct mp_count<V, L<T...>>
{
static const size_t value = mp_get_sum(mp_is_same<V, T>::value...);
};
//////////////////////////////////////
// whether or not the type list contains the type
template<class V, class L>
struct mp_contains;
template<class V, template<class...> class L, class... T>
struct mp_contains<V, L<T...>>
{
static const bool value = mp_to_bool<(mp_count<V, L<T...> >::value)>::value;
};
////////////////////////////////////////
// size of type-list
template<class L>
struct mp_size;
template<template<class...> class L, class... T>
struct mp_size<L<T...>>
{
static const size_t value = sizeof...(T);
};
////////////////////////////////////////
// index_of helper
template<size_t N, class V, class L>
struct mp_index_of_impl;
template<size_t N, class V, template<class...> class L>
struct mp_index_of_impl<N, V, L<>>
{
static const size_t value = N;
};
template<size_t N, class V, template<class...> class L, class T1, class... T>
struct mp_index_of_impl<N, V, L<T1, T...>>
{
static const size_t value = (mp_is_same<V, T1>::value) ? N : mp_index_of_impl<N+1, V, L<T...>>::value;
};
////////////////////////////////////////
// index_of
template<class V, class L>
struct mp_index_of;
template<class V, template<class...> class L, class T1, class... T>
struct mp_index_of<V, L<T1, T...>>
{
//static_assert(mp_count<V, L<T1, T...>>::value == 1, "There must be exactly one of the type in the type list");
static const size_t value = (mp_is_same<V, T1>::value) ? 0 : mp_index_of_impl<1, V, L<T...>>::value;
};