lumiera_/tests/library/meta/meta-utils-test.cpp
Ichthyostega 974c670d41 fix **** in doxygen comments
to make them stand out more prominently, some entity comments
where started with a line of starts. Unfortunately, doxygen
(and javadoc) only recogise comments which are started exactly
with /**

This caused quite some comments to be ignored by doxygen.
Credits to Hendrik Boom for spotting this problem!

A workaround is to end the line of stars with *//**
2013-10-24 23:06:36 +02:00

171 lines
4.8 KiB
C++

/*
MetaUtils(Test) - check some simple type trait helpers
Copyright (C) Lumiera.org
2011, Hermann Vosseler <Ichthyostega@web.de>
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License as
published by the Free Software Foundation; either version 2 of
the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
* *****************************************************/
#include "lib/test/run.hpp"
#include "lib/meta/util.hpp"
#include "lib/meta/typelist.hpp"
#include <string>
namespace lib {
namespace meta {
namespace test {
using std::string;
/*********************************************************************//**
* @test verify basic type trait and metaprogramming helpers.
* - marker types to tell which overload the compiler picks
* - simple trait to detect the possibility of a string conversion
* - trait to detect a typelist type
*/
class MetaUtils_test : public Test
{
void
run (Arg)
{
verify_basicAssumptions();
detect_stringConversion();
detect_typeList();
}
/** @test demonstrate / verify the
* basic type trait detection technique:
* By investigating the return type, we can
* figure out which overload the compiler picks..
*/
void
verify_basicAssumptions()
{
CHECK (sizeof(Yes_t) != sizeof (No_t));
CHECK (sizeof(Yes_t) == sizeof (probe (1)));
CHECK (sizeof(Yes_t) == sizeof (probe (1L))); // conversion long -> int
CHECK (sizeof(Yes_t) == sizeof (probe ('a'))); // conversion char -> int
CHECK (sizeof(No_t) == sizeof (probe ("a"))); // char * can't be converted
}
static Yes_t probe (int);
static No_t probe (...);
//-------------------------------------------------TEST-types--
class SubString : public string
{
public:
SubString() : string("sublunar") { }
};
class Something { };
struct SomehowStringy
{
operator string() { return "No such thing"; }
};
struct SomehowSubtle
{
operator SubString() { return SubString(); }
};
class SomehowSubSub : public SomehowSubtle { };
//-------------------------------------------------TEST-types--
template<typename TY>
static bool
can_convert (TY const&)
{
return can_convertToString<TY>::value;
}
void
detect_stringConversion()
{
CHECK ( can_convert (string("inline string")));
CHECK ( can_convert ("char literal"));
CHECK (!can_convert (23.34));
CHECK (!can_convert (23));
CHECK (!can_convert (1L));
string str("mhm");
string & str_ref (str);
string const& str_const_ref (str);
string * str_ptr = &str;
CHECK ( can_convert (str));
CHECK ( can_convert (str_ref));
CHECK ( can_convert (str_const_ref));
CHECK ( can_convert (*str_ptr));
CHECK (!can_convert (str_ptr));
SubString sub;
Something thing;
const SomehowStringy stringy = SomehowStringy();
SomehowSubSub subsub;
SubString const& subRef(subsub);
CHECK ( can_convert (sub));
CHECK (!can_convert (thing));
CHECK ( can_convert (stringy));
CHECK ( can_convert (subsub));
CHECK ( can_convert (subRef));
}
//-------------------------------------------------TEST-types--
typedef Types< int
, uint
, int64_t
, uint64_t
>::List TheList;
typedef Types< >::List EmptyList;
//-------------------------------------------------TEST-types--
void
detect_typeList()
{
CHECK ( is_Typelist<TheList>::value);
CHECK ( is_Typelist<EmptyList>::value);
CHECK (!is_Typelist<Something>::value);
}
};
/** Register this test class... */
LAUNCHER (MetaUtils_test, "unit meta");
}}} // namespace lib::meta::test