variable - انواع البيانات في لغة c++



c++ أنواع متداخلة بشكل متكرر وحقن الاسم (1)

حاولت غوغلينغ هذا مع أي حظ، لذلك أنا أحاول هنا.

لدي بضع فصول، كل منها يحدد عضو منظمة struct foo . هذا النوع عضو foo يمكن أن ترث نفسها من واحدة من الطبقات السابقة، وبالتالي الحصول على نوع عضو foo نفسه.

أريد الوصول إلى أنواع foo المتداخلة باستخدام قالب ميتابروغرامينغ (انظر أدناه)، ولكن c ++ اسم حقن يدخل مشاكل، كما يتم حقن اسم نوع foo العلوي في نوع foo السفلي، ويتم حل الجزء العلوي واحد عندما أريد الوصول إلى أسفل ، ويقول باستخدام A::foo::foo .

هنا مثال:

#include <type_traits>

struct A;
struct B;

struct A {
    struct foo;
};

struct B {
    struct foo;
};

struct A::foo : B { };
struct B::foo : A { };

// handy c++11 shorthand
template<class T>
using foo = typename T::foo;

static_assert( std::is_same< foo< foo< A > >, foo< B > >::value, 
               "this should not fail (but it does)" );

static_assert( std::is_same< foo< foo< A > >, foo< A > >::value, 
               "this should fail (but it does not)" );

لمعلوماتك، أنا تنفيذ مشتقات وظيفة، foo هو نوع المشتقة. يحدث الوضع أعلاه على سبيل المثال مع الخطيئة / كوس.

تلدر: كيف يمكنني الحصول على foo<foo<A>> ليكون foo<B> ، لا foo<A> ؟

شكر !


هذا ليس حقا حل تلقائي ولكن يحل المشكلة. أنواعك توفر تيبيديف إلى الطبقة الأساسية، يتم الكشف عن غياب / وجود هذا تيديف من خلال سفيناي ويتم العثور فو المتداخلة إما من خلال القاعدة أو من خلال البحث العادي.

ربما يمكنك أتمتة has_base للتحقق من قائمة القواعد المعروفة مع is_base_of إذا كنت بحاجة إلى المزيد من التشغيل الآلي.

#include <type_traits>
template <typename T>
struct has_base
{
    typedef char yes[1];
    typedef char no[2];

    template <typename C>
    static yes& test(typename C::base*);

    template <typename>
    static no& test(...);

    static const bool value = sizeof(test<T>(0)) == sizeof(yes);
};

struct A {
    struct foo;
};

struct B {
    struct foo;
};

struct A::foo : B { typedef B base; };
struct B::foo : A { typedef A base; };

template<typename T, bool from_base = has_base<T>::value >
struct foo_impl {
  typedef typename T::base::foo type;
};

template<typename T> 
struct foo_impl<T, false> {
  typedef typename T::foo type;
};

template<typename T>
using foo = typename foo_impl<T>::type;

static_assert( std::is_same< foo< foo<A> >::, foo< B > >::value, 
               "this should not fail (but it does)" );

static_assert( std::is_same< foo< foo< A > >, foo< A > >::value, 
               "this should fail (but it does not)" );
int main()
{

  return 0;
}




typename