2017-08-15 31 views
1

是否可以編寫一個元函數,如果某種類型包含多個特定類型的事件template<class> class Decor,則返回該類型,但不顯示類Decorator刪除嵌套類型中的所有包裝類型

的一個例子是以下類型 A<Decor<T<B<A<Decor<C>>>>>> 轉換成 A<T<B<A<C>>>>

我們假設最終類型的結構的確是一個正確的類型,但我們不輸入型的結構假設任何事情。可能會出現這樣的情況:用於構建輸入類型的某些類型的格式爲template<class...> class或任何其他類型的類。

回答

0
template <class T> 
struct RemDec 
{ using type = T; }; 
template <class T> 
struct RemDec<Decor<T>> 
{ using type = T; }; 
template <class T> 
struct RemDec<T&> 
{ using type = typename RemDec<T>::type&; }; 
template <class T> 
struct RemDec<T&&> 
{ using type = typename RemDec<T>::type&&; }; 
template <class T> 
struct RemDec<const T> 
{ using type = typename RemDec<T>::type const; }; 
template <class T> 
struct RemDec<volatile T> 
{ using type = typename RemDec<T>::type volatile; }; 
template <template <typename...> class TT, class... Ts> 
struct RemDec<TT<Ts...>> 
{ using type = TT<typename RemDec<Ts>::type...>; } 

如果您的模板可能具有值或模板模板參數,您將需要更多的專業化。

+0

你的確有一個很好的觀點。 – Lezkus

1

您可以使用類模板,像這樣一對夫婦專門化:

template<typename T> 
struct RemDec { 
    using type = T; 
}; 

template<template<typename...> class C, typename... T> 
struct RemDec<C<T...>> { 
    using type = C<typename RemDec<T>::type...>; 
}; 

template<typename T> 
struct RemDec<Decorator<T>> { 
    using type = typename RemDec<T>::type; 
}; 

類模板有助於停止迭代在你的類型的鏈條。
第一個專業記憶一個類模板,並幫助清理遺留物。
最後一個專業化將刪除檢測到的Decorator,並繼續分析剩下的內容。


它遵循最小,工作示例:

#include<type_traits> 

template<typename> 
struct Decorator {}; 

template<typename...> 
struct S {}; 

template<typename T> 
struct RemDec { 
    using type = T; 
}; 

template<template<typename...> class C, typename... T> 
struct RemDec<C<T...>> { 
    using type = C<typename RemDec<T>::type...>; 
}; 

template<typename T> 
struct RemDec<Decorator<T>> { 
    using type = typename RemDec<T>::type; 
}; 

int main() { 
    static_assert(std::is_same< 
     typename RemDec<S<Decorator<S<S<Decorator<S<int>>>>>, Decorator<S<double>>>>::type, 
     S<S<S<S<int>>>, S<double>> 
    >::value, "!"); 
} 

正如你可以運行它看,任何實例Decorator是從原始類型刪除。

+0

上帝,你是對的。我幾乎實現了這一點,但我錯過了一些東西,我認爲你不能做這種類型的匹配。 正如我所指出的那樣,該類在其模板參數中可以是可變的,但泛化是微不足道的。非常感謝! – Lezkus

+0

@Lezkus錯過了可變的評論。請給我幾分鐘的時間來整合答案。 – skypjack

+1

@Lezkus完成。現在代碼是_variadic-oriented_。 ;-) – skypjack