2015-06-22 162 views
0

我有一個轉換模板,如果轉換是安全的,它應該在指向類型的指針之間進行轉換。這就像static_cast,但允許用戶定義的類型。例如:2個複雜類型的表示,一個作爲具有2個成員的實體/成像的結構,一個作爲具有2個元素的數組。將一個指針轉換爲另一個指針是安全的。傳遞模板實例化

我的模板看起來是這樣的:

template< typename T_Src, typename T_Dest, typename T_SFINAE = void > 
struct SafePtrCast; 

template< typename T > 
struct SafePtrCast< Complex<T>*, T* > 
{ 
    T* 
    operator()(Complex<T>* data) 
    { 
     return &data->real; 
    } 
}; 

template< typename T > 
struct SafePtrCast< T*, fftw_complex* > 
    :Ptr2Ptr<T, fftw_complex>{}; 

template< typename T_Src, typename T_Dest = T_Src > 
struct Ptr2Ptr 
{ 
    using Src = T_Src; 
    using Dest = T_Dest; 

    Dest* 
    operator()(Src* data) const 
    { 
     return reinterpret_cast<Dest*>(data); 
    } 
}; 

也就是說,我可以從複雜的*轉換成T *和T *至* fftw_complex。在語義上,這意味着我也可以將Complex *轉換爲fftw_complex *。

但是我怎樣才能告訴編譯器,這是好的?我試着用:

template< typename T_Src, typename T_Dest > 
struct SafePtrCast< 
    T_Src, 
    T_Dest, 
    void_t< std::result_of_t< 
     SafePtrCast< 
      std::result_of_t< 
       SafePtrCast<T_Src, double* > 
      >, 
      T_Dest 
     > 
    > > 
>{ 
    using Conv1 = SafePtrCast< T_Src, double* >; 
    using Conv2 = SafePtrCast< double*, T_Dest >; 

    T_Dest 
    operator()(T_Src&& data) const 
    { 
     return Conv2(Conv1(std::forward<T_Src>(data))); 
    } 
}; 

,並使用此一對夫婦基本類型(雙,浮法,INT ...)的允許至少T->鹼 - >ü這應該是足夠的。

不幸的是,編譯器似乎並沒有找到SafePtrCast <複雜專業化,fftw_complex>

有沒有更好的方式來處理這件事?我的模板有什麼問題?

回答

0

怎麼樣使用特點:

template< typename T_Src, typename T_Dest, bool > 
struct Ptr2Ptr 

// allowed conversion 
template< typename T_Src, typename T_Dest> 
struct Ptr2Ptr<T_Src, T_Dest, true> 
{ 
    using Src = T_Src; 
    using Dest = T_Dest; 

    static Dest* conv(Src* data) const 
    { 
     return reinterpret_cast<Dest*>(data); 
    } 
}; 

template <typename T_Src, typename T_Dest> 
conv_trait 
{ 
    static const bool enabled = false ; 
} 
template< typename T_Src, typename T_Dest> 
struct SafePtrCast 
{ 
    T_Dest* 
    operator()(T_Src* data) const 
    { 
     return Ptr2Ptr<T_Src, T_Dest, conv_trait<T_Src, T_Dest>::value>::conv(data); 
    } 
} 

現在你可以在專門爲conv_trais允許轉換

template <class T> 
conv_trait<Complex, T *> 
{ 
    static const bool value = true ; 
} 
+0

'靜態目的地* CONV(SRC *數據)const'靜不可能是常量 –

+0

reinterpret_cast有它的缺陷,所以我想避免它,而是提供SafePtrCast的專門化(就像上面的Complex-> T) 也應該可以傳遞類似指針的類型(例如智能指針),但是在那裏我無法使用static_cast 這就是爲什麼我基本上想檢查,如果SafePtrCast的專業化T和T存在(T beeing一個整數類型) – Flamefire