#include <type_traits>
#include <string>
#include <iostream>
#include <functional>
// Данные
struct Base
{};
struct A : Base
{
std::string name = "A";
};
struct B : Base
{
std::string name = "B";
};
struct Meta
{
public:
template< typename T >
explicit Meta( const T& data )
: _data{data}
, _getName{
[](const Base& base) {
return static_cast<const T&>(base).name;
}
}
{
static_assert(std::is_base_of<Base, T>::value, "");
}
std::string name() const
{
return "Name is: " + _getName(_data);
}
private:
const Base& _data;
std::string (*_getName)(const Base&);
};
template< typename T >
Meta Wrap( const T& data )
{
return Meta{ data };
}
int main()
{
const A a{};
const B b{};
const auto wa = Wrap( a );
const auto wb = Wrap( b );
std::cout << wa.name() << "\n";
std::cout << wb.name() << "\n";
for ( const auto& meta : { wa, wb } )
std::cout << meta.name() << "\n";
return 0;
}
I2luY2x1ZGUgPHR5cGVfdHJhaXRzPgojaW5jbHVkZSA8c3RyaW5nPgojaW5jbHVkZSA8aW9zdHJlYW0+CiNpbmNsdWRlIDxmdW5jdGlvbmFsPgoKLy8g0JTQsNC90L3Ri9C1CnN0cnVjdCBCYXNlCnt9OwoKc3RydWN0IEEgOiBCYXNlCnsKICAgIHN0ZDo6c3RyaW5nIG5hbWUgPSAiQSI7Cn07CgpzdHJ1Y3QgQiA6IEJhc2UKewogICAgc3RkOjpzdHJpbmcgbmFtZSA9ICJCIjsKfTsKc3RydWN0IE1ldGEKewogICAgcHVibGljOgogICAgdGVtcGxhdGU8IHR5cGVuYW1lIFQgPgogICAgZXhwbGljaXQgTWV0YSggY29uc3QgVCYgZGF0YSApCiAgICAgICAgOiBfZGF0YXtkYXRhfQogICAgICAgICwgX2dldE5hbWV7CiAgICAgICAgICAgIFtdKGNvbnN0IEJhc2UmIGJhc2UpIHsKICAgICAgICAgICAgICAgIHJldHVybiBzdGF0aWNfY2FzdDxjb25zdCBUJj4oYmFzZSkubmFtZTsKICAgICAgICAgICAgfQogICAgICAgIH0KICAgIHsKICAgICAgIHN0YXRpY19hc3NlcnQoc3RkOjppc19iYXNlX29mPEJhc2UsIFQ+Ojp2YWx1ZSwgIiIpOwogICAgfQoKICAgIHN0ZDo6c3RyaW5nIG5hbWUoKSBjb25zdAogICAgewogICAgICAgIHJldHVybiAiTmFtZSBpczogIiArIF9nZXROYW1lKF9kYXRhKTsKICAgIH0KCnByaXZhdGU6CiAgICBjb25zdCBCYXNlJiBfZGF0YTsKICAgIHN0ZDo6c3RyaW5nICgqX2dldE5hbWUpKGNvbnN0IEJhc2UmKTsKfTsKCnRlbXBsYXRlPCB0eXBlbmFtZSBUID4KTWV0YSBXcmFwKCBjb25zdCBUJiBkYXRhICkKewogICAgcmV0dXJuIE1ldGF7IGRhdGEgfTsKfQoKCmludCBtYWluKCkKewogICAgY29uc3QgQSBhe307CiAgICBjb25zdCBCIGJ7fTsKICAgIGNvbnN0IGF1dG8gd2EgPSBXcmFwKCBhICk7CiAgICBjb25zdCBhdXRvIHdiID0gV3JhcCggYiApOwoKICAgIHN0ZDo6Y291dCA8PCB3YS5uYW1lKCkgPDwgIlxuIjsKICAgIHN0ZDo6Y291dCA8PCB3Yi5uYW1lKCkgPDwgIlxuIjsKCiAgICBmb3IgKCBjb25zdCBhdXRvJiBtZXRhIDogeyB3YSwgd2IgfSApCiAgICAgICAgc3RkOjpjb3V0IDw8IG1ldGEubmFtZSgpIDw8ICJcbiI7CgogICAgcmV0dXJuIDA7Cn0=