Commit 184118d9 authored by Kenneth Moreland's avatar Kenneth Moreland

Add a template that tests whether a type is in a list.

Also reduced the maximum list size to 15 (which is the current longest
single list we have). Trying to reduce the size of the generated code a
bit, which is getting a little long.
parent b368830f
......@@ -29,13 +29,6 @@
namespace vtkm {
namespace detail {
template<typename ListTag1, typename ListTag2>
struct ListJoin { };
} // namespace detail
namespace internal {
template<typename ListTag>
......@@ -57,6 +50,13 @@ struct ListTagCheck
::vtkm::internal::ListTagCheck<tag>::Valid, \
"Provided type is not a valid VTK-m list tag.")
namespace detail {
template<typename ListTag1, typename ListTag2>
struct ListJoin { };
} // namespace detail
/// A special tag for an empty list.
///
struct ListTagEmpty : detail::ListRoot {
......@@ -105,6 +105,7 @@ template<typename Functor, typename ListTag>
VTKM_CONT_EXPORT
void ListForEach(Functor &f, ListTag)
{
VTKM_IS_LIST_TAG(ListTag);
detail::ListForEachImpl(f, typename ListTag::List());
}
......@@ -115,9 +116,33 @@ template<typename Functor, typename ListTag>
VTKM_CONT_EXPORT
void ListForEach(const Functor &f, ListTag)
{
VTKM_IS_LIST_TAG(ListTag);
detail::ListForEachImpl(f, typename ListTag::List());
}
/// Checks to see if the given \c Type is in the list pointed to by \c ListTag.
/// There is a static boolean named \c value that is set to true if the type is
/// contained in the list and false otherwise.
///
template<typename ListTag, typename Type>
struct ListContains
{
VTKM_IS_LIST_TAG(ListTag);
static const bool value =
detail::ListContainsImpl<typename ListTag::List,Type>::value;
};
namespace detail {
template<typename Type, typename ListTag1, typename ListTag2>
struct ListContainsImpl<ListJoin<ListTag1,ListTag2>, Type>
{
static const bool value = (vtkm::ListContains<ListTag1,Type>::value ||
vtkm::ListContains<ListTag2,Type>::value);
};
} // namespace detail
} // namespace vtkm
#endif //vtk_m_ListTag_h
......@@ -180,6 +180,16 @@ struct TypeListTagCommon
vtkm::Vec<vtkm::Float64,3> >
{ };
// Special implementation of ListContains for TypeListTagAll to always be
// true. Although TypeListTagAll is necessarily finite, the point is to
// be all inclusive. Besides, this should speed up the compilation when
// checking a list that should contain everything.
template<typename Type>
struct ListContains<vtkm::TypeListTagAll, Type>
{
static const bool value = true;
};
} // namespace vtkm
#endif //vtk_m_TypeListTag_h
This diff is collapsed.
......@@ -41,7 +41,7 @@ $# Ignore the following comment. It is meant for the generated file.
#include <vtkm/Types.h>
$py(max_base_list=25)\
$py(max_base_list=15)\
#define VTKM_MAX_BASE_LIST $(max_base_list)
$# Python commands used in template expansion.
......@@ -68,11 +68,11 @@ def param_list(num_params, name='T', start=1):
result += ',%s%d' % (name, param)
return result
def signature(num_params, name='T', return_type='void'):
def signature(num_params, name='T', return_type='void', start=1):
result = '%s(' % return_type
if num_params > 0:
result += '%s1' % name
for param in xrange(2, num_params+1):
if num_params >= start:
result += '%s%d' % (name, start)
for param in xrange(start+1, num_params+1):
result += ',%s%d' % (name, param)
result += ')'
return result
......@@ -125,6 +125,47 @@ $endfor\
$endfor\
//-----------------------------------------------------------------------------
template<typename List, typename Type>
struct ListContainsImpl;
template<typename Type>
struct ListContainsImpl<ListBase<void()>, Type>
{
static const bool value = false;
};
template<typename Type>
struct ListContainsImpl<ListBase<void(Type)>, Type>
{
static const bool value = true;
};
template<typename Type, typename T1>
struct ListContainsImpl<ListBase<void(T1)>, Type>
{
static const bool value = false;
};
$for(num_params in xrange(2, max_base_list+1))\
template<typename Type,
$template_params(num_params, start=2)>
struct ListContainsImpl<ListBase<void(Type,$param_list(num_params, start=2))>, Type>
{
static const bool value = true;
};
template<typename Type,
$template_params(num_params)>
struct ListContainsImpl<ListBase<$signature(num_params)>, Type>
{
static const bool value =
ListContainsImpl<ListBase<$signature(num_params, start=2)>, Type>::value;
};
$endfor\
} // namespace detail
//-----------------------------------------------------------------------------
......
......@@ -24,6 +24,7 @@
#include <vtkm/testing/Testing.h>
#include <algorithm>
#include <vector>
namespace {
......@@ -94,6 +95,16 @@ void CheckSame(const vtkm::Vec<int,N> &expected,
}
}
template<int N, typename ListTag>
void CheckContains(TestClass<N>, ListTag, const std::vector<int> contents)
{
bool listContains = vtkm::ListContains<ListTag, TestClass<N> >::value;
bool shouldContain =
std::find(contents.begin(), contents.end(), N) != contents.end();
VTKM_TEST_ASSERT(listContains == shouldContain,
"ListContains check failed.");
}
template<vtkm::IdComponent N, typename ListTag>
void TryList(const vtkm::Vec<int,N> &expected, ListTag)
{
......@@ -107,6 +118,18 @@ void TryList(const vtkm::Vec<int,N> &expected, ListTag)
std::cout << " Try constant for each" << std::endl;
vtkm::ListForEach(ConstantFunctor(), ListTag());
CheckSame(expected, g_FoundType);
std::cout << " Try checking contents" << std::endl;
CheckContains(TestClass<11>(), ListTag(), functor.FoundTypes);
CheckContains(TestClass<21>(), ListTag(), functor.FoundTypes);
CheckContains(TestClass<22>(), ListTag(), functor.FoundTypes);
CheckContains(TestClass<31>(), ListTag(), functor.FoundTypes);
CheckContains(TestClass<32>(), ListTag(), functor.FoundTypes);
CheckContains(TestClass<33>(), ListTag(), functor.FoundTypes);
CheckContains(TestClass<41>(), ListTag(), functor.FoundTypes);
CheckContains(TestClass<42>(), ListTag(), functor.FoundTypes);
CheckContains(TestClass<43>(), ListTag(), functor.FoundTypes);
CheckContains(TestClass<44>(), ListTag(), functor.FoundTypes);
}
void TestLists()
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment